symfony - Doctrine ORM select articles by list of tags -
i have webinar
entity connected tag
's many-to-many association.
i want fetch webinars list of tags, webinar must have tags in list appear in result.
and have following code query it:
$tags = [1, 2]; // base query. $builder = $this->getentitymanager()->createquerybuilder() ->select('w, vr, ar, t') ->from('model:webinar', 'w') ->leftjoin('w.videorecord', 'vr') ->leftjoin('w.audiorecord', 'ar') ->leftjoin('w.tags', 't') ; // tags query. if (isset($tags)) { $builder ->andwhere('t.id in (:tags)') ->setparameter('tags', $tags) ; } // other conditions. // ... // issuing query. return $builder->getquery()->getresult();
this query give me webinars have @ least 1 tag in list (or), want have tags in list (and).
i've found answer. looks have more complex example , i'm not sure how re-write code enable correct behavior, have other joined entities , additional conditions. possible isolate behavior in single block without breaking whole query , other conditionals?
i not being able use both aggregations , fetching in single query decided split in two.
by using first query apply necessary conditions in order receive list of webinar ids , using second query fetch object graph these ids.
here's complete example:
// i. making first query fetch webinar ids. // base query. $builder = $this->getentitymanager()->createquerybuilder() ->select('w.id') ->from('model:webinar', 'w') ->orderby('w.' . $sort, $order) ; // selected tags condition. if (is_array($criteria['tags']) && count($criteria['tags']) > 0) { $builder ->innerjoin('w.tags', 't', 'with', 't.id in (:tags)') ->setparameter('tags', $criteria['tags']) ->groupby('w.id') ->having('count(t.id) = :tags_count') ->setparameter('tags_count', count($criteria['tags'])) ; } // additional conditions // ... // building list of webinar ids. $ids = []; foreach ($builder->getquery()->getscalarresult() $record) { $ids[] = $record['id']; } // ii. , selecting complete object graph specified webinar ids. // base query. $builder = $this->getentitymanager()->createquerybuilder() ->select('w, vr, ar, t') ->from('model:webinar', 'w') ->leftjoin('w.videorecord', 'vr') ->leftjoin('w.audiorecord', 'ar') ->leftjoin('w.tags', 't') ->where('w.id in (:ids)') ->setparameter('ids', $ids) ; // issuing query. return $builder->getquery()->getresult();
i hope someone. cheers!
Comments
Post a Comment