symfonydoctrinedqlcreatequery

Doctrine (Symfony 2.0.x) createBuilder one-to-many - no idea how to get the right Entities


I'm searching the net for hours now and can't find a soluting for the following (reduced) problem:

I have two entities in my Symfony2-project:

/**
 * @ORM\Entity(repositoryClass="myBundle\Entity\AppuserRepository")
 * @ORM\Table(name="appuser")
 */
class Appuser implements UserInterface {
    /**
     * @ORM\Id
     * @ORM\Column(type="integer")
     * @ORM\GeneratedValue(strategy="AUTO")
     */
    protected $id = "";

    /**
     * @ORM\OneToMany(targetEntity="Watched", mappedBy="appuserReference")
     */
    protected $watches;

    // ________________________________________________________________________

    public function __construct() {
        $this->watches = new \Doctrine\Common\Collections\ArrayCollection();
    }

}
/**
 * @ORM\Entity
 * @ORM\Table(name="watched")
 */
class Watched extends WatchedAbstract {
    /**
     * @ORM\ManyToOne(targetEntity="Appuser", inversedBy="watches")
     * @ORM\JoinColumn(name="appuserReference_id", referencedColumnName="id")
     */
    protected $appuserReference;
}

How do I use the queryBuilder oder createQuery to get all the Users, that are referenced by a couple of the Watched-Entities (i.e., the ones with the IDs 1, 3 and 12 ;-))?

This is the SQL that runs right in MySql and which I can't 'translate'to DQL:

SELECT * FROM appuser WHERE id IN (
    SELECT w.appuserReference_id 
        FROM watched w WHERE w.id IN (1, 3, 12));

I just manage to join in the other direction, because the Appuser-Entity has no related Column for 'watches'. I can't user 'appuserReference_id' or 'appuserReference' to do the inner select.

I hope you understand me, thx!


Solution

  • Since your entities are related, you should use JOIN instead of multiple SELECTs:

    $repository = $this->getDoctrine()->getRepository('jwatchBundle:Appuser');
    
    $query = $repository->createQueryBuilder('u')
                        ->join('u.watches', 'w')
                        ->where('w.id IN :watched_ids')
                        ->setParameter('watched_ids', array(1, 3, 12))
                        ->getQuery();
    
    $result = $query->getResult();