Model Relationships in Django
Django provides robust support for defining relationships between models. The main types of relationships are One-to-One, One-to-Many, and Many-to-Many. This article explains these relationships with examples.
One-to-One Relationship
A One-to-One relationship is used when each record in one model is associated with exactly one record in another model. This is implemented using OneToOneField
.
from django.db import models
class UserProfile(models.Model):
user = models.OneToOneField('auth.User', on_delete=models.CASCADE)
bio = models.TextField()
profile_picture = models.ImageField(upload_to='profiles/')
def __str__(self):
return self.user.username
In this example, each UserProfile
is linked to a single User
. If a user is deleted, the associated profile is also deleted due to on_delete=models.CASCADE
.
Usage
# Create a user profile
from django.contrib.auth.models import User
from myapp.models import UserProfile
user = User.objects.create(username="johndoe")
profile = UserProfile.objects.create(user=user, bio="Hello world!")
print(profile.user.username) # Output: johndoe
One-to-Many Relationship
A One-to-Many relationship is used when one record in a model is associated with multiple records in another model. This is implemented using ForeignKey
.
class Author(models.Model):
name = models.CharField(max_length=100)
def __str__(self):
return self.name
class Book(models.Model):
title = models.CharField(max_length=100)
author = models.ForeignKey(Author, on_delete=models.CASCADE)
def __str__(self):
return self.title
In this example, an Author
can have multiple Book
records, but each book belongs to one author. Deleting an author will delete all their books due to on_delete=models.CASCADE
.
Usage
# Create an author and books
from myapp.models import Author, Book
author = Author.objects.create(name="J.K. Rowling")
book1 = Book.objects.create(title="Harry Potter and the Sorcerer's Stone", author=author)
book2 = Book.objects.create(title="Harry Potter and the Chamber of Secrets", author=author)
# Get all books by the author
books = author.book_set.all()
for book in books:
print(book.title)
Many-to-Many Relationship
A Many-to-Many relationship is used when multiple records in one model can be associated with multiple records in another model. This is implemented using ManyToManyField
.
class Student(models.Model):
name = models.CharField(max_length=100)
def __str__(self):
return self.name
class Course(models.Model):
title = models.CharField(max_length=100)
students = models.ManyToManyField(Student)
def __str__(self):
return self.title
In this example, a Student
can enroll in multiple Course
instances, and each course can have multiple students.
Usage
# Create students and courses
from myapp.models import Student, Course
student1 = Student.objects.create(name="Alice")
student2 = Student.objects.create(name="Bob")
course = Course.objects.create(title="Mathematics")
# Add students to the course
course.students.add(student1, student2)
# Get all students in a course
students = course.students.all()
for student in students:
print(student.name)
# Get all courses for a student
courses = student1.course_set.all()
for course in courses:
print(course.title)
Custom Through Model
For Many-to-Many relationships, you can define a custom intermediary model using the through
attribute:
class Enrollment(models.Model):
student = models.ForeignKey(Student, on_delete=models.CASCADE)
course = models.ForeignKey(Course, on_delete=models.CASCADE)
date_enrolled = models.DateField()
class Course(models.Model):
title = models.CharField(max_length=100)
students = models.ManyToManyField(Student, through='Enrollment')
Conclusion
Model relationships in Django provide a flexible and powerful way to design your database schema. Understanding these relationships is essential for building complex applications with Django's ORM.