Sustitución del mapeo original de FOSUserBundle en symfony2

Para un nuevo proyecto en PHP que estamos empezando, hemos decidido utilizar la plataforma symfony2. En el pasado he tenido la suerte de trabajar, disfrutar y aprender con symfony 1.x, gracias a su coherente organización, buen uso del PHP y unos robustos cimientos fundados en una extensa documentación y una vasta comunidad de activos desarrolladores. En agosto del 2011, SensioLabs, la empresa liderada por Fabien Potencier, liberó la versión 2.0 y este septiembre pasado la 2.1 (la versión actual es la 2.1.2). Ya sólo respecto a la 2.0, la 2.1 incluye una serie de cambios importantes, como puede ser la gestión de la instalación y actualización de los bundles mediante composer. Ahora bien, el cambio de verdad, como es de suponer, se hizo al pasar de la serie 1.x a symfony2. Cierto es que siguen manteniendo la arquitectura MVC en su núcleo, pero la estructura de la aplicación cambia sustancialmente, así como la manera de auto-cargar las clases o los comandos de consola y otros puntos más que no vienen al caso ahora. La gran aportación de symfony2 es la nueva organización basada en paquetes (bundles). En symfony2, todo el código de la aplicación vive y ha de vivir dentro de un paquete (aproximadamente equivalente a lo que venía siendo un plugin en symfony1). De modo que ya no se instalan plugins, si no bundles. Y, en realidad, esto hace la vida más sencilla, sobre todo para el mantenimiento de la aplicación, gracias a que están mucho más desacoplados respecto del código que los antiguos plugins. Uno de los bundles estrella de symfony2 es FOSUserBundle, un paquete para gestionar usuarios, algo así como el sfGuardPlugin de symfony 1.x. Este bundle utiliza el ORM Doctrine y viene con un esquema y un mapeo de las clases, predefinidos en una serie de archivos. De ahí que nos podamos encontrar con un pequeño escollo al intentar cambiar alguna propiedad de las clases mapeadas o el nombre de un tabla, en caso de querer, por ejemplo, adaptar el mapeo a una base de datos heredada. Obviamente no podemos cambiarlo directamente en el bundle de FOSUserBundle, pues los cambios quedarían sobrescritos en la siguiente actualización del bundle. Además, ninguno de los proyectos de Doctrine permite actualmente sobrescribir parte de la asignación de una superclase mapeada en una entidad hijo. ¿Cómo proceder entonces si, por ejemplo, quiero quitar la clave única de una columna? La gente de FOSUserBundle no son muy locuaces al respecto, pero algo de información puedes encontrar en su página de github. Básicamente dicen que hay que volver a escribir el mapeo de la superclase mapeada, que la entidad ha de extender directamente a FOS\UserBundle\Model\User y aconsejan que se respeten todos los campos asignados en el bundle por lo que pueda pasar en futuras actualizaciones. Con la poca información proporcionada (tampoco he encontrado ningún ejemplo que pudiera guiarme), y después de pelearme un ratito, he llegado a la conclusión que básicamente estos son los ficheros que hay que tocar.
  1. /src/Application/MiSuperAPP/UserBundle/Entity/User.php
  2. /src/Application/MiSuperInvento/UserBundle/Entity/Group.php
  3. /src/Application/MiSuperInvento/UserBundle/Resources/config/doctrine/User.orm.xml
  4. /src/Application/MiSuperInvento/UserBundle/Resources/config/doctrine/Group.orm.xml
En el primer archivo hay que sustituir el alias del BaseUser en el use utilizado para importar la clase base de User por Luego hay que traerse todas las propiedades y métodos de la clase /vendor/sonata-project/user-bundle/Sonata/UserBundle/Model/User.php y añadirlas a la clase de la entidad User de nuestra aplicación.
Nótese que, en nuestro caso, hemos utilizado el FOSUserBundle integrado en el bundle de sonata. En caso de utilizar el bundle sin sonata, la ruta sería: /vendor/friendsofsymfony/user-bundle/FOS/UserBundle/Model/User.php
Después hacemos exactamente lo mismo con la entidad Group, teniendo en cuenta que donde pone user hay que poner group; por ejemplo en la entidad Group Los siguientes ficheros que tenemos que modificar son los XML donde se define la asignación del esquema de la base de datos respecto al modelo de clases:
  • /src/Application/MiSuperInvento/UserBundle/Resources/config/doctrine/User.orm.xml
  • /src/Application/MiSuperInvento/UserBundle/Resources/config/doctrine/Group.orm.xml
