doctrine QueryBuilder -- where или andWhere. Или как динамически добавлять условия в запрос

В процессе создания запросов к БД, возможно вам потребуется динамически добавлять условия where в запрос. Например, в зависимости от переданных / непереданных аргументов. В таком случае не понятно, сколько всего условий добавится в запрос, и с какого условия он будет начинаться.

Решение просто: всегда используйте метод andWhere() вместо where().

Он не добавит лишних AND в sql, но добавит нужный код.

Почему использовать where() в данном случае не получится: каждый следующий where() заменит предыдущий, а не дополнит.

Насчёт orWhere(). Здесь советуют не использовать orWhere(), т.к. иногда он выдаёт непредсказуемое поведение, а вместо него писать

->andWhere('condition OR condition2')

либо можно использовать подзапрос.

Пример

Итого. Код класса Repository (Symfony):

    $query = $this->getEntityManager()
        ->createQueryBuilder()
        ->select('s')
        ->from(Sale::class, 's');
        
        if (!empty($rejectionFilter)) {
           $query->leftJoin(Rejection::class, 'r', 'with', "r.sale = s.id ")
                ->andWhere('r.sale is null');
        }

        if (!empty($dateFrom)) {
            $query->andWhere("s.date > '{$filterValue->format('Y-m-d H:i:s')}'");
        }

        if (!empty($dateTo)) {
            $query->andWhere("s.date < '{$filterValue->format('Y-m-d H:i:s')}'");
        }

    return $query->orderBy('s.id', 'ASC')
            ->getQuery()
            ->getResult();

Источник