symfony2 delete consultas doctrine2 dql

doctrine2 - delete - Obtener Doctrine DQL da como resultado el modo SQL



find by id doctrine (2)

Al realizar una consulta DQL como, por ejemplo:

SELECT u AS user, t AS transaction FROM Model/User u JOIN Model/Transaction t WITH t.user = u

Obtiene filas de resultados alternas, como:

  • [''user'' => Model/User(1)]
  • [''transaction'' => Model/Transaction(1)]
  • [''transaction'' => Model/Transaction(2)]
  • [''user'' => Model/User(2)]
  • [''transaction'' => Model/Transaction(3)]
  • [''transaction'' => Model/Transaction(4)]
  • [''transaction'' => Model/Transaction(5)]

¿Es posible obtener el resultado de la manera SQL, como:

  • [''user'' => Model/User(1), ''transaction'' => Model/Transaction(1)]
  • [''user'' => Model/User(1), ''transaction'' => Model/Transaction(2)]
  • [''user'' => Model/User(2), ''transaction'' => Model/Transaction(3)]
  • [''user'' => Model/User(2), ''transaction'' => Model/Transaction(4)]
  • [''user'' => Model/User(2), ''transaction'' => Model/Transaction(5)]

Sería mucho más fácil tratar que alternar objetos.


Desafortunadamente, no existe una manera fácil y actual de lograr esto. Sin embargo, hay una forma de que puedas obtener ese resultado.

Cree una clase llamada UserTransactionDTO y acepte 2 argumentos de constructor: User y Transaction.

Ahora reescribe tu consulta DQL así:

SELECT NEW UserTransactionDTO(user, transaction) FROM Model/User u JOIN Model/Transaction t WITH t.user = u

Esto debería darle un resultado que coincida con su comportamiento deseado (una lista de objetos UserTransactionDTO), lo que le permite acceder tanto al Usuario como a la Transacción en un solo registro.


La forma en que lo hago ahora es:

$query = $em->createQuery('' SELECT u, t FROM Model/User u JOIN Model/Transaction t WITH t.user = u ''); $rows = $query->getResult(); $rowCount = count($rows); $result = []; for ($i = 0; $i < $rowCount; $i += 2) { /** @var Model/User $user */ $user = $rows[$i]; /** @var Model/Transaction $transaction */ $transaction = $rows[$i + 1]; $result[] = new UserTransactionDTO($user, $transaction); } return $result;

Que es lo suficientemente limpio

Tenga en cuenta que este ejemplo es malo, ya que solo puede devolver Transacciones y obtener el Usuario desde allí; pero encuentro regularmente casos de uso donde un solo objeto no contiene toda la información.