0
0
DjangoHow-ToBeginner · 4 min read

How to Chain Querysets in Django: Syntax and Examples

In Django, you can chain querysets using the union() method to combine querysets of the same model or compatible fields. Alternatively, use Python's itertools.chain() to concatenate querysets from different models, but note this returns an iterable, not a queryset.
📐

Syntax

There are two main ways to chain querysets in Django:

  • Using union(): Combines querysets of the same model or compatible fields into a single queryset.
  • Using itertools.chain(): Concatenates querysets from different models or incompatible fields into a single iterable.

union() returns a queryset, so you can continue filtering or ordering. itertools.chain() returns an iterable, so it does not support queryset methods.

python
qs1 = Model.objects.filter(condition1)
qs2 = Model.objects.filter(condition2)

# Using union
combined_qs = qs1.union(qs2)

# Using itertools.chain
from itertools import chain
combined_iterable = chain(qs1, qs2)
💻

Example

This example shows how to chain two querysets of the same model using union() and how to chain querysets of different models using itertools.chain().

python
from django.db import models
from itertools import chain

class Book(models.Model):
    title = models.CharField(max_length=100)

class Author(models.Model):
    name = models.CharField(max_length=100)

# Querysets of the same model
books1 = Book.objects.filter(title__startswith='A')
books2 = Book.objects.filter(title__startswith='B')
combined_books = books1.union(books2)

print('Books starting with A or B:')
for book in combined_books:
    print(book.title)

# Querysets of different models
authors = Author.objects.filter(name__startswith='A')
combined_iterable = chain(books1, authors)

print('\nCombined books and authors:')
for item in combined_iterable:
    if isinstance(item, Book):
        print(f'Book: {item.title}')
    else:
        print(f'Author: {item.name}')
Output
Books starting with A or B: A Tale of Two Cities Brave New World Combined books and authors: Book: A Tale of Two Cities Book: Another Book Author: Alice Author: Alan
⚠️

Common Pitfalls

1. Using union() with querysets of different models or incompatible fields causes errors.
Only querysets of the same model or with matching fields can be combined with union().

2. itertools.chain() returns an iterable, not a queryset. You cannot use queryset methods like filter() or order_by() on the result.

3. union() removes duplicates by default. Use all=True to include duplicates if needed.

python
# Wrong: union of different models
# qs1 = Book.objects.all()
# qs2 = Author.objects.all()
# combined = qs1.union(qs2)  # Raises error

# Right: use itertools.chain for different models
from itertools import chain
combined = chain(qs1, qs2)
📊

Quick Reference

MethodUse CaseReturnsNotes
union()Combine querysets of same model or compatible fieldsQuerySetRemoves duplicates by default; supports further queryset methods
itertools.chain()Combine querysets of different models or incompatible fieldsIterableDoes not support queryset methods; manual iteration only

Key Takeaways

Use union() to chain querysets of the same model or with matching fields for a combined queryset.
Use itertools.chain() to combine querysets from different models but remember it returns an iterable, not a queryset.
union() removes duplicates by default; pass all=True to keep duplicates.
You cannot chain querysets of different models using union() without errors.
Chained querysets with union() support further filtering and ordering.