I have 3 entities associated this way:
Don't worry, I've set associations using annotations, but I thought the following mix would be lighter/cleaner to expose my issue
Post
@ORM\ManyToOne(targetEntity="User", fetch="EAGER")
- author
User
@ORM\OneToOne(targetEntity="Vip", mappedBy="user", fetch="EAGER")
- vip
Vip
# Notice that the primary key of vip is a foreign key on User primary
@ORM\id
@ORM\OneToOne(targetEntity="User", inversedBy="peliqan", fetch="EAGER")
@ORM\JoinColumn(name="user_id", referencedColumnName="id", nullable=false)
- user
As you can see, all is set to be eagerly fetched.
What do I need?
I would like to retrieve Posts sets along with both Users & Vip infos ONLY, using a single query. (see edit)
Right now, for every post entry I get one extra query:
SELECT t0.valid AS valid_1, ...
FROM vip t0
INNER JOIN user t10 ON t0.user_id = t10.id WHERE t0.user_id = ?
when:
I execute this
$results = $qb ->select('ps') ->leftJoin('ps.author','u')->addSelect('u') ->add('where', $qb->expr()->in('ps.id', $ids)) ->getQuery()->getResult();
and even while I try to enforce FETCH_EAGER mode like this
->getQuery() ->setFetchMode('AppBundle\Entity\User', 'vip', ClassMetadata::FETCH_EAGER) ->getResult();
Note:
I managed to get rid of extra query by enforcingQuery::HYDRATE_ARRAY
upon getResult()
call.
Queries vanished which saved a third of the initial time.
The downside here is that while retrieving association as arrays, I could not take advantage of Symfony\Component\Serializer\Annotation\Groups
any more to filter entities properties and had to manually edit result set in order to remove/transform some values.
EDIT
Wilt answer is okay for the original post. I did not expose my issue the right way. I told I want to retrieve Vip infos because I thought it was a good way to get rid of the extra query I talk above. Actually I do not need Vip infos but omitting ->leftJoin('u.vip','v')->addSelect('v')
makes doctrine issue the extra query which gather Vip infos! Is there a way to prevent doctrine from executing this query?