Monthly Archives: May 2012

Those who use south to manage their migrations perhaps have wondered that would be nice to test them without having to mess with their local test database and usually every time you run a datamigration you want to make sure everything went fine and the data integrity was not compromised, that assumes special importance when for instance your migration is dealing with important records where the consequences of something to go wrong can be catastrophic.

Unfortunately south doesn’t provide any way to test its migrations and when you have to write a migration most of the times you find yourself testing it in your local machine against your own development data and if something fails you will have to replace your previous data and setting your testing environment so you can test it again. If you ever experienced this you know that this repetitive process can become quite a big pain.
Django however have a very good testing framework which becomes even better with django-nose, and not taking advantage of it when testing migrations sounds a bit like a waste of resources.

This was sort of the problem I came across this week and I did a bit of research and found a way to unittest datamigrations in a django testcase.

So imagine you have this migration:

# file: myapp/migrations/ 
import datetime                   
from south.db import db           
from south.v2 import DataMigration 
from django.db import models     
class Migration(DataMigration):   
    def forwards(self, orm):                       
        "Write your forwards methods here."       
        # access your orm here 
        Model1 = orm.Model1

The test would look like:

# file: myapp/ 
from django.test import TestCase 
from south.migration import Migrations 
from myapp.models import Model1 

class TestOrm(self): 
    This class will be used to mock the orm object which goes as a 
    param to forwards() method 
    def __init__(self): 
        setattr(self, 'Model1', Model1) 

class MyMigrationTest(TestCase): 

    def _pick_migration(self, app_label, migration_name):               
        This method will pick a migration object                         
        migrations = Migrations(app_label)                     
        for migration in migrations:                                     
            if migration.full_name().split('.')[-1] == migration_name:   
                return migration                                                            
        return None 

     def test_migration_0002_some_migration(self): 
         self.migration = self._pick_migration('myapp', '0002_some_migration')
         if not self.migration:                         
        # running migrations             
        orm  = TestOrm()                                 
        # assertations here 
        # self.assertEquals(......) 

And that’s it.
This of course only covers datamigrations, not schema migrations but I hope this can still be useful.

I don’t know if it is appropriate to create a way to test south migrations in django but if it is I think would be an interesting feature.


%d bloggers like this: