Skip to main content

django-ninja-aio-crud

CRUD framework for Django Ninja, sync or async
Serializer-first schemas · Relations · Filtering · Pagination · Auth · Permissions

Tests Quality Gate Status codecov PyPI - Version PyPI - License Ruff Performance

Documentation · PyPI · Framework Comparison · Performance Benchmarks · Example Project · Issues


django-ninja-aio-crud builds complete REST APIs on top of Django Ninja. You say which fields each operation reads and writes, register a viewset, and get create, list, retrieve, update and delete endpoints with validation, pagination and interactive docs. The same serializer is also a CRUD API you can call from Python, in sync or async code.

Features

Feature Description
⚡ Sync and async Every viewset runs async by default, or sync with execution_mode = "sync"
🐍 Python CRUD API create, get, update, destroy, model_dump and their async versions on every serializer
📐 Schemas Declare create, update, read and detail with class Schemas and SchemaConfig
🔗 Relations Nested reads, relations as ids, and nested writes for child objects
📦 Bulk operations Bulk create, update and delete with per-item results
🔍 Filtering Filter, search, ordering and pagination mixins
🛡️ Permissions Viewset and object-level permission checks, including role-based access
🗑️ Soft delete Mark rows as deleted instead of removing them
🔑 Authentication JWT bearer and cookie auth, with per-method settings
🪝 Hooks Reactive @on_create, @on_update and @on_delete hooks on your models
🧰 Django admin Register a ModelSerializer in the admin with @register_admin
🤖 MCP server Expose your viewsets as MCP tools
🔒 Type safety Generic Serializer and APIViewSet classes for IDE autocomplete

Install

pip install django-ninja-aio-crud

Requires Python 3.10-3.14, Django 5.2 or 6.0, and Django Ninja 1.7.x.

Quick start

Define the model. A ModelSerializer is a normal Django model with a Schemas class that says which fields each operation reads and writes.

# blog/models.py
from django.db import models
from ninja_aio import ModelSerializer, SchemaConfig


class Article(ModelSerializer):
    title = models.CharField(max_length=200)
    body = models.TextField()
    is_published = models.BooleanField(default=False)
    created_at = models.DateTimeField(auto_now_add=True)

    class Schemas:
        create = SchemaConfig(
            fields=["title", "body"],
            optionals=[("is_published", bool)],
        )
        update = SchemaConfig(
            optionals=[("title", str), ("body", str), ("is_published", bool)],
        )
        read = SchemaConfig(
            fields=["id", "title", "body", "is_published", "created_at"],
        )

Create the API and add the URLs:

# blog/api.py
from ninja_aio import NinjaAIO, APIViewSet

from .models import Article

api = NinjaAIO(title="Blog API")


@api.viewset(model=Article)
class ArticleViewSet(APIViewSet):
    pass
# project/urls.py
from django.urls import path

from blog.api import api

urlpatterns = [
    path("api/", api.urls),
]

Run python manage.py runserver and open http://localhost:8000/api/docs.

Method Path What it does
GET /api/articles List articles, with pagination
POST /api/articles/ Create an article
GET /api/articles/{id} Get one article
PATCH /api/articles/{id}/ Update some fields
DELETE /api/articles/{id}/ Delete an article

Keep your models as they are

Use a Serializer when you don't want to change your model's base class:

# blog/serializers.py
from ninja_aio import Serializer, SchemaConfig

from .models import Article


class ArticleSerializer(Serializer[Article]):
    class Meta:
        model = Article

    class Schemas:
        create = SchemaConfig(fields=["title", "body"])
        update = SchemaConfig(optionals=[("title", str), ("body", str)])
        read = SchemaConfig(fields=["id", "title", "body"])
@api.viewset(model=Article)
class ArticleViewSet(APIViewSet):
    serializer_class = ArticleSerializer

Sync or async

Viewsets are async by default. To serve the same endpoints with regular sync views, set execution_mode:

@api.viewset(model=Article)
class ArticleViewSet(APIViewSet):
    execution_mode = "sync"

The model is also a CRUD API you can call in scripts, tasks and tests:

# Sync
article = Article.create({"title": "Draft", "body": "..."})
article = Article.update(article, {"is_published": True})
data = Article.model_dump(article)
# Async
article = await Article.acreate({"title": "Draft", "body": "..."})
article = await Article.aupdate(article, {"is_published": True})
data = await Article.amodel_dump(article)

Custom actions

from ninja_aio import APIViewSet, action, on


@api.viewset(model=Article)
class ArticleViewSet(APIViewSet):
    @on("publish")
    async def publish(self, request, obj):
        obj.is_published = True
        await obj.asave(update_fields=["is_published"])
        return await Article.amodel_dump(obj)

    @action(detail=False, url_path="stats")
    async def stats(self, request):
        return {"total": await Article.objects.acount()}

This adds POST /api/articles/{id}/publish and GET /api/articles/stats.

Validators

Add Pydantic validators to a CreateValidators or UpdateValidators class:

from pydantic import field_validator


