Skip to main content

Latest Version Build Status Code Coverage Code Climate

Django Mock Queries

A library for mocking Django queryset functions in memory for testing

Features

  • QuerySet style support for method chaining
  • Filtering with Q objects
  • Aggregates generation
  • CRUD functions
  • Field lookups
  • django-rest-framework serializer asserts

Examples

from django.db.models import Avg, Q
from django_mock_queries.query import MockSet, MockModel

qs = MockSet(
    MockModel(mock_name='john', email='john@gmail.com'),
    MockModel(mock_name='jeff', email='jeff@hotmail.com'),
    MockModel(mock_name='bill', email='bill@gmail.com'),
)

print([x for x in qs.all().filter(email__icontains='gmail.com').select_related('address')])
# Outputs: [john, bill]

qs = MockSet(
    MockModel(mock_name='model s', msrp=70000),
    MockModel(mock_name='model x', msrp=80000),
    MockModel(mock_name='model 3', msrp=35000),
)

print(qs.all().aggregate(Avg('msrp')))
# Outputs: {'msrp__avg': 61666}

qs = MockSet(
    MockModel(mock_name='model x', make='tesla', country='usa'),
    MockModel(mock_name='s-class', make='mercedes', country='germany'),
    MockModel(mock_name='s90', make='volvo', country='sweden'),
)

print([x for x in qs.all().filter(Q(make__iexact='tesla') | Q(country__iexact='germany'))])
# Outputs: [model x, s-class]

qs = MockSet(cls=MockModel)
print(qs.create(mock_name='my_object', foo='1', bar='a'))
# Outputs: my_object

print([x for x in qs])
# Outputs: [my_object]

Test function that uses Django QuerySet:

from unittest import TestCase
from unittest.mock import patch
from django_mock_queries.query import MockSet, MockModel


class TestApi(TestCase):
    """
    Test function applies expected filters by patching Django's user model Manager or Queryset with a MockSet.
    """
    users = MockSet()
    user_objects = patch('django.contrib.auth.models.User.objects', users)
    
    def active_users(self):
        """
        Query active users.
        """
        return User.objects.filter(is_active=True).all()

    @user_objects
    def test_api_active_users_filters_by_is_active_true(self):
        self.users.add(
            MockModel(mock_name='active user', is_active=True),
            MockModel(mock_name='inactive user', is_active=False)
        )

        for user in self.active_users():
            self.assertTrue(user.is_active)

Test django-rest-framework model serializer:

class CarSerializer(serializers.ModelSerializer):
    """
    Car model serializer that includes a nested serializer and a method field.
    """
    make = ManufacturerSerializer()
    speed = serializers.SerializerMethodField()

    def get_speed(self, obj):
        return obj.format_speed()

    class Meta:
        model = Car
        fields = ('id', 'make', 'model', 'speed',)


def test_car_serializer_fields(self):
    """
    Test serializer returns fields with expected values and mock the result of nested serializer for field `make`.
    """
    car = Car(id=1, make=Manufacturer(id=1, name='vw'), model='golf', speed=300)

    values = {
        'id': car.id,
        'model': car.model,
        'speed': car.formatted_speed(),
    }

    assert_serializer(CarSerializer) \
        .instance(car) \
        .returns('id', 'make', 'model', 'speed') \
        .values(**values) \
        .mocks('make') \
        .run()

Full Example

There is a full Django application in the examples/users folder. It shows how to configure django_mock_queries in your tests and run them with or without setting up a Django database. Running the mock tests without a database can be much faster when your Django application has a lot of database migrations.

To run your Django tests without a database, add a new settings file, and call monkey_patch_test_db(). Use a wildcard import to get all the regular settings as well.

# settings_mocked.py
from django_mock_queries.mocks import monkey_patch_test_db

from users.settings import *

monkey_patch_test_db()

Then run your Django tests with the new settings file:

./manage.py test --settings=users.settings_mocked

Here's the pytest equivalent:

pytest --ds=users.settings_mocked

That will run your tests without setting up a test database. All of your tests that use Django mock queries should run fine, but what about the tests that really need a database?

ERROR: test_create (examples.users.analytics.tests.TestApi)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/.../examples/users/analytics/tests.py", line 28, in test_create
    start_count = User.objects.count()
  [...]
