Reputation: 33
I've run into an issue with the doctrine 2 paginator. I made a very basic example which will explain the situation:
$queryBuilder->select('entity');
$queryBuilder->join('SomeModule\Entity\SomeEntity', 's', 'WITH', '(s.objectClass = :class AND p.foreignKey = :foreignkey');
$paginator = new \Doctrine\ORM\Tools\Pagination\Paginator($queryBuilder);
causes the error 'Cannot count query which selects two FROM components, cannot make distinction' in: Doctrine\ORM\Tools\Pagination\WhereInWalker
It does that because there are two components, but in this case, no columns are selected from the 'SomeModule\Entity\SomeEntity':
if (count($rootComponents) > 1) {
throw new \RuntimeException("Cannot count query which selects two FROM components, cannot make distinction");
}
In my case, it works when I comment the exception, because it will just use the first $rootComponent. Does anyone know a solution for this exotic join, without changing/extending the WhereInWalker class?
I used version 2.4.6 of the ORM, when I use the master branch: https://github.com/doctrine/doctrine2/blob/master/lib/Doctrine/ORM/Tools/Pagination/WhereInWalker.php The issue is resolved. But I'd rather not use the master branch in our environment.
Upvotes: 3
Views: 753
Reputation: 578
There is no solution for using exotic joins, without changing/extending the WhereInWalker class. The fix is now in Doctrine 2.5.0-alpha2 which is released now so you could upgrade to that if you'd like. 2.5 is scheduled to be released next month so you could wait until then if you'd like.
If you want to keep your existing Doctrine install as is changing the WhereInWalker and related classes is not terribly difficult.
First you'll need to copy
Doctrine\ORM\Tools\Pagination\LimitSubqueryWalker
Doctrine\ORM\Tools\Pagination\WhereInWalker
and Doctrine\ORM\Tools\Pagination\CountWalker
From Doctrine master branch to your own code base and change the namespace accordingly. So you might use AcmeBundle\Components\Pagination\WhereInWalker
or something similar.
You'll need to create your own Paginator which extends Doctrine\ORM\Tools\Pagination\Paginator
and then copy past the functions count
and getIterator
from the parent class. Then update the functions to use your own Walkers you created above. So in count() You replace:
$this->appendTreeWalker($countQuery, 'Doctrine\ORM\Tools\Pagination\CountWalker');
with
$this->appendTreeWalker($countQuery, 'AcmeBundle\Components\Pagination\CountWalker');
Do the same for WhereInWalker and LimitSubqueryWalker in the getIterator method. Then everything will work fine. I just did something similar with the KnpPaginator to resolve this same issue. It does create a bit of maintenance headache so be sure to undo these things if you ever update to 2.5.
Upvotes: 2