class Article(ModelSerializer):
    # fields and Schemas as above

    class CreateValidators:
        @field_validator("title")
        @classmethod
        def title_not_blank(cls, value: str) -> str:
            if not value.strip():
                raise ValueError("Title cannot be blank")
            return value.strip()

Invalid input returns 422 with the error message.

Upgrading from 2.x

Version 3 replaces the inner ReadSerializer/CreateSerializer classes and Meta.schema_in/schema_out with a single class Schemas, adds sync viewsets and the Python CRUD API. Follow the migration guide to upgrade.

Support

If you find this project useful, consider giving it a star or supporting development:

Buy me a coffee

License

MIT License. See LICENSE.

Metadata

Release files for django-ninja-aio-crud 3.0.1

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-ninja-aio-crud 3.0.1
File Size Uploaded
django_ninja_aio_crud-3.0.1.tar.gz 10.3 MB Details

Built distribution (wheel)

Table of built distributions (wheels) for django-ninja-aio-crud 3.0.1
File Interpreter ABI Platform
django_ninja_aio_crud-3.0.1-py3-none-any.whl Python 3 none any Details

Total release size: 10.4 MB

Release files / django_ninja_aio_crud-3.0.1.tar.gz

Download URL django_ninja_aio_crud-3.0.1.tar.gz
Size 10.3 MB
Tags Source
SHA-256 checksum
How to use checksums
08005558e1eb71e8fb7c08a49653521c3aaf9baf16fc3449018b0acfb4d0852b
BLAKE2b-256 checksum
How to use checksums
c2bb15c5c7d48a3b624f1f3982473b4019ba194bc86e99d1af17efd989cdf189
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via python-requests/2.34.2

Release files / django_ninja_aio_crud-3.0.1-py3-none-any.whl

Download URL django_ninja_aio_crud-3.0.1-py3-none-any.whl
Size 136.1 kB
Tags Python 3
SHA-256 checksum
How to use checksums
4b3e38dd67d0b7eaf1914e969acd7eb576d37c629e84f3e2e5f157cb36e9e9d5
BLAKE2b-256 checksum
How to use checksums
ff7c72f96eb57b8421fb04bea21d0f7464726894bd25453578f346e5548f3816
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via python-requests/2.34.2

Release history Release notifications | RSS feed

This release

3.0.1 This release

2 release files

3.0.0

2 release files

2.36.0

2 release files

2.35.0

2 release files

2.34.2

2 release files

2.34.1

2 release files

2.34.0

2 release files

2.33.0

2 release files

2.32.0

2 release files

2.31.0

2 release files

2.30.6

2 release files

2.30.5

2 release files

2.30.4

2 release files

2.30.3

2 release files

2.29.0

2 release files

2.28.0

2 release files

2.27.0

2 release files

2.26.0

2 release files

2.25.0

2 release files

2.23.1

2 release files

2.23.0

2 release files

2.22.0

2 release files

2.21.0

2 release files

2.17.0

2 release files

2.16.2

2 release files

2.16.1

2 release files

2.16.0

2 release files

2.15.1

2 release files

2.15.0

2 release files

2.14.0

2 release files

2.13.0

2 release files

2.12.3

2 release files

2.12.2

2 release files

2.12.1

2 release files

2.12.0

2 release files

2.11.2

2 release files

2.11.1

2 release files

2.11.0

2 release files

2.10.1

2 release files

2.10.0

2 release files

2.9.0

2 release files

2.8.0

2 release files

2.7.0

2 release files

2.6.1

2 release files

2.5.0

2 release files

2.4.0

2 release files

2.3.2

2 release files

2.3.1

2 release files

2.3.0

2 release files

2.2.0

2 release files

2.1.0

2 release files

2.0.0

2 release files

1.0.5

2 release files

1.0.4

2 release files

1.0.3

2 release files

1.0.2

2 release files

1.0.1

2 release files

1.0.0

2 release files

0.11.4

2 release files

0.11.3

2 release files

0.11.2

2 release files

0.11.1

2 release files

0.11.0

2 release files

0.10.3

2 release files

0.10.2

2 release files

0.10.1

2 release files

0.10.0

2 release files

0.9.2

2 release files

0.9.1

2 release files

0.9.0

2 release files

0.8.4

2 release files

0.8.3

2 release files

0.8.2

2 release files

0.8.1

2 release files

0.8.0

2 release files

0.7.8

2 release files

0.7.7

2 release files

0.7.6

2 release files

0.7.5

2 release files

0.7.4

2 release files

0.7.3

2 release files

0.7.2

2 release files

0.7.1

2 release files

0.7.0

2 release files

0.6.4

2 release files

0.6.3

2 release files

0.6.2

2 release files

0.6.1

2 release files

0.6.0

2 release files

0.5.0

2 release files

0.4.0

2 release files

0.3.1

2 release files

0.3.0

2 release files

0.2.2

2 release files

0.2.1

2 release files

0.2.0

2 release files

0.1.4

2 release files

0.1.3

2 release files

0.1.2

2 release files

0.1.1

2 release files

0.1.0

2 release files

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