This is the first migration recipe I publish for Django’s migration framework. I published it as part of my talk at DjangoCon Europe 2016 in Budapest. This recipe will show that migration code is just Python and Django’s built-in “makemigrations” command might not output the most efficient migration.
This recipe show how one can optimize a migration Django creates.
Take the following 2 models, a “Book” and a “Library”. Each book is associated with exactly one library:
from django.db import models
class Book(models.Model):
title = models.CharField(max_length=200)
library = models.ForeignKey('Library')
class Library(models.Model):
name = models.CharField(max_length=200)
When you run makemigrations for an app with these models you get 3 operations.
$ python manage.py makemigrations
Migrations for 'optimize_makemigrations':
0001_initial.py:
- Create model Book
- Create model Library
- Add field library to book
You may ask now why the ForeignKey is added as a separate operation. There are 2, maybe 3 reasons behind that:
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = []
operations = [
migrations.CreateModel(
name='Book',
fields=[
('id', models.AutoField(...)),
('title', models.CharField(max_length=200)),
],
),
migrations.CreateModel(
name='Library',
fields=[
('id', models.AutoField(...)),
('name', models.CharField(max_length=200)),
],
),
migrations.AddField(
model_name='book',
name='library',
field=models.ForeignKey(to='app.Library'),
),
]
Now, that we have this example, how can it be optimized? I guess some of you already have an idea:
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = []
operations = [
migrations.CreateModel(
name='Library',
fields=[
('id', models.AutoField(...)),
('name', models.CharField(max_length=200)),
],
),
migrations.CreateModel(
name='Book',
fields=[
('id', models.AutoField(...)),
('title', models.CharField(max_length=200)),
('library', models.ForeignKey(to='app.Library')),
],
),
]
The answer to that is, to re-order the CreateModel operations and merge the AddField into the CreateModel for the Book.