如何在 doctrine2 queryBuilder 中实现 ON ( ... OR ...) mysql 查询

How to implement ON ( ... OR ...) mysql query in doctrine2 queryBuilder

我在 MYSQL 中有一个 SQL 查询: 例如

SELECT s.* FROM vplanning.cities as c1
INNER JOIN vplanning.cities as c2
ON (c1.id = c2.area_id)
INNER JOIN vplanning.storages as s
ON (s.city_id = c2.id OR s.city_id = c1.id)
WHERE c1.id = 109;

在学说上我可以这样写(来自我的工作代码):

$query = $em->getRepository('VplanningPageBundle:Storage')
            ->createQueryBuilder('s')
            ->innerJoin('s.city', 'c1')
            ->innerJoin('c1.area', 'c2')
            ->innerJoin('s.storagestype', 'st')
            ->where('c2.id = :cityID')
            ->andWhere('st.typename = :storagesTypeName')
            ->andWhere('s.active = :active')
            ->setParameters(array(
                'cityID' => $cityID,
                'storagesTypeName' => $storagesTypeName,
                'active' => 1
            ))
            ->orderBy('s.adress')
            ->getQuery();

如你所见,我在

中显示了我的关系
->innerJoin('s.city', 'c1')

但我还需要像

这样的关系
->innerJoin('s.city', 'c2')

条件是:

ON (s.city_id = c2.id OR s.city_id = c1.id)

但是它抛出这个错误:

Error: 'c2' is already defined

c1c2是同一个实体,有内在联系

试试这个:

$repository = $em->getRepository('VplanningPageBundle:Storage');
$qb = $repository->createQueryBuilder('storage');
//We can now use the expr()
$qb->join('storage.city', 'city', Join::WITH)
   ->join('city.area', 'area', Join::WITH, $qb->expr()->eq('area.id', ':cityID'))
   ->join('storage.storagestype', 'type', Join::WITH, $qb->expr()->eq('type.typename', ':storagesTypeName'))
   ->where('storage.active = :active')
   ->setParameters(array(
       'cityID' => $cityID,
       'storagesTypeName' => $storagesTypeName,
       'active' => 1
   ))
   ->orderBy('storage.adress');
$query = $qb->getQuery();

像这样试试

$qb = $this->getRepository('VplanningPageBundle:City')->createQueryBuilder('c');
$qb->leftJoin('c.area', 'a')
    ->join('c.storage', 's', Join::ON, $qb->expr()->orX($qb->expr()->eq('c.id', 's.id'), $qb->expr()->eq('a.id', 's.id')))
    ->innerJoin('s.storagestype', 'st')
    ->where('c.id = :cityID')
    ->andWhere('st.typename = :storagesTypeName')
    ->andWhere('s.active = :active')
    ->setParameters(array(
       'cityID' => $cityID,
       'storagesTypeName' => $storagesTypeName,
       'active' => 1,
    ))
    ->orderBy('s.adress')
    ->getQuery()
;

问题的解决对我来说很难,我必须研究一下:)

这是某个论坛版块对我的问题的回答:

$qb = $em->getRepository('VplanningPageBundle:Storage')->createQueryBuilder('storage');
            $query = $qb->join('storage.city', 'city1', Join::WITH)
                ->leftJoin('city1.area', 'area', Join::WITH, $qb->expr()->eq('area.id', ':cityID'))
                ->leftJoin('storage.city', 'city2', Join::WITH, $qb->expr()->eq('city2.id', ':cityID'))
                ->join('storage.storagestype', 'type', Join::WITH, $qb->expr()->eq('type.typename', ':storagesTypeName'))
                ->where('storage.active = :active')
                ->andWhere($qb->expr()->orX($qb->expr()->isNotNull('city2'), $qb->expr()->isNotNull('area')))
                ->setParameters(array(
                'cityID' => $cityID,
                'storagesTypeName' => $storagesTypeName,
                'active' => 1
            ))
                ->orderBy('storage.adress')
            ->getQuery();