我正在尝试根据名为Account的关联实体的属性过滤“客户”实体列表。问题是,Account实体只是一个基类,过滤的实际属性存在于其子实体(PersonalAccount和EnterpriseAccount)中,但是doctrine只允许我访问Account基类的属性。
总结一下,这是我的情况:
客户实体:
class Client
{
/** @ORM\OneToMany(targetEntity="Account", mappedBy="client") */
protected $accounts;
}
基础帐户实体:
class Account
{
/** @ORM\ManyToOne(targetEntity="Client", inversedBy="accounts") */
protected $client;
}
PersonalAccount实体(账户子)
class PersonalAccount extends Account
{
/** @ORM\Column() */
protected $name;
}
在我的控制器中,我试过了:
$qb = $em->getRepository('MyBundle:Client')->createQueryBuilder('cl');
$query = $qb->select('cl')
->innerJoin('cl.accounts', 'acc')
->where('acc.name = :name')
->setParameter('name', 'Jhon')
->getQuery();
但它抛出异常,因为基类Account没有名为“name”的属性。
如何使用继承的PersonalAccount类的属性过滤客户端实体?
答案 0 :(得分:3)
首先,您应该在父类中添加一些继承注释。 您应该从Doctrine doc:6. Inheritance Mapping中阅读本文。
事实上,继承是提升,而不是下降。
“事先没有特定的投射,任何严格的OO语言都无法访问超类并检查某个孩子上存在的属性。”
正在讨论您需要的功能here。
但是:您现在可以做的是使用类表继承,如下所示:
$qb = $em->getRepository('MyBundle:Client')->createQueryBuilder('cl');
$qb2 = $em->getRepository('MyBundle:PersonalAccount')->createQueryBuilder('persoAcc');
$query = $qb->select('cl')
->where(
$qb->expr()->in(
'cl.id',
$qb2->select('persoAcc.id')
->where('persoAcc.name = :name')
->setParameter('name', 'Jhon')
->getDql()
)
)
->getQuery();
我建议你使用Repository Class。
答案 1 :(得分:1)
在客户端添加关联:
/** @ORM\OneToMany(targetEntity="PersonalAccount", mappedBy="client") */
protected $personalAccounts;
并加入它:
->innerJoin('cl.personalAccounts', 'acc')