我遇到了在单个查询中获取相关实体的麻烦。我使用fetch = Eager和手动查询with join.Here是我的实体
----------------------Store.php--------------------------------------
/**
* @ORM\OneToMany(targetEntity="Mycomp\ProductBundle\Entity\Product", mappedBy="store_id", cascade={"all"},fetch="EXTRA_LAZY")
*
**/
protected $products;
--------------------Product.php---------------------------------------
/**
* @ORM\OneToMany(targetEntity="ProductOption", mappedBy="product", cascade={"all"},orphanRemoval=true,fetch="EAGER")
*
**/
protected $options;
/**
* @ORM\OneToMany(targetEntity="Like", mappedBy="product", cascade={"all"},orphanRemoval=true,indexBy="id",fetch="EAGER")
*
**/
protected $likes;
-------------------Like.php---------------------------------------------
/**
* @ORM\Id
* @ORM\ManyToOne(targetEntity="Product", inversedBy="likes")
*
**/
private $product;
/**
* @ORM\Id
* @ORM\ManyToOne(targetEntity="Mycomp\UserBundle\Entity\User",inversedBy="likes")
*
**/
private $user;
-------------------Option.php---------------------------------------------
/**
* @ORM\ManyToOne(targetEntity="Product", inversedBy="options")
*
**/
private $product;
查询:
$qb = $em->createQueryBuilder('qb1');
$qb->add('select', 'a', 'p', 'po', 'pl','sl')
->add('from', 'MycompStoreBundle:Store a')
->add('where', 'a.id = :store')
->innerJoin('a.products','p')
->leftJoin('p.options','po') // ***
->leftJoin('p.likes','pl')
->leftJoin('a.followers','sl')// ***
->setParameter('store', $id);
$store = $qb->getQuery()->getResult();
并在树枝
{% for product in store.0.products %}
{{ product.name }}
{% for option in product.options %}
{{ option }}
{% endfor %}
<div id="like-holder{{ product.id }}"> {{ like_module(product) }}</div>
{% endfor %}
对于4种产品,我会收到以下问题:
+ SELECT t0.username AS [...] FROM apps_user t0 WHERE t0.id = ? LIMIT 1
Parameters: [2]
[Display runnable query]
Time: 1.52 ms [ + Explain query ]
+ SELECT s0_.id AS id0, [...] FROM store s0_ INNER JOIN [...] WHERE (s0_.id = ?) AND s0_.dtype [...]
Parameters: ['5']
[Display runnable query]
Time: 0.89 ms [ + Explain query ]
+ SELECT t0.id AS id1, t0.name AS [...] FROM product t0 WHERE t0.store_id_id = ? AND [...]
Parameters: [5]
[Display runnable query]
Time: 0.69 ms [ + Explain query ]
+ SELECT t0.id AS id1, t0.name AS [...] FROM product_option t0 WHERE t0.product_id = ? AND [...]
Parameters: [5]
[Display runnable query]
Time: 0.46 ms [ + Explain query ]
+ SELECT t0.createdAt AS createdAt1, [...] FROM product_like t0 WHERE t0.product_id = ? AND [...]
Parameters: [5]
[Display runnable query]
Time: 0.39 ms [ + Explain query ]
+ SELECT t0.id AS id1, t0.name AS [...] FROM product_option t0 WHERE t0.product_id = ? AND [...]
Parameters: [6]
[Display runnable query]
Time: 0.54 ms [ + Explain query ]
+ SELECT t0.createdAt AS createdAt1, [...] FROM product_like t0 WHERE t0.product_id = ? AND [...]
Parameters: [6]
[Display runnable query]
Time: 0.45 ms [ + Explain query ]
+ SELECT t0.id AS id1, t0.name AS [...] FROM product_option t0 WHERE t0.product_id = ? AND [...]
Parameters: [7]
[Display runnable query]
Time: 0.42 ms [ + Explain query ]
+ SELECT t0.createdAt AS createdAt1, [...] FROM product_like t0 WHERE t0.product_id = ? AND [...]
Parameters: [7]
[Display runnable query]
Time: 0.40 ms [ + Explain query ]
+ SELECT t0.id AS id1, t0.name AS [...] FROM product_option t0 WHERE t0.product_id = ? AND [...]
Parameters: [8]
[Display runnable query]
Time: 0.37 ms [ + Explain query ]
+ SELECT t0.createdAt AS createdAt1, [...] FROM product_like t0 WHERE t0.product_id = ? AND [...]
Parameters: [8]
[Display runnable query]
Time: 0.42 ms [ + Explain query ]
为什么?正如您所看到的,我为每个产品添加了2个查询。对于喜欢和选项。
答案 0 :(得分:0)
尝试更改qb代码:
$qb = $em->createQueryBuilder('qb1');
$qb->add('select', 'a', 'p', 'po', 'pl','sl')
->add('from', 'MycompStoreBundle:Store a')
->add('where', 'a.id = :store')
->innerJoin('a.products','p')
->leftJoin('p.options','po') // ***
->leftJoin('p.likes','pl')
->leftJoin('a.followers','sl')// ***
->setParameter('store', $id);
$store = $qb->getQuery()->getResult();
为:
$qb = $em->createQueryBuilder('a');
$qb->select('a', 'p', 'po', 'pl','sl')
->from('MycompStoreBundle:Store a')
->where('a.id = :store')
->innerJoin('a.products','p')
->leftJoin('p.options','po') // ***
->leftJoin('p.likes','pl')
->leftJoin('a.followers','sl')// ***
->setParameter('store', $id);
$store = $qb->getQuery()->getResult();
答案 1 :(得分:0)
好的,这是修复,万一有人需要它。
$qb = $em->createQueryBuilder('qb1');
$qb->add('select', 'a,s,po,pi,us,so,si,su')
->add('from', 'MycompStoreBundle:Store a')
->add('where', 'a.id = :store')
->leftJoin('a.followers','so')
->leftJoin('a.tags','si')
->leftJoin('a.categories','su')
->Join('a.products','s')
->leftJoin('s.options','po')
->leftJoin('s.likes','pi')
->leftJoin('pi.user','us')
->setParameter('store', $id);
$store = $qb->getQuery()->getResult(Query::HYDRATE_ARRAY);
然后将所有内容视为数组。
答案 2 :(得分:0)
你可以通过这样做来进一步改善这个问题。
//Controller
$em = $this->getDoctrine()->getManager();
$qb = $em->createQueryBuilder();
$store = $qb->select('a', 's', 'po', 'pi', 'us', 'so', 'si', 'su')
->from('MycompStoreBundle:Store', 'a')
->add('where', 'a.id = :id')
->innerJoin('a.products','s')
->leftJoin('a.followers','so')
->leftJoin('a.tags','si')
->leftJoin('a.categories','su')
->leftJoin('s.options','po')
->leftJoin('s.likes','pi')
->leftJoin('pi.user','us')
->setParameter(compact('id'))
->getQuery()
->getOneOrNullResult();
return compact('store');
//twig
{% for product in store.products}
{% for option in product.options %}
{{ option }}
{% endfor %}
<div id="like-holder{{ product.id }}"> {{ like_module(product) }}</div>
{% else %}
// no results
{% endfor %}