tarda rapidas optimizar mucho mas inner hacer consultas consulta como php doctrine symfony doctrine-orm

php - rapidas - doctrine2 carga asociaciones de uno a muchos con el modo de búsqueda y con muchas consultas SQL



optimizar consultas sql server 2014 (3)

Estoy cargando una lista de muchas entidades.
Estas entidades tienen una asociación de uno a muchos con otras entidades.
Quiero cargar todas estas otras entidades en una sola consulta SQL (en lugar de una consulta para cada entidad en la primera lista).

Como se describe en la documentación de doctrine2: http://www.doctrine-project.org/docs/orm/2.1/en/reference/dql-doctrine-query-language.html#temporarily-change-fetch-mode-in-dql Esto debería ser posible con la carga de "EAGER".

pero no funciona como se describe.

mi código:

class User{ /** * @ORM/OneToMany(targetEntity="Address", mappedBy="user", indexBy="id", fetch="EAGER") */ protected $addresses; public function __construct(){ $this->addresses = new ArrayCollection(); } } class Address{ /** * @ORM/ManyToOne(targetEntity="User", inversedBy="addresses") * @ORM/JoinColumns({ * @ORM/JoinColumn(name="UserId", referencedColumnName="id") * }) */ private $user; } class UserRepository{ public function findUsersWithAddresses(){ return $this->getEntityManager() ->createQuery(''SELECT u FROM MyBundle:User u ORDER BY u.name ASC'') ->setFetchMode(''MyBundle/Entity/User'', ''addresses'', /Doctrine/ORM/Mapping/ClassMetadata::FETCH_EAGER) ->setMaxResults(10) ->getResult(); } }

El método UserRepository :: findUsersWithAddresses () ejecuta 11 consultas SQL.

¿Cómo puedo decirle a Doctrine que use solo una consulta SQL para cargar las entidades de dirección?

Estoy usando:

  • Symfony v2.0.9
  • doctrina común 2.1.4
  • doctrina-dbal 2.1.5
  • doctrina 2.1.5

La versión actual de la doctrina no apoya esto.

Hay una solicitud de características sobre esto en el rastreador de problemas de doctrine2.

Así que espero que sea implementado pronto.


Tuve exactamente los mismos problemas y actualicé mi módulo de doctrina en Zend Framework 2 a la versión 2.5 y ahora todo funciona bien. Puedes consultar mi pregunta here


Según su enlace:

Puede marcar una asociación de muchos a uno o uno a uno como recuperada temporalmente para obtener por lotes estas entidades usando una consulta WHERE .. IN

Parece que la versión actual de Doctrine no admite la carga impaciente en una colección de uno a muchos , desafortunadamente.

Esta página parece confirmar esta suposición:

@Uno a muchos

Atributos requeridos:

targetEntity : FQCN de la entidad objetivo a la que se hace referencia. Puede ser el nombre de clase no calificado si ambas clases están en el mismo espacio de nombres. IMPORTANTE: ¡No hay barra invertida!

Atributos opcionales:

  • Cascada : Opción Cascada
  • orphanRemoval : Boolean que especifica si las huérfanas, las entidades OneToOne inversas que no están conectadas a ninguna instancia propietaria, deben ser eliminadas por Doctrine. El valor predeterminado es falso.
  • mappedBy : esta opción especifica el nombre de la propiedad en targetEntity que es el lado propietario de esta relación. Es un atributo requerido para el lado inverso de una relación.

La anotación @OneToMany no presenta un atributo de fetch , a diferencia de @OneToOne y @ManyToOne .

Actualizar

Acabo de darme cuenta de que en realidad puedes obtener las entidades relacionadas con entusiasmo, utilizando un LEFT JOIN explícito en DQL:

SELECT u, a FROM User u LEFT JOIN u.addresses a

Utilice un LEFT JOIN , y no un JOIN interno, o las entidades con una colección vacía ( User sin ninguna Address ) se omitirán del conjunto de resultados.

Actualización (2017)

Como señalaron GusDeCool y webDEVILopers en los comentarios, el atributo fetch ahora se admite en @OneToMany . La respuesta anterior es ahora obsoleta.