使用类表继承从存储库获取子类

时间:2015-01-20 23:56:03

标签: php mysql symfony inheritance doctrine-orm

我有一个实体,比如Person,其中包含$pets的列表:

protected $pets;

public function getPets()
{
  return $this->pets;
}

标准学说。不幸的是,这些宠物可能是不同类型的,例如猫或狗,或混合物。所以我使用了Class Table Inheritance:

/**
 * @ORM\Entity
 * @ORM\Table(name="pets")
 * @ORM\InheritanceType("JOINED")
 * @ORM\DiscriminatorColumn(name="pettype", type="string")
 * @ORM\DiscriminatorMap({"cat_animal" = "CatAnimal", "dog_animal" = "DogAnimal"})
 */
class Pet
{
  /**
   * @ORM\Column(name="eventid", type="integer")
   * @ORM\Id
   */
  private $id; // protected did not work either

  /**
   * Get id
   */
  public function getId()
  {
    return $this->id;
  }
}

/**
 * @ORM\Entity
 * @ORM\Table(name="cat_animal")
 */
class CatAnimal extends Pet
{
  /**
   * @ORM\Column(type="float")
   */
  protected $height;

  // etc.
}

// DogAnimal class omitted.

使用Doctrine's docs这是相对简单的。

如果我想让一个人获得所有猫,我发现我可以这样做:

public function getCats($person)
{
  return $this->getEntityManager()->getRepository('MyBundle:CatAnimal')
    ->findByPerson($person);
}

但是,如何使用查询构建器访问子类?如果我有Person存储库($ repos here),我想做类似以下的事情:

$repos->createQueryBuilder('person')
  ->select('pet.height')
  ->join('person.pets', 'pet')
  ->where('person = :person')
  ->setParameter('person', $person);

除了宠物没有身高,所以这会引发异常。生成的DQL自动连接到DogAnimal和CatAnimal,所以我应该能够访问这些属性,但我不知道如何。我试过了:

$repos->createQueryBuilder('person')
  ->select('cat.height')
  ->from('MyBundle:CatAnimal', 'cat)
  ->join('person.pets', 'pet')
  ->where('person = :person')
  ->setParameter('person', $person);

但这似乎是笛卡尔积。我可以通过添加:

来解决这个问题
->andWhere('person.id = cat.person')

对于我想要的东西,这似乎过于复杂。我一直试图寻找正确的方法,但资源有限。

这基于previous question,具有类似的结构。为了清晰和普遍性,更改了表格的名称。

1 个答案:

答案 0 :(得分:1)

您需要正确加入Person,向Pet课程添加字段。在我的例子中,我将其命名为owner

$catRepo->createQueryBuilder('cat')
  ->select('cat.height')
  ->from('MyBundle:CatAnimal', 'cat')
  ->join('cat.owner', 'person')
  ->where('person = :person')
  ->setParameter('person', $person);