Estos archivos son fundamentales a la hora actualizar la base de datos a partir del modelo ( php app/console doctrine:schema:update --force), pues los campos que no estén definidos no se replicarán en la base de datos y viceversa. El fichero /src/Application/MiSuperInvento/UserBundle/Resources/config/doctrine/User.orm.xml es el que va a tener en cuenta la entidad de nuestra aplicación para las asignaciones del ORM: ¿Y dónde se encuentra el resto de propiedades de nuestro modelo? Un sitio interesante para ir a echar un vistazo es en /vendor/sonata-project/user-bundle/Sonata/UserBundle/Resources/config/doctrine/User.orm.xml
Recuerda que, en caso de no utilizar el bundle de sonata, la ruta sería: /vendor/friendsofsymfony/user-bundle/FOS/UserBundle/Resources/config/doctrine/User.orm.xml
En este fichero se define el mapeo de la superclase. Como en los primeros pasos, cambiamos las entidades /src/Application/MiSuperAPP/UserBundle/Entity/User.php y de /src/Application/MiSuperInvento/UserBundle/Entity/Group.php para que no herederan de la superclase, ahora sólo tenemos que añadir las propiedades que nos faltan de /vendor/sonata-project/user-bundle/Sonata/UserBundle/Resources/config/doctrine/User.orm.xml. Con lo que nuestro fichero User.orm.xml quedaría así: Seguimos los mismos pasos con Group.orm.xml y ya estamos listos para poder modificar nuestro esquema y modelo sin perjuicio de futuras actulizaciones. Por ejemplo, en este caso he quitado la clave única de emailCanonical y usernameCanonical. De modo que, después de ejecutar php app/console doctrine:schema:update --force, los cambios se ven reflejados en la base de datos. Por último recordar que, a partir de ahora, los cambios en el esquema han de ser modificados en el User.orm.xml de la aplicación y los del modelo en el User.php de la entidad de la aplicación.

Publicaciones Similares

  • Modelos locales

    Llevaba tiempo queriendo correr uno de esos modelos generativos en mi propia máquina. Libre de otras prioridades, hoy por fin he tenido ocasión de comprobar si era verdad que modelos de la familia GPT4All o LlamaCpp estaban preparados para ser consumidos en ordenadores personales. De los centenares de proyectos que han proliferado desde el advenimiento…

  • |

    Cómo ampliar el espacio en disco en 1and1

    Escenario Hemos contratado un servidor dedicado en 1and1 (ubuntu 14.04) y al acceder por ssh constatamos que no disponemos de todo el espacio en disco disponible: $ df -hFilesystem Size Used Avail Use% Mounted onudev 3.9G 4.0K 3.9G 1% /devtmpfs 798M 592K 797M 1% /run/dev/md1 4.0G 990M 3.0G 25% /none 4.0K 0 4.0K 0% /sys/fs/cgroupnone 5.0M 0 5.0M 0% /run/locknone 3.9G 0 3.9G 0% /run/shmnone 100M 0 100M 0% /run/user/dev/mapper/vg00-usr 4.8G 1.3G 3.3G 28% /usr/dev/mapper/vg00-var 4.8G 812M 3.8G 18% /var/dev/mapper/vg00-home 4.8G 10M 4.6G 1% /home Objetivo Aumentar el espacio disponible para dar cabida a nuestros recursos. Solución Nota: sólo aplicable a sistemas linux Primer paso Comprobamos el espacio en disco real: ~$ sudo fdisk -lDisk /dev/sda: 240.1 GB, 240057409536 bytes255 heads, 63 sectors/track, 29185 cylinders, total 468862128 sectorsUnits = sectors of 1 * 512 = 512 bytesSector size (logical/physical): 512 bytes / 4096 bytesI/O size (minimum/optimal): 4096 bytes / 4096 bytesDisk identifier: 0x24e3fc12   Device Boot      Start         End      Blocks   Id  System/dev/sda1            2048     8390655     4194304   fd  Linux raid autodetect/dev/sda2         8390656    12584959     2097152   82  Linux swap / Solaris/dev/sda3        12584960   468862127   228138584   fd  Linux raid autodetect Segundo…

  • |

    Traducción de variables en javascript

    Escenario Estoy trabajando en una aplicación multi-lenguaje desarrollada con la plataforma spring boot. Para quien no conozca esta plataforma de desarrollo, spring boot te permite gestionar varios lenguajes gracias a un sistema que utiliza ficheros de tipo propiedades para almacenar las traducciones. Los nombres de estos ficheros han de respetar la siguiente convención, messages_{código ISO…

  • |

    Actualización de Apache Guacamole server 1.0 → 1.2

    Escenario En el trabajo usamos Apache Guacamole para conectarnos a nuestros escritorios de la oficina desde casa. Apache Guacamole proporciona una puerta de entrada HTML5 para conectar con servicios de acceso remoto, como pueden ser VNC o RDP. Consta de dos : el servidor y el cliente que no tienen por qué correr en la…

  • phpsize

    phpize: command not found Si alguna vez te topas con este error intentando instalar un paquete PEAR en un sistema linux, muy probablemente sea por que no tienes installado el paquete php-devel.

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *