web-dev-qa-db-ja.com

EntityManagerをDoctrine 2.0エンティティ内で使用する

私は2つのエンティティ:国(ID、名前)とマッピング(ID、オブジェクト、内部ID、外部ID)を持っています。国とマッピングは関連付けに関連付けられていません(マッピングには国だけでなく行があるため)。次の条件を使用して国の外部IDを取得する必要があります。

  • country.id = mapping.internalId
  • mapping.object = 'country'

そのため、Countryに関数getExternalId()を追加する予定です。

function getExternalId() {
    $em = Registry::getEntityManager();

    $mapping = $em->getRepository('Mapping')->findOneBy(array(
        'object'     => 'country',
        'internalId' => $this->getId()
    ));

    return !empty($mapping) ? $mapping->getExternalId() : false;
}

質問:

  1. エンティティ内でEntityManagerを使用することは良い習慣ですか?いいえの場合、私の場合、外部IDを取得する方法を説明してください。
  2. たぶん、yamlファイルを使用して国とマッピングを関連付けることが可能ですか?

前もって感謝します!

33
Torchello

エンティティオブジェクトがエンティティマネージャに依存することを許可することはお勧めできません。これはエンティティを永続化レイヤーに関連付けますが、これは問題でしたDoctrine 2は特に解決しようとしていました。エンティティマネージャーに依存する最大の手間は、モデルを分離してテストすることが困難になることです。 、データベースから離れています。

エンティティーマネージャーに依存する操作を処理するには、おそらくサービスオブジェクトに依存しているはずです。

// CountryService
public function getExternalId($country) {}

さらに、モデルにプロキシメソッドを作成して、外部で設定されたサービスオブジェクトを呼び出すことができます。サービスオブジェクトは、エンティティマネージャーよりもテスト中にモックを行う方がはるかに簡単です。

$country->setService($countryService);
$country->getExternalId();

// Country
public function getExternalId()
{
   $this->_service->getExternalId($this);
}  
51
Bryan M.

これは最良のアイデアではないかもしれませんが、これを行う簡単な方法があります。

doctrineのUnitOfWorkクラスは、エンティティマネージャーとそのエンティティのクラスメタデータでObjectManagerAwareを実装するエンティティをハイドレートします。

エンティティのエンティティマネージャーを取得するために必要なのは、以下の例に示すように、インターフェイスを実装することだけです。

use Doctrine\Common\Persistence\Mapping\ClassMetadata;
use Doctrine\Common\Persistence\ObjectManager;
use Doctrine\Common\Persistence\ObjectManagerAware;

/**
 * @ORM\Entity
 */
class MyEntity implements ObjectManagerAware
{
    public function injectObjectManager(ObjectManager $objectManager, ClassMetadata $classMetadata)
    {
        $this->em = $objectManager;
    }
}

データベースからクエリするのではなく、新しいエンティティを作成する場合は、たとえば、setterメソッドを使用して、エンティティマネージャーを手動で設定する必要があります。

12
juanmf

あなたが使用する必要があるのはエンティティリポジトリだと思います。これらについては、情報を見つけるのは少し難しいですが、ドキュメントで詳しく説明されています。これが Getting Started 記事へのリンクで、エンティティの「アクセス」機能の「リポジトリ」を作成する方法を説明しています。

さらに、ここにあなたが始めるためのいくつかの疑似コードがあります:

<?php
// repositories/CountryRepository.php

use Doctrine\ORM\EntityRepository;

class CountryRepository extends EntityRepository
{
    public function getExternalId()
    {
9
MikeMurko

これに対するわずかにカットされたEdgeの補足(PHP 5.4はこの投稿の時点でアルファ2にあります)は将来使用される可能性があります。

ここ は、Doctrine2内でphp 5.4トレイトを使用するいくつかの例です。その1つはアクティブエンティティと呼ばれ、Doctrine 2内でアクティブなレコードスタイルの機能を提供します。これには、エンティティ内からのエンティティマネージャーへのアクセスが含まれます。

1
Fost