php - 教义2 : get count of one to many relation directly mapped in entity

标签 php doctrine-orm symfony

我使用的是doctrine2和symfony3.1

我有一个电影列表,人们可以使用一对多关系购买门票

在仪表板上,我想显示电影列表,以及每部电影购买的门票数量

通过这样做我得到了我想要的数据

    $manager = $this->getDoctrine()->getManager();
    $builder = $manager->createQueryBuilder();

    $results = $builder
        ->select('m')
        ->from('AppBundle:Movie', 'm')
        ->addSelect($builder->expr()->count('t'))
        ->leftJoin('m.tickets', 't')
        ->groupBy('m.id')
        ->getQuery()
        ->getResult()
    ;

它为 100 部电影、1 个请求制作:

SELECT
       e0_.title AS title_0,
       e0_.is_published AS is_published_1,
       e0_.description AS description_2,
       e0_.author AS author_3,
       e0_.director AS director_4,
       e0_.artist_list AS artist_list_5,
       e0_.tags_list AS tags_list_6,
       e0_.creation_time AS creation_time_7,
       e0_.id AS id_8,
       COUNT(t1_.id) AS sclr_9,
       e0_.place_id AS place_id_10,
       e0_.organization_id AS organization_id_11,
       e0_.inner_image1_id AS inner_image1_id_12,
       e0_.inner_image2_id AS inner_image2_id_13,
       e0_.inner_image3_id AS inner_image3_id_14,
       e0_.image_id AS image_id_15
FROM event e0_
LEFT JOIN event_occurence e2_ ON e0_.id = e2_.event_id
LEFT JOIN ticket t1_ ON e2_.id = t1_.occurence_id
WHERE e0_.organization_id = '956744cb-6f76-4328-8ea5-c9715d762509'
GROUP BY e0_.id
LIMIT 100;

这正是我想要的发出 SQL 请求的结果。

问题出在 ORM 方面,结果是这样组织的

[
   [ movie, nbrTickets],
   [ movie, nbrTickets],
   [ movie, nbrTickets],
]

我想知道如何向 Doctrine 提供提示,以便 nbrTickets 直接成为 Movie 的属性(目前我必须自己迭代),同时仍然只做1 个 SQL 查询(我强烈强调,所以我不想在我的 twig 中执行 movie.tickets | length

答案应满足以下要求:

  • 执行1且仅一个 SQL 查询( => 否则,当我的页面显示 100 部电影时,它将仅针对此发出 101 个查询)
  • 允许直接从实体内部访问结果(=>否则如上所述,我已经有了一个可以检索我想要的数据的解决方案,我有兴趣使代码更多地遵循 ORM)<
  • 不要检索太多数据。

“目前在学说上不可能”的答案也是可以接受的。

最佳答案

您需要正确的注释才能使电影和门票实体中的关系发挥作用。

电影实体:

 * One user has Many tickets.
 * @ORM\OneToMany(targetEntity="Ticket", mappedBy="user")
 */
private $tickets;

票证实体:

 * Many tickets have One movie.
 * @ORM\ManyToOne(targetEntity="movie", inversedBy="tickets")
 * @ORM\JoinColumn(name="movie_id", referencedColumnName="id")
 */
private $movie;

对于关系,您需要在构造函数中定义一个数组集合

public function __construct() {
    $this->tickets = new ArrayCollection();
}

您需要为 Movie 实体创建一个 getTickets 函数,如下所示:

 * tickets
 *
 * @return arrayCollection
 */
public function getTickets()
{
    return $this->tickets;
}

然后,您可以使用以下存储库调用检索电影:

    $movies = $this->getDoctrine()
        ->getRepository('AppBundle:movies')
        ->findAll();

最后你取回了票:

    $tickets = $movies[0]->getTickets()

然后你用以下方法来计算它们:

    $tickets->count()

关于php - 教义2 : get count of one to many relation directly mapped in entity,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41410163/

相关文章:

php - 对应于您的 MariaDB 服务器版本,以便在第 1 行 '3g,charging=999,diagnostic=299 ,screen=2190 ,water=299 ,camera' 附近使用正确的语法

php - <head> 在 Chrome 中显示为空

php - JQuery fomdata 将空数据发送到 php 文件?

mysql - Doctrine一对多关联: Issues with composite primary key

symfony - 查询构建器中具有不相关实体的“Invalid PathExpression. Must be a StateFieldPathExpression”

php - Magento Soap V2 CatalogProductListOfAdditionalAttributes 无法识别。

php - 如何使用 Doctrine 在 Symfony 中创建查询,从三个相关表中提取数据

entity-framework - 我可以在不将实体连接到数据库表的情况下使用 ORM 吗

php - Symfony 2.7 EntityType -> StartDateTime 和 EndDateTime 之间的 QueryBuilder 或 null

doctrine-orm - Symfony - 在 INSERT、UPDATE 或 DELETE 中以不同方式验证实体