Welcome to the next stage of your journey! In the previous modules, you've built a strong foundation in Python, mastered the core concepts of Django, and even secured your application with user authentication and authorization. You now have all the individual components you need.
Today, we begin Module 7: Building the Task Manager Project. This is where we start assembling those components into the portfolio project you set out to create.
Our first step is the most crucial one: designing and implementing the Django models for the task management application. A model is the blueprint for your database; it defines the structure of your data. Getting this right is the foundation upon which your entire application will be built.
Let's start building!
Step 1: Planning Your Data Model
Before writing any code, it's essential to think about the data we need to store. For a task management application, what information defines a single task?
At a minimum, each task will need:
- A Title: A short, descriptive name for the task (e.g., "Finish project proposal").
- A Description: A longer, optional field for more details.
- A Completion Status: A simple way to mark a task as done or not done.
- A Creation Date: To know when the task was created.
- An Associated User: This is critical. Building on our last lessons, every task must belong to a specific user.
This plan translates directly into a Django model.
Step 2: Writing the Task Model in models.py
Now, let's turn our plan into code. We will define a Python class in your app's models.py file that inherits from django.db.models.Model. Each attribute of this class will represent a field in our database table.
Open the models.py file inside your Django app (you might have named it tasks or similar in previous lessons) and define the Task model like this:
from django.db import models
from django.contrib.auth.models import User # We need to import the User model
# Create your models here.
class Task(models.Model):
user = models.ForeignKey(
User, on_delete=models.CASCADE, null=True, blank=True)
title = models.CharField(max_length=200)
description = models.TextField(null=True, blank=True)
completed = models.BooleanField(default=False)
created = models.DateTimeField(auto_now_add=True)
def __str__(self):
return self.title
class Meta:
ordering = ['completed']
Let's break this down:
user = models.ForeignKey(...): This is the most important field for our multi-user app. It creates a relationship between ourTaskmodel and Django's built-inUsermodel.on_delete=models.CASCADE: This tells Django that if a user is deleted, all of their tasks should be deleted as well. This maintains database integrity.null=True, blank=True: This makes the user field optional for now. It's helpful during development but we'll enforce it later.
title = models.CharField(...): A field for short strings.max_lengthis required.description = models.TextField(...): A field for long-form text. We've made it optional withnull=True, blank=True.completed = models.BooleanField(default=False): A true/false field. By default, new tasks will be marked as not completed.created = models.DateTimeField(auto_now_add=True): A date and time field that automatically records the timestamp when a task is first created.def __str__(self):: This special method provides a human-readable name for each task object, which is very useful in the Django admin site. Instead of seeing "Task object (1)", you'll see "Finish project proposal".class Meta:: This inner class lets you configure metadata for your model.ordering = ['completed']tells Django to sort tasks by their completion status by default.
The ForeignKey establishes a One-To-Many relationship: one user can have many tasks, but each task belongs to only one user.

For a deeper dive into the different field types and their options, the Real Python guide is an excellent resource.
Manage Your To-Do Lists Using Python and Django
The article 'Manage Your To-Do Lists Using Python and Django' provides a great explanation of defining models. While its example uses two related models, the breakdown of field types like CharField, TextField, and ForeignKey is universally helpful.
Read the section 'Define Your Data Models'. Pay close attention to the descriptions of each field type (CharField, TextField, DateTimeField, ForeignKey) and their parameters. This will solidify your understanding of the code we just wrote.
Step 3: Applying Your Model to the Database with Migrations
You've written the Python code for your model, but your database doesn't know about it yet. We need to create and apply a migration. This is a two-step process:
makemigrations: Django inspects yourmodels.pyfile, detects changes, and generates a special file in themigrations/directory. This file is a Python script that describes the changes needed for your database schema.migrate: Django takes the pending migration files and executes the necessary SQL commands to apply those changes to your actual database, creating or altering tables as needed.
The following video provides a clear, step-by-step walkthrough of this entire process, from writing the model to migrating it and registering it in the admin.
To-do list with Django | Build a task application | Django projects | #3
The video 'To-do list with Django' by Cloud With Django demonstrates exactly what we need to do. It covers defining a simple Task model, running migrations, and registering it in the admin.
Watch the section from 00:22:54 to 00:31:59. Follow along with the instructor to: Define the Task model in your models.py file. Run python manage.py makemigrations in your terminal. Run python manage.py migrate to apply the changes to the database.
After running these commands, you have successfully created the Task table in your database!
Step 4: Registering and Testing in the Admin Panel
How can you interact with your new model without building any forms or views yet? The Django admin site is the perfect tool for this. By "registering" your model, you make it available in the admin interface, where you can easily create, view, update, and delete records.
Continue with the same video segment you were watching, as it also covers this final step. In your app's admin.py file, add the following code:
from django.contrib import admin
from .models import Task # Import your Task model
# Register your models here.
admin.site.register(Task)
Now, run your development server (python manage.py runserver), log in to the admin panel (/admin/) with your superuser account, and you should see a new "Tasks" section. Go ahead and create a few sample tasks to populate your database. This is an excellent way to confirm that your model works as expected.
Test your understanding!
You've successfully created the Task model. Now, imagine your project manager wants to add a priority level to each task (e.g., Low, Medium, High).
How would you modify the Task model to include a priority field? You should define a set of choices and use an appropriate field type.
Show answer
You would use an IntegerField or CharField with a choices option. Here's a common way to do it using an IntegerField:
class Task(models.Model):
# ... existing fields ...
# Define choices for priority
LOW = 1
MEDIUM = 2
HIGH = 3
PRIORITY_CHOICES = [
(LOW, 'Low'),
(MEDIUM, 'Medium'),
(HIGH, 'High'),
]
priority = models.IntegerField(
choices=PRIORITY_CHOICES,
default=MEDIUM
)
# ... __str__ and Meta class ...
After adding this, you would need to run makemigrations and migrate again to update your database table. The Django admin would automatically render this field as a dropdown menu.
Conclusion
Excellent work! You have just completed the most fundamental step in building your application. You designed a data model that captures the essential information for a task, translated that design into a Django model class, and used migrations to create the corresponding table in your database. Finally, you used the admin panel to interact with your new model and add some sample data.
Key Takeaways:
- Model-First Design: A web application's structure is defined by its data models. Planning your models is the first step.
- Django Models: Django models are Python classes that inherit from
models.Model, with class attributes representing database fields. - Field Types: Django provides a rich set of field types (
CharField,ForeignKey,BooleanField, etc.) to represent different kinds of data. - Migrations: The
makemigrationsandmigratecommands are the bridge between your Python model code and your database schema. - Admin Panel: The admin is an invaluable tool for testing models and managing data during development.
Preview of the Next Lesson:
Now that you have a database table for tasks, the next logical step is to allow users to add tasks through the main website, not just the admin panel. In the next lesson, you will build the 'Create' functionality for tasks using Django's CreateView.