Doctrine2 + Symfony2: How to bring more than one entity into queryBuilder

Asked

Viewed 153 times

0

Hello.

I have the following doubt.

I’m doing a select on several different tables, I want to bring some of them. But any way I try, it either returns only the main or a mistake.

Can you help me?

 $em = $this->getDoctrine()->getManager();
    $qb = $em->createQueryBuilder()
        ->select( ['c as customer','b as bankAccount']  )
        ->from('MyBundle:BankAccount', 'b')
        ->join('b.customer', 'c')
        ->join('c.prepaidCards', 'p')
        ->leftJoin('c.addresses', 'a', Join::WITH, 'a.type = :address_type')
        ->leftJoin('a.city', 'ci')
        ->leftJoin('a.state', 's')
        ->leftJoin('c.company', 'co')
        ->where('b.accountType = :account_type')
        ->andWhere('b.isActive = 1')
        ->andWhere('p.status = :card_status')
        ->andWhere('p.shippingType ' . (is_null($shippingType) ? 'IS NULL' : '= :shipping_type'))
        ->andWhere('c.status IN (:customer_status)')
        ->setParameter('account_type', BankAccount::ACCOUNT_TYPE_CARD)
        ->setParameter('card_status', PrepaidCard::CARD_STATUS_ASSIGNED)
        ->setParameter('address_type', Address::TYPE_SHIPPING);
    if (!is_null($shippingType)) {
        $qb->setParameter('shipping_type', $shippingType);
    }
    $result = $qb->setParameter('customer_status', [Customer::STATUS_ACCEPTED, Customer::STATUS_ACTIVATED])
        ->getQuery()->getResult();

I tried the line:

->select( ['c as customer','b as bankAccount']  )

Like:

->select( 'c as customer, b as bankAccount'  )

->select( ['c','b']  )

->select( 'c','b'  )

And some others I don’t remember at the time.

I need to bring 'c', 'b', 'p', 'a', 'ci', ’s'

1 answer

1


Just do it like this:

$em = $this->getDoctrine()->getManager();
$qb = $em->createQueryBuilder()
    ->select('b, c, p, a, ci, s')
    ->from('MyBundle:BankAccount', 'b')
    ->join('b.customer', 'c')
    ->join('c.prepaidCards', 'p')
    ->leftJoin('c.addresses', 'a', Join::WITH, 'a.type = :address_type')
    ->leftJoin('a.city', 'ci')
    ->leftJoin('a.state', 's')
    ->leftJoin('c.company', 'co')
    ->where('b.accountType = :account_type')
    ->andWhere('b.isActive = 1')
    ->andWhere('p.status = :card_status')
    ->andWhere('p.shippingType ' . (is_null($shippingType) ? 'IS NULL' : '= :shipping_type'))
    ->andWhere('c.status IN (:customer_status)')
    ->setParameter('account_type', BankAccount::ACCOUNT_TYPE_CARD)
    ->setParameter('card_status', PrepaidCard::CARD_STATUS_ASSIGNED)
    ->setParameter('address_type', Address::TYPE_SHIPPING);
if (!is_null($shippingType)) {
    $qb->setParameter('shipping_type', $shippingType);
}
$result = $qb
    ->setParameter('customer_status', [Customer::STATUS_ACCEPTED, Customer::STATUS_ACTIVATED])
    ->getQuery()
    ->getResult();
  • Only returns the Bankaccount: array (size=1) 0 => Object(Mybundle Entity Bankaccount)[5575]

  • 1

    It is from this object that you will access the other objects. DQL returns only the main object (from the clause FROM). The feature of separating objects by comma exists for Doctrine to bring all related objects at once, and not bring them one by one when you iterate for a certain attribute of the main object.

  • Okay, if I wanted to bring prepaidCards I would have to access $bank->getCustomer()->getPrepaidCards(); it would return all of the client. I would have to take the card id and then bring via getRepository? Have some easier way?

  • 1

    It is not necessary to use the card repository to bring them one by one if they already come in the main query. If you are giving a join in prepaidCards, this will translate into a INNER JOIN when the query effectively runs in the bank. That is, the cards will already be brought together with the main resultset. You can do the following to read the appointment cards: foreach ($bankAccount->getCustomer()->getPrepaidCards() as $prepaidCard()) { echo $prepaidCard->getId(); }.

  • Okay, thank you very much. I think I was doing something wrong before, because now it worked. I was returning all the addresses from Jupiter, now it’s bringing only the right one.

Browser other questions tagged

You are not signed in. Login or sign up in order to post.