Usar EntityManager dentro de las entidades de Doctrine 2.0

Tengo 2 entidades: País (id, nombre) y Mapeo (id, object, internalId, externalId). El país y el mapeo no están conectados con asociaciones (porque Mapeo tiene filas no solo para el país). Necesito obtener una identificación externa para el país usando las siguientes condiciones:

  • country.id = mapping.internalId
  • mapping.object = 'country'

Así que planeo agregar la función getExternalId () en Country

 function getExternalId() { $em = Registry::getEntityManager(); $mapping = $em->getRepository('Mapping')->findOneBy(array( 'object' => 'country', 'internalId' => $this->getId() )); return !empty($mapping) ? $mapping->getExternalId() : false; } 

Preguntas:

  1. ¿Es una buena práctica usar EntityManager dentro de las entidades? En caso negativo, explique cómo obtener una identificación externa en mi caso.
  2. ¿Quizás es posible asociar Country y Mapping usando archivos yaml?

¡Gracias por adelantado!

No es una buena idea permitir que un objeto de la entidad dependa del administrador de la entidad. Vincula a la entidad con la capa de persistencia, que era un problema que Doctrine 2 estaba tratando específicamente de resolver. La mayor molestia al confiar en el administrador de entidades es que hace que su modelo sea difícil de probar de forma aislada, lejos de la base de datos.

Probablemente deberías confiar en los objetos de servicio para manejar las operaciones que dependen del administrador de entidades.

 // CountryService public function getExternalId($country) {} 

Además, puede crear métodos de proxy en su modelo para llamar a un objeto de servicio que se establece externamente. Un objeto de servicio sería mucho más fácil de simular durante la prueba de lo que sería el administrador de la entidad.

 $country->setService($countryService); $country->getExternalId(); // Country public function getExternalId() { $this->_service->getExternalId($this); } 

Esta podría no ser la mejor idea, pero hay una forma simple de hacerlo.

La clase UnitOfWork in doctrine hidratará cualquier entidad que implemente ObjectManagerAware con el administrador de entidades y los metadatos de clase para esa entidad.

Todo lo que tiene que hacer para obtener el administrador de la entidad en su entidad es implementar la interfaz como se muestra en el siguiente ejemplo:

 use Doctrine\Common\Persistence\Mapping\ClassMetadata; use Doctrine\Common\Persistence\ObjectManager; use Doctrine\Common\Persistence\ObjectManagerAware; /** * @ORM\Entity */ class MyEntity implements ObjectManagerAware { public function injectObjectManager(ObjectManager $objectManager, ClassMetadata $classMetadata) { $this->em = $objectManager; } } 

Si crea una nueva entidad en lugar de consultarla desde la base de datos, deberá configurar el administrador de entidades manualmente, por ejemplo, con un método setter.

Creo que lo que necesitas usar son repositorys de entidades. Estos se detallan en la documentación, aunque es un poco difícil de encontrar información. Aquí hay un enlace al artículo Getting Started que documenta cómo se crearía un “repository” de funciones de ‘acceso’ para sus entidades.

Además, aquí hay un pseudocódigo para que comiences:

  

Una adición levemente innovadora a esto (PHP 5.4 está en alpha 2 en el momento de esta publicación) que puede ser de utilidad en el futuro:

Aquí hay algunos ejemplos del uso de rasgos de PHP 5.4 dentro de Doctrine2; uno de los cuales se llama entidad activa y proporciona funcionalidad de estilo de registro activo dentro de Doctrine 2, incluido el acceso al administrador de la entidad desde dentro de la entidad.