NotSupportedError: Mock database tried to execute SQL for User model.

If you want to run your tests without a database, you need to tell Django to skip the tests that need a database. You can do that by putting a skip decorator on the test classes or test methods that need a database.

@skipIfDBFeature('is_mocked')
class TestApi(TestCase):
    def test_create(self):
        start_count = User.objects.count()

        User.objects.create(username='bob')
        final_count = User.objects.count()

        self.assertEqual(start_count + 1, final_count)

Installation

pip install django_mock_queries

Contributing

Anything missing or not functioning correctly? PRs are always welcome! Otherwise, you can create an issue so someone else does it when time allows.

You can follow these guidelines:

  • Fork the repo from this page
  • Clone your fork:
git clone https://github.com/{your-username}/django-mock-queries.git
cd django-mock-queries
git checkout -b feature/your_cool_feature
  • Implement feature/fix
  • Add/modify relevant tests
  • Run tox to verify all tests and flake8 quality checks pass
tox
  • Commit and push local branch to your origin
git commit . -m "New cool feature does this"
git push -u origin HEAD
  • Create pull request

TODO

  • Add docs as a service like readthedocs with examples for every feature
  • Add support for missing QuerySet methods/Field lookups/Aggregation functions:
    • Methods that return new QuerySets: annotate, reverse, none, extra, raw
    • Methods that do not return QuerySets: bulk_create, in_bulk, as_manager
    • Field lookups: search
    • Aggregation functions: StdDev, Variance

Metadata

Release files for django-mock-queries 2.4.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for django-mock-queries 2.4.0
File Size Uploaded
django_mock_queries-2.4.0.tar.gz 34.5 kB Details

Built distribution (wheel)

Table of built distributions (wheels) for django-mock-queries 2.4.0
File Interpreter ABI Platform
django_mock_queries-2.4.0-py3-none-any.whl Python 3 none any Details

Total release size: 55.1 kB

Release files / django_mock_queries-2.4.0.tar.gz

Download URL django_mock_queries-2.4.0.tar.gz
Size 34.5 kB
Tags Source
SHA-256 checksum
How to use checksums
36004f052c23164e8c5fe4a3ec6948cabbb8eb427ed835bafccac973e1393dc5
BLAKE2b-256 checksum
How to use checksums
50941488ec0b698424f81d5832ce4b07734062f9c7b65be69d1a95a2fb3959ed
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 30, 2026.

Transparency log

Release files / django_mock_queries-2.4.0-py3-none-any.whl

Download URL django_mock_queries-2.4.0-py3-none-any.whl
Size 20.6 kB
Tags Python 3
SHA-256 checksum
How to use checksums
28987a1f337939ab24bca6b5e64d4baf076d9a820083f8701acb89725d5a75d6
BLAKE2b-256 checksum
How to use checksums
6721e605c2ace3c5412645538deb8b1653cf94badf0483b09f53fb4c62530440
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
Yes
Uploaded via twine/7.0.0 CPython/3.13.14

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

PyPI Publish Attestation

PyPI verified that this artifact, at this checksum, originated from the publisher listed below.

Signed by GitHub Actions, verified by PyPI on Sep 30, 2026.

Transparency log

Release history Release notifications | RSS feed

This release

2.4.0 This release

2 release files

2.3.0

2 release files

2.2.0

1 release file

2.1.8

1 release file

2.1.7

1 release file

2.1.6

1 release file

2.1.5

1 release file

2.1.4

1 release file

2.1.3

1 release file

2.1.2

1 release file

2.1.1

1 release file

2.1.0

1 release file

2.0.5

1 release file

2.0.1

2 release files

2.0.0

1 release file

1.0.7

1 release file

1.0.6

1 release file

1.0.5

1 release file

1.0.4

1 release file

1.0.3

1 release file

1.0.2

1 release file

1.0.1

1 release file

1.0.0

1 release file

0.0.16

1 release file

0.0.15

1 release file

0.0.14

1 release file

0.0.13

1 release file

0.0.12

1 release file

0.0.11

1 release file

0.0.10

1 release file

0.0.9

1 release file

0.0.8

1 release file

0.0.7

1 release file

0.0.6

1 release file

0.0.5

1 release file

0.0.4

0.0.3

1 release file

0.0.2

0.0.1

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page