考えると2つの教義の1対多の関連するエンティティ(Person
とCompany
)、そして私は、エンティティを取得する可能性がどのようにこのSymfony2の/ Doctrine2はquerybuilderオブジェクトからエンティティ
namespace TestBundle\Entity\Repository;
use Doctrine\ORM\EntityRepository;
class PersonRepository extends EntityRepository {
public function findAllByAge($age) {
$qb = $this->createQueryBuilder('p')
->select('p','c')
->leftjoin('p.company', 'c')
->where("p.age = :age")
->setParameter('age', $age);
// ...
}
}
ようになり、リポジトリ参加します会社の(オブジェクトまたは名前)、好ましくは$ qbオブジェクト(またはエイリアス、DQL、AST、パーサーなど)からのものですか?
理想的には、私はQuerybuilderインスタンスによって使用されるすべてのエイリアスを含む配列を持っていると思い、またはで定義された少なくともこれらの形式で、それらのエンティティと一緒に、方法を選択:
[
'p' => 'TestBundle\Entity\Person',
'c' => 'TestBundle\Entity\Company',
// etc
]
$qb->getDQLPart('join')
または$qb->getQuery()->getAST()->fromClause->identificationVariableDeclarations
のような低レベルでも、エイリアスに関する結合情報がありますが、ルートエンティティとそのエイリアス(p = TestBundle \ Entity \ Person)のみが含まれています。
getRootEntity
getRootAliases
getAllAliases
私はルートエンティティおよび/またはすべてのエイリアスを取得しますが、それらをリンクする方法はありません。
$em->getClassMetadata($rootentity)->associationMappings
は私にルートエンティティの関連付けを行い、結合のターゲットエンティティを含みますが、エイリアスはありません。私はフィールド名を$qb->getDQLPart('join')
の情報にマップすることができますが、それは私が情報を再帰的にクロールしなければならない領域に私を持ち込みます。各エンティティオブジェクトから。それは重大なエラーを引き起こす可能性があるようです。
クエリビルダは関連付けを正しいエンティティにどのように変換しますか?それとも、何もしていないエンティティを知ることなく、より低いレベルのものに構文解析するだけですか?
特定のエンティティフィールドに特定のセカンダリインデックスがあるようにするために、情報が必要です。これらの二次インデックスは注釈を使用して設定でき、doctrine($em->getClassMetadata($entity)->table['indexes']
)によってエンティティに格納されます。
クエリを作成する際にどのフィールドにセカンダリインデックスがあるかを知る必要があり、可能な限り抽象ツリーを高く保つことをお勧めします。
namespace TestBundle\Entity\Repository;
use Doctrine\ORM\EntityRepository;
class PersonRepository extends EntityRepository {
public function findAllByAge($age) {
$qb = $this->createQueryBuilder('p')
->where("p.age = :age")
->setParameter('age', $age);
return $qb->getQuery()->getResult();
}
}
...応答歩くときに、::
$people = $personRepository->findAllByAge($age);
$companies = array_map(function ($person) {
return $person->getCompany();
}, $people);
を、私はあなたが何を考えて知っている:それは、不要な作成しないでしょう
答えをありがとう。私は実際にはデータベースレベルでより小さいサブセットを取得する必要があります。これは、数百万のレコードを持つテーブルを必要とします。複雑な結合や順序付けが頻繁にあります。だから私は、クエリを実行する前に、二次インデックス情報をdoctrineから取得する必要があります。 andbuild()をquerybuilderに適用できるようにするには、この情報が必要です。その後、doctrine paginatorを使用してさらに制限されます。 – Fx32
ああ、素敵な編集。 GithubのDoctrineコードを数時間読むと、私はこのアプローチがうまくいかない、あるいはDoctrineをひどく乱用していないという結論に達しました。問題は、何百ものエンティティを持つ別々のSymfonyプロジェクトがあることです。それらはすべて、QBを引数にとり、(FunctionNodeを拡張するクラスを使用して)いくつかのカスタム機能を適用し、QBを戻す方法を持つ1つの(私的に開発された)ベンダーバンドルを共有します。だから私は実際にネイティブクエリを作成することはできません、単にquerybuilderを取得し、querybuilderを返します。 – Fx32
また、エンティティ@Indexアノテーションで定義されているセカンダリインデックスを自動的に(安全のために)検出するのは良いことでしたが、エンドユーザに、フィールド名/エイリアスの配列を指定するだけで、変換/フィルター法。 – Fx32