2012-03-08 2 views
6

Я должен выполнить этот запрос:Symfony2 подзапрос в Doctrine менеджера сущности

SELECT * FROM (SELECT * FROM product WHERE car = 'large' ORDER BY onSale DESC) AS product_ordered GROUP BY type 

В Symfony2 с помощью менеджера объекта.

Мой основной конструктор запросов будет:

$query = $em->getRepository('AutomotiveBundle:Car') 
     ->createQueryBuilder('p') 
     ->where('pr.car = ?1') 
     ->andWhere('pr.status = 1') 
     ->orderBy('pr.onSale', 'DESC') 
     ->setParameter(1, $product->getName()) 
     ->groupBy('p.type') 
     ->getQuery(); 

Но я не могу работать, как добавить в подзапрос к этому.

Ive пытался сделать отдельный запрос и присоединиться к нему, как:

->andWhere($query->expr()->in('pr.car = ?1',$query2->getQuery())); 

Но я получаю:

Call to undefined method Doctrine\ORM\Query::expr() 

ответ

8

Один Хитрость заключается в том, чтобы построить два запроса, а затем использовать getDQL(), чтобы накормить первый запрос во второй запрос.

Например, этот запрос возвращает особый список игровых идентификаторов:

$qbGameId = $em->createQueryBuilder(); 

    $qbGameId->addSelect('distinct gameGameId.id'); 

    $qbGameId->from('ZaysoCoreBundle:Event','gameGameId'); 

    $qbGameId->leftJoin('gameGameId.teams','gameTeamGameId'); 

    if ($date1) $qbGameId->andWhere($qbGameId->expr()->gte('gameGameId.date',$date1)); 
    if ($date2) $qbGameId->andWhere($qbGameId->expr()->lte('gameGameId.date',$date2)); 

Теперь использовать DQL, чтобы получить дополнительную информацию о самих играх:

$qbGames = $em->createQueryBuilder(); 

    $qbGames->addSelect('game'); 
    $qbGames->addSelect('gameTeam'); 
    $qbGames->addSelect('team'); 
    $qbGames->addSelect('field'); 

    $qbGames->addSelect('gamePerson'); 
    $qbGames->addSelect('person'); 

    $qbGames->from('ZaysoCoreBundle:Event','game'); 

    $qbGames->leftJoin('game.teams', 'gameTeam'); 
    $qbGames->leftJoin('game.persons', 'gamePerson'); 
    $qbGames->leftJoin('game.field', 'field'); 

    $qbGames->leftJoin('gameTeam.team',  'team'); 
    $qbGames->leftJoin('gamePerson.person', 'person'); 

    // Here is where we feed in the dql 
    $qbGames->andWhere($qbGames->expr()->in('game.id',$qbGameId->getDQL())); 

Вид длинного примера, но я не хотел редактировать материал и, возможно, сломал его.

+0

Я считаю, что это решение игнорирует ограничения на подзапроса @cerad. Например, $ qbGameId-> setMaxResults (20), и когда u распечатывает $ qbGames-> getDQL(), u не будет видеть ограничение на подзапрос. – EnchanterIO

+0

Одно из возможных решений: http://stackoverflow.com/questions/15877287/symfony2-doctrine-expr-subquery-error?answertab=active#tab-top – EnchanterIO

8

Вы можете использовать DBAL для выполнения любого SQL-запроса.

$conn = $this->get('database_connection');//create a connection with your DB 

$sql="SELECT * FROM (SELECT * FROM product WHERE car =? ORDER BY onSale DESC) AS product_ordered GROUP BY type"; //Your sql Query     
$stmt = $conn->prepare($sql); // Prepare your sql 
$stmt->bindValue(1, 'large'); // bind your values ,if you have to bind another value, you need to write $stmt->bindValue(2, 'anothervalue'); but your order is important so on.. 
$stmt->execute(); //execute your sql 
$result=$stmt->fetchAll(); // fetch your result 

счастливым кодирования

+0

Борясь, чтобы решить, кого принять в качестве моего ответа. Я на самом деле пошел с этим маршрутом, поскольку он меньше, но он не использует Query Builder, как ответ Cerads. – BobFlemming

+0

Thx asish! и BTW просто небольшой совет для других пользователей, которые еще не владеют symfony2 ... если вы напишете этот запрос уже в репозитории, то вы можете получить соединение через $ conn = $ this -> _ em-> getConnection(); – EnchanterIO

+0

Проблема с этим решением заключается в том, что он возвращает необработанные данные вместо объектов объектов :( – Timwi

Смежные вопросы