sábado 28 de febrero de 2009

Actualización de modelos con Django Evolution.

Últimamente, es estado jugando bastante con Django, la y la verdad es fantástico.

Lo único que le encuentro un poco engorroso es el hecho de que una vez creado un modelo de datos, django no permite la modificación del mismo. Busqué sin cesar opciones para probar hasta que desistí y dije, ok, con cada modificación que haga, tendré que actualizar las tablas en bd a mano, o resignarme a perder mis datos de prueba (con un sqlreset).

Hasta que hace un rato, sin querer me encontré con una opcion: Django Evolution. Este corresponde con un proyecto independiente a Django (o por lo menos eso creo), se instala como un paquete python más, y luego puede usarse desde el aplicativo manage.py para sincronizar nuestras tablas.

Descarga e instalación:

$ svn co http://django-evolution.googlecode.com/svn/trunk/ django-evolution
$ cd django-evolution && sudo python setup.py install


luego para poder utilizarlo en nuestro proyecto solo basta con agregar django_evolution a nuestro INSTALLED_APPS:

$cd /path/a/nuestro/proyecto/django

editar settings.py y agregar la linea 'django_evolution' a nuestras aplicaciones:

INSTALLED_APPS = (
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.sites',
    'django.contrib.admin',
    'django_evolution',
    'miweb.miaplicacion'
)


y ya está listo para usarse, para hacerlo en primer lugar hay que hacer un syncdb normal, de esta forma, django_evolution generá unas tablas extra en nuestra base de datos, en estas tablas guardará toda la meta información de nuestro proyecto:


jaa@dino-thunder_ng ~/taller/miweb $ python manage.py syncdb
Creating table django_project_version
Creating table django_evolution
Installing baseline version
Installing index for django_evolution.Evolution model


y después de esto podemos ir modificando modelos al vuelo, y luego para actualizar las tablas haremos:


jaa@dino-thunder_ng ~/taller/miweb $ python manage.py evolve --hint --execute

You have requested a database evolution. This will alter tables
and data currently in the 'django_miweb' database, and may result in
IRREVERSABLE DATA LOSS. Evolutions should be *thoroughly* reviewed
prior to execution.

Are you sure you want to execute the evolutions?

Type 'yes' to continue, or 'no' to cancel: yes
Evolution successful.


y luego con cada cambio podemos repetir nuestro último comando, dejando atrás syncdb.

Agrego un ejemplo, supongamos que generé mi proyecto, y tengo el archivo models.py con el siguiente contenido:

class DireccionFields (models.Model):
    """ Objeto que simplemente guarda la direccion de una entidad/persona/..."""
    calle = models.CharField (max_length=100, blank=True)
    altura= models.IntegerField (blank=True, null=True)


Entonces hago:

jaa@dino-thunder_ng ~/nueva_web $ python manage.py syncdb
Creating table auth_permission
Creating table auth_group
Creating table auth_user
Creating table auth_message
Creating table django_content_type
Creating table django_session
Creating table django_site
Creating table django_admin_log
Creating table django_project_version
Creating table django_evolution
Creating table prueba_direccionfields

You just installed Django's auth system, which means you don't have any superusers defined.
Would you like to create one now? (yes/no): yes
Username (Leave blank to use 'jaa'): JAA
E-mail address: barakawins@gmail.com
Password:
Password (again):
Superuser created successfully.
Installing baseline version
Installing index for auth.Permission model
Installing index for auth.Message model
Installing index for admin.LogEntry model
Installing index for django_evolution.Evolution model

Installing index for django_evolution.Evolution model


Luego, cambio el modelo anterior:

class DireccionFields (models.Model):
    """ Objeto que simplemente guarda la direccion de una entidad/persona/..."""
    calle = models.CharField (max_length=100, blank=True)
    altura= models.IntegerField (blank=True, null=True)
    depto   = models.CharField (max_length=25, blank=True)

Invoco la actualizacion de la tabla:


jaa@dino-thunder_ng ~/nueva_web $ python manage.py evolve --hint --execute

You have requested a database evolution. This will alter tables
and data currently in the 'django_miweb_p' database, and may result in
IRREVERSABLE DATA LOSS. Evolutions should be *thoroughly* reviewed
prior to execution.

Are you sure you want to execute the evolutions?

Type 'yes' to continue, or 'no' to cancel: yes
Evolution successful.


jaa@dino-thunder_ng ~/nueva_web $ mysql mi_base
mysql> describe prueba_direccionfields;
+--------+--------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+--------+--------------+------+-----+---------+----------------+
| id | int(11) | NO | PRI | NULL | auto_increment |
| calle | varchar(100) | NO | | NULL | |
| altura | int(11) | YES | | NULL | |
| depto | varchar(25) | NO | | NULL | |
+--------+--------------+------+-----+---------+----------------+
4 rows in set (0.00 sec)

y apareció nuestro nuevo campo!.

Otra cosa importante, es que django-evolution puede agregarse a cualquier proyecto existente previamente, pero siempre hay que recordar ejecutar el syncdb la primera vez.

Etiquetas: , , , , , , , ,

0 comentarios:

Publicar un comentario en la entrada

Suscribirse a Enviar comentarios [Atom]

<< Página principal