symfony querybuilder和增加sql请求号

时间:2017-09-25 07:58:24

标签: php symfony doctrine repository query-builder

我创建了一个querybuilder来将我想要的所有实体放到一个请求中,但最后,它发出了26个sql请求。

有办法吗?

感谢您的回复/帮助。

以下是查询构建器:

$builder = $this->createQueryBuilder("message")
    ->innerJoin("AppBundle:User", "user", "WITH", "message.sender = user.id")
    ->innerJoin("AppBundle:Thread", "thread", "WITH", "message.thread = thread.id")
    ->innerJoin("AppBundle:MessageMetadata", "messageMetadata", "WITH", "messageMetadata.message = message.id AND messageMetadata.participant != user.id")
;

$builder = $this->filterSoftdelete($builder, $user);

if($filters != null) {
    foreach ($filters as $key => $value) {
        $builder->andWhere("(message.recipient = :id  AND user.firstname LIKE '%". $value ."%') OR 
                (message.recipient = :id  AND user.lastname LIKE '%". $value ."%') OR 
                (message.recipient = :id  AND thread.subject LIKE '%". $value ."%')")
            ->setParameter("id", $user->getId());;
    }
} else {
    $builder->andWhere("message.recipient = :id or message.sender = :id")
        ->setParameter("id", $user->getId());
}

if($ordering != null) {
    foreach ($ordering as $key => $value) {
        if($key == "subject") {
            $builder->addOrderBy("thread.subject", $value);
        } else if($key == "createdAt") {
            $builder->addOrderBy("message." . $key, $value);
        } else {
            $builder->addOrderBy("messageMetadata.isRead", "desc");
        }
    }
} else {
    $builder->addOrderBy("messageMetadata.isRead", "desc");
}

return $this->query($builder);

1 个答案:

答案 0 :(得分:0)

您的构建器只应触发一个请求。但是,您可能正在尝试访问未获取的属性或已加入的集合,并且延迟加载会起作用,从而产生许多不需要的请求。

通常在控制器中,您可以使用构建器获取实体:

$entities = $em->getRepository('myrepo')->myCustomQuery($myparams...);

然后你遍历你的实体(也许在树枝上):

foreach ($entities as $entity) {
    $entity->getAssociation()->doSomething; // sometime here you forgot to fetch sayed association
}

解决方案是在查询构建器中使用->addSelect(),这将强制选择和保持关联实体。

基本上你在做:

SELECT entity.* FROM entity JOIN other_entity ON ...;

并且在需​​要的时候获取缺少的other_entity会导致不必要的查询。

但你应该这样做:

SELECT entity.*, other_entity.* FROM entity JOIN other_entity ON ...;

您应该使用symfony工具栏查看您的请求。

希望这有帮助