Test data with factory_boy and query-count assertions

Backend Live Coding November 13, 2026 python

With factory_boy each test declares only what it cares about, and the rest have sensible defaults.

python
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
# ======================================================================
# Q: How do you create test data without huge fixture files?
#
# With factory_boy each test declares only what it cares about, and the rest
# have sensible defaults. django_assert_num_queries pins the number of queries
# so I catch N+1 regressions in CI.
# ======================================================================

import factory
from factory.django import DjangoModelFactory

class CustomerFactory(DjangoModelFactory):
    class Meta:
        model = Customer
    name = factory.Faker('company', locale='el_GR')
    vat_number = factory.Sequence(lambda n: f'EL{n:09d}')
    kind = 'b2b'

class OrderFactory(DjangoModelFactory):
    class Meta:
        model = Order
    customer = factory.SubFactory(CustomerFactory)
    status = 'placed'

    class Params:
        paid = factory.Trait(status='paid')

def test_report_counts_only_paid(django_assert_num_queries):
    OrderFactory.create_batch(3, paid=True)
    OrderFactory()                                   # placed
    with django_assert_num_queries(1):
        assert revenue_report()['orders'] == 3