【问题标题】:How to limit OneToMany/ManyToOne associations depth/loop in Doctrine2?如何限制 Doctrine2 中的 OneToMany/ManyToOne 关联深度/循环?
【发布时间】:2016-12-12 13:37:04
【问题描述】:

我有 3 个教义实体。一个是User,第二个是Product,第三个是ProductUsers

因此,UserProductUsers 具有 OneToMany 关联,并且相同的 ProductProductUsers 具有 OneToMany 关联。 ProductUsersUserProductManyToOne 关联。像这样:

class Product
{
    /**
     * @var ProductUsers
     *
     * @ORM\OneToMany(targetEntity="ProductUsers", mappedBy="product")
     */
    private $productUsers;
}

class ProductUsers
{
    /**
     * @var Product
     *
     * @ORM\Id
     * @ORM\ManyToOne(targetEntity="Product", inversedBy="productUsers")
     * @ORM\JoinColumn(name="product_ID", referencedColumnName="ID")
     */
    private $product;

    /**
     * @var User
     *
     * @ORM\Id
     * @ORM\ManyToOne(targetEntity="User", inversedBy="productUsers")
     * @ORM\JoinColumn(name="user_ID", referencedColumnName="ID")
     */
    private $user;

    // extra fields ...
}

class User
{
    /**
     * @var ProductUsers
     *
     * @ORM\OneToMany(targetEntity="ProductUsers", mappedBy="user")
     */
    private $productUsers;
}

一个用户可以使用多个产品,一个产品可以有多个用户。 ProductUsers 有一些关于关系的额外信息,而不仅仅是关系。

问题是当我获取一个User 对象时,它带有关联的ProductUsers,并且它关联了Product。不仅如此,Product 还附带所有与 ProductUsers 相关联的 User 对象,这是相当大的开销。

This问题与我的问题密切相关。

我希望像 JMSSerializerBundle MaxDepth 那样在教义层面限制这一点。有没有办法在学说中限制这种开销?

【问题讨论】:

  • 这就是 Doctrine 的运作方式。您获得的集合应该是惰性集合,即只有当您访问底层数据时,才会从数据库中获取实际数据。默认情况下,当获取用户时,只会运行 SELECT * FROM users 查询。要一次获取记录(不是懒惰),您需要将它们加入 ORM 查询选择:$qb->select('u', 'up')

标签: symfony doctrine-orm doctrine associations model-associations


【解决方案1】:

我很久以前就遇到过这个问题。我试过lazy loading。这没有按预期工作,这不是我的问题的正确解决方案。所以我做了一些研发并想出了一个解决方案,我不需要从ProductProductUsersbidirectional 关系。

我只能从ProductUsers 方处理与unidirectional 相同的关系。当您需要 cascade-persist 或类似功能时,您将需要 One-To-Many 关联。我也为此写了small blog

因此,对于您的解决方案,只需将来自 ProductUsersMany-To-One 关联与 ProductUser 实体。您不需要对数据库关联进行任何更改。

当您需要为单个用户关联产品时,您始终可以在存储库中保存 Querybuilder,以便在需要关联数据时使用。

它会节省很多性能。希望对您有所帮助!

【讨论】:

  • 非常感谢@Jeet!目前我正在用DQL 解决这个问题,以获取唯一需要的。我还需要OneToMany,以防我需要产品用户列表,反之亦然,但这就是问题所在,因此自定义查询是可行的方法。 OneToMany 几乎没用 :(
猜你喜欢
  • 2013-08-20
  • 2021-09-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-02-04
  • 1970-01-01
  • 2020-09-04
相关资源
最近更新 更多