2011-03-21 9 views
38

Necesito insertar una entidad que tenga asociaciones.Al insertar una entidad con asociaciones, ¿hay alguna manera de simplemente usar el FK en lugar de recuperar la entidad?

Si ya tengo los FK de las entidades asociadas, ¿hay alguna manera de insertar la entidad principal en el db con solo los FK rellenos?

O qué siempre tengo a

  • recuperar las entidades asociadas a través del FK,
  • pueblan las propiedades de la entidad primaria en referencia a las Asociaciones del,
  • y luego invoque el método persistir.
+2

Así que quieres ¿crear manualmente una relación especificando la ID de una entidad existente para relacionarla? ¿Podría agregar algún código de ejemplo de lo que está tratando de lograr? – Cobby

+0

hey Cobby, aprecia la respuesta. Tengo un formulario de creación de usuario, donde puede elegir de una lista de opciones de selección qué función asignar a un usuario (el usuario solo puede tener un rol en este caso). Entonces, cuando procese el envío del formulario, debería tener un nombre de usuario y un ID de función.Si quiero guardar al usuario, ¿necesito recuperar la entidad de rol asociada y configurarla dentro de mi objeto de usuario para guardar el objeto de usuario? ¿O puedo simplemente establecer el roleId dentro del objeto de usuario y guardarlo? – blacktie24

Respuesta

61

¿Quieres una reference proxy

Digamos que tengo mensajes y etiquetas. Un mensaje tiene muchas etiquetas. Recibo un montón de etiquetas del usuario que verificó varias casillas de verificación.

Lo siguiente agregaría etiquetas a una publicación existente, sin buscar primero cada entidad de etiqueta. Esto se logra mediante el uso de proxies de referencia, generadas por EntityManager::getReference():

$tag_ids = $_POST['tag_id']; // an array of integers representing tag IDs. 
$post = $em->getRepository('Post')->find($post_id); // returns a Post entity. 

foreach($tags_ids as $tid){ 
    $post->addTag($em->getReference('Tag',$tid)); 
} 
$em->persist($post); 
$em->flush(); 
+0

ahhh lo tengo, eso tiene mucho sentido, pero ¿qué sucede realmente en el back-end? Cuando la doctrina persiste, la publicación, con sus etiquetas recién agregadas, ¿acaso reemplaza los proxies con las entidades reales y luego agrega estas asociaciones a la tabla de unión? – blacktie24

+0

No estoy seguro de lo que Doctrine hace internamente, pero espero que sea eficiente, simplemente inserta y/o actualiza según sea necesario. Si crea un proxy de referencia con un ID que no existe, es probable que obtenga una excepción cuando intente vaciar() y la transacción se retrotraiga. Pero no confíe en mi palabra, pruébelo usted mismo. – timdev

+0

ya lo probaré. De nuevo por tu tiempo, Timdev, realmente lo aprecio. Aclamaciones. – blacktie24

0

Debe recuperar la entidad que se va a relacionar y establecer la relación.

Supongo que podría especificar manualmente la relación al acceder directamente a la base de datos a través de la capa DBAL, pero no lo recomendaría ni lo habría intentado.

+0

Cobby, sí, eso es lo que esperaba, pero ¿por qué no se recomienda esto, ya que técnicamente se guardará una consulta adicional? Gracias de nuevo por tomarse un tiempo para dar seguimiento a mi pregunta, realmente lo aprecio. – blacktie24

+1

Según su ejemplo, ya debería tener sus roles en caché (asegúrese de esto en la solicitud anterior cuando se carguen para la lista desplegable). Entonces no es realmente una consulta extra. Al hacerlo de esta manera, mantienes una capa de dominio más limpia a expensas de un golpe de rendimiento extremadamente pequeño. – Cobby

4

En lo que se refiere al uso de un proxy referencia
En mis investigaciones Esto es sólo parcialmente una solución, de la siguiente manera:

Sí , no tiene que recuperar proactivamente el registro relacionado (porque crea un registro de proxy), pero cuando vacía (confirma) la transacción de actualización, primero ejecuta una declaración de selección para recuperar el registro relacionado, y luego solo lo hace. actualización (todo en un golpe al db).
Esto es ineficiente y no debería ser necesario (tenemos el id-clave externa, ¿por qué recuperar el registro ..?)

Así que aunque no es una solución completa, lo que se hace es la ganancia de una única conexión a la base de datos (lo cual es bueno) y un código ligeramente simplificado.

No estoy seguro si hay una solución para esto en este momento ... ??
esperemos que la doctrina cyberwizard actualizará en el futuro y si se utiliza la lógica de proxy que deberíamos obtener una mejora automática el rendimiento ...

0

Usted puede hacer esto utilizando entityManager :: funden

$post = new Post(); 
$post->setPostCategory(['id' => 1]); 
$em->persist($em->merge($post)); 
$em->flush(); 
Cuestiones relacionadas