2013-04-04 11 views
5

Próbuję znaleźć "Produkt" według identyfikatora, a do lewej dołączyć wszystkie "zdjęcie" na dwóch warunkach: locale I stan aktywny.Doctrine2 LEWE DOŁĄCZ z 2 warunkami

Oto mój QueryBuilder:

$queryBuilder = $this->createQueryBuilder('p') 
      ->select('p, photos, photoTranslation') 
      ->leftJoin('p.photos', 'photos') 
      ->leftJoin('photos.translations', 'photoTranslation') 
      ->where('p.id = :id') 
      ->andWhere('(photoTranslation.locale = :locale OR photoTranslation.locale IS NULL)') 
      ->andWhere('(photoTranslation.active = :active OR photoTranslation.active IS NULL)') 
      ->setParameters(array(
       'id' => $id 
       'locale' => $this->getLocale(), 
       'active' => true 
      )); 

To działa dobrze, gdy nie ma żadnych zdjęć lub gdy nie są aktywne zdjęcia, ale nie wtedy, gdy jest nieaktywny zdjęcie, ponieważ nie pasuje do jednej z dwa warunki.

Jeśli używam tylko jeden warunek, na przykład tylko część locale, to działa dobrze:

$queryBuilder = $this->createQueryBuilder('p') 
      ->select('p, photos, photoTranslation') 
      ->leftJoin('p.photos', 'photos') 
      ->leftJoin('photos.translations', 'photoTranslation') 
      ->where('p.id = :id') 
      ->andWhere('(photoTranslation.locale = :locale OR photoTranslation.locale IS NULL)') 
      ->setParameters(array(
       'id' => $id 
       'locale' => $this->getLocale() 
      )); 

Na razie ja tez pętla na wynikach i Usuń wszystkie zdjęcia ... ale nieaktywnych Chciałbym zrobić czysty sposób w QueryBuilder.

Próbowałem też umieścić warunki na LEFT JOIN klauzuli:

->leftJoin('photo.translations', 'phototTranslation', Doctrine\ORM\Query\Expr\JOIN::WITH, 'photoTranslation.locale = :locale AND photoTranslation.active = :active') 

Ale ona zawsze wraca na zdjęciu, nawet jeśli jest nieaktywny.

Odpowiedz

0

wierzę jednego swojego andWhere powinny być orWhere

+0

Niestety, zarówno warunki "aktywne", jak i "locale" są w tym przypadku wymagane. – Tiois

+1

@Tiois Czy możesz dodać małą próbkę każdego stołu i oczekiwanych rezultatów? To może pomóc sobie i innym lepiej dostrzec potencjalny problem. – Shawn

+0

orW przypadku uzyskania wyników WTF zaleca się, aby go nie używać. – Hornth

11

Dla tego problemu rozwiązaniem może być:

$em = $this->getEntityManager(); 
$qb = $em->createQueryBuilder(); 
$qb 
    ->select('p', 'pp') 
    ->from('Product', 'p') 
    ->leftJoin('p.photos', 'pp') 
    ->leftJoin('pp.translations', 'ppt', Doctrine\ORM\Query\Expr\Join::WITH, $qb->expr()->andX(
     $qb->expr()->eq('ppt.locale', ':locale'), 
     $qb->expr()->eq('ppt.active', ':active') 
    )) 
    ->where('p.id', ':productId') 
    ->setParameters(
     array(
      'productId', $productId, 
      'active', $active, 
      'locale', $locale 
     ) 
    ); 

    $query = $qb->getQuery(); 
    return $query->getResult(); // or ->getSingleResult(); 

UWAGA: W tym przykładzie jest to sposób, aby to zrobić w Symfony2 (2.3) repozytorium podmiot

+0

Szukałem wszędzie przykładu, jak dodać warunki i IN wewnątrz zapytania złączenia. To "andX" uratowało mój dzień! –