orphanRemoval绕过onDelete吗?

时间:2015-04-18 21:25:05

标签: php symfony doctrine-orm doctrine

假设我们有两个实体(ProfileAddress)。配置文件可以包含许多地址。在那种情况下,我们有:

Profile:
    ...
    fields:
        ...
    oneToMany:
        addresses:
            targetEntity: Address
            mappedBy: profile
            orphanRemoval: true

Address:
    ...
    fields:
        ...
    manyToOne:
        profile:
            targetEntity: Profile
            inversedBy: addresses
            joinColumn:
                name: profile_id
                referencedColumnName: id
                onDelete: cascade

现在,如果删除包含许多地址的配置文件:

$em->remove($profile);

如何删除地址?

Doctrine 是否会获取与此配置文件相关的所有地址,然后将其删除或仅删除配置文件并让数据库处理这些地址?

我找到了一些关于 Hibernate 的答案,但没有关于 Doctrine 的答案。


编辑:从条款一书

添加三条音符
  

1.如果关联被标记为CASCADE = REMOVE,则Doctrine 2将获取此关联。如果是单一关联,它会将此实体传递给EntityManager#remove()。如果关联是一个集合,Doctrine将遍历其所有元素并将它们传递给EntityManager#remove()。在这两种情况下,级联删除语义都是递归应用的。对于大型对象图,这种删除策略可能非常昂贵。

     

2.使用DQL DELETE语句允许您使用单个命令删除某个类型的多个实体,而不会保留这些实体。这可以非常有效地从数据库中删除大对象图。

     

3.使用外键语义onDelete =“CASCADE”可以强制数据库在内部删除所有关联的对象。这个策略有点难以实现,但可以非常强大和快速。 您应该知道,使用策略1(CASCADE=REMOVE)完全绕过任何外键onDelete=CASCADE选项,因为Doctrine将显式地提取并删除所有关联的实体。 / p>

2 个答案:

答案 0 :(得分:3)

我做了一个测试:

我首先抓取Profile(仅profile没有加入)并将其传递给$em->remove($profile),然后 doctrine 运行另一个获取与Address相关的所有Profile的查询(一个查询)及之后, doctrine为与Profile相关的每个地址运行删除查询,在最后它删除Profile

所以,我可以说 orphanRemoval是另一种类型的级联,正如教义所说:

  

orphanRemoval :只有在从集合中删除实体时才有其他级联概念

orphanRemoval绕过onDelete

答案 1 :(得分:1)

Doctrine手册中有orphan removal部分。还有another question澄清onDelete: cascade。我希望这两个链接可以帮助您进一步理解该主题。

另外,请确保在$em->remove($profile);之后调用$em->flush();操作将本地工作单元同步到数据库。