简体   繁体   English

原则ORM与继承

[英]Doctrine ORM and inheritance

Given the following entities: 给定以下实体:

class Entity {
    protected $id;
}
class User extends Entity {
    /** @var Entity */
    protected $target;
}
class Document extends Entity {
    protected $title;
}
class Report extends Entity {
    protected $level;
}

What mapping do I need to create so doctrine can map the User entity correctly. 我需要创建什么映射,以便该理论可以正确映射User实体。 The problem here is, I want to be able to have User::$target use any Entity (hence the Entity type hint) and later in the code be able to respond accordingly, depending if it's a Document or a Report . 这里的问题是,我希望User::$target使用任何Entity(因此具有Entity类型提示),并且稍后在代码中能够做出相应的响应,具体取决于它是Document还是Report

This also means, that in the code, I need to be able to fetch either Entity::$title if it's a Document or Entity::$level if it's a Report . 这也意味着,在代码中,我需要能够获取Entity::$title如果是DocumentEntity::$level如果是Report

Can I achieve this with doctrine? 我可以用学说来实现吗?

This should work fine. 这应该工作正常。 I did not add default annotations like "@ORM\\Entity" ( http://docs.doctrine-project.org/en/latest/reference/annotations-reference.html ) . 我没有添加“ @ORM \\ Entity”之类的默认注释http://docs.doctrine-project.org/en/latest/reference/annotations-reference.html I hope this is what you are looking for, otherwise let me know. 我希望这是您要寻找的,否则请告诉我。

/**
 * @ORM\InheritanceType("SINGLE_TABLE")
 */
class Entity {
    protected $id;
}

class User extends Entity {
    /** 
     * @ORM\ManyToOne(targetEntity="Entity")
     * @var Entity 
     */
    protected $target;
}

Have a look at: http://docs.doctrine-project.org/en/2.0.x/reference/inheritance-mapping.html You should use Single Inheritance over Class Table Inheritance due performance issues. 看一下: http : //docs.doctrine-project.org/en/2.0.x/reference/inheritance-mapping.html由于性能问题,您应该对类表继承使用单继承。

Otherwise Doctrine will make joins over child tables of the entity table because Doctrine doesn't know which type the "Entity" has. 否则,Doctrine将对实体表的子表进行联接,因为Doctrine不知道“ Entity”具有哪种类型。 Something like: 就像是:

 SELECT t1.id, t2.title, t3.level FROM entity t1 LEFT JOIN document t2 ON t2.id = t1.id LEFT JOIN report t3 ON t3.id = t1.id 

More child tables will result in more joins -> slow. 更多的子表将导致更多的联接->缓慢。

This is how you check if target is a Document or a Report and to determine which field you have to access. 这是检查目标是文档还是报告并确定您必须访问哪个字段的方法。

// loads all users
$users = $this->em->getRepository('User')->findAll();
foreach($users as $user){
    $target = $user->getTarget()
    if($target instanceof Document){
        echo $target->getTitle(); 
    }
    else if($target instanceof Report){
        echo $target->getLevel()
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM