In this article I will show you how to implement a custom django-admin command for creating dummy data to test your django web app. It will provide an easy way for you to test your application quickly without having to manually create data in your database.
We are going to create a custom seed command which will accept an optional DjangoModelFactory class.
Now, having a django app employees with the model below:
from django.db import models
class Employee(models.Model):
first_name = models.CharField(max_length=255)
last_name = models.CharField(max_length=255)
middle_name = models.CharField(max_length=255, null=True)
email = models.EmailField(unique=True)
address = models.TextField(null=True)
def __str__(self):
return self.email
Next, we create a DjangoModelFactory Class for the Employee model. To be able to create factories in our django application install the site-package factory_boy.
pip install factory_boy
Once installed, inside the employees app folder create factories.py and create EmployeeFactory class.
import factory
from .models import Employee
class EmployeeFactory(factory.django.DjangoModelFactory):
first_name = factory.Faker('first_name')
last_name = factory.Faker('last_name')
middle_name = factory.Faker('first_name')
email = factory.Faker('email')
address = factory.Faker('address')
class Meta:
model = Employee
We created the EmployeeFactory class using the factory module that generates dummy data specified by the factory.Faker function. At this point, we can open a django shell and import the EmployeeFactory and generate the dummy data manually without any command.
python manage.py shell
>>> EmployeeFactory.create_batch(10)
To create the custom seed command, in your application's app directory create a management/commands directory and create a seed.py inside the commands/ subdirectory.
app/
|-- management/
|-- __init__.py
|-- commands/
|-- __init__.py
|-- seed.py
Inside of seed.py create a Command class that inherits from the BaseCommand class. Import your factories and then implement add_arguments
and handle methods.
from django.core.management.base import BaseCommand
from employees.factories import EmployeeFactory
class Command(BaseCommand):
def add_argumments(self, parser):
...
def handle(self, *args, **options):
...
The add_arguments method is for managing arguments passed along with the seed command. The handle method manage the core functionality of the command. We are going to add an optional argument that specifies the factory we want to use to seed the database and the number for records.
def add_arguments(self, parser):
parser.add_argument('--factory', help='The name of the factory you want to use')
parser.add_argument('--size', help="The number of object to create", type=int, default=10)
Now, we are going to use the options created above in the handle method to implement the seed function.
def handle(self, *args, **options):
if options['factory']:
factory = eval(options['factory'])
factory.create_batch(size=options['size'])
self.stdout.write(
self.style.SUCCESS('Database seeding done.')
)
Finllay we can seed our database using the custom command.
python manage.py seed --factory EmployeeFactory