Skip to main content

An intelligent compiler tool to convert Django Rest Framework code to Django Ninja.

Project description

🤖 DRF to Django Ninja Compiler

CI License: MIT Python 3.10+

An intelligent, user-friendly compiler tool designed to automatically parse Django Rest Framework (DRF) code (serializers.py, views.py, urls.py, settings.py) and convert it into modern, fast Django Ninja equivalents (schemas.py, api.py).

Tired of manually migrating hundreds of legacy DRF endpoints? This tool automates the heavy lifting by leveraging Abstract Syntax Tree (AST) parsing to reverse-engineer your code.

CLI Demo

✨ Features

  • Pydantic Schemas: Parses DRF ModelSerializer and generates standard Ninja ModelSchema.
  • Intelligent Routing: Parses DRF APIView and ModelViewSet and generates clean @router or @api endpoints.
  • URL Wiring: Parses urls.py and generates NinjaAPI setup with router registration.
  • Auth & Permissions: Detects permission_classes and authentication_classes and maps them to Ninja equivalents.
  • Settings Migration: Parses REST_FRAMEWORK settings dict and generates a migration report (pagination, throttling, filters).
  • User Review: Automatically flags custom overrides (like SerializerMethodField or custom View methods) and injects helpful TODO comments so you know exactly what needs manual review.
  • Beautiful DX: Powered by Typer and Rich for a stunning terminal experience.

� Before & After

Your legacy DRF code:

# serializers.py
class OrderSerializer(serializers.ModelSerializer):
    total = serializers.SerializerMethodField()

    class Meta:
        model = Order
        fields = ['id', 'status', 'total']

    def get_total(self, obj):
        return sum(item.price for item in obj.items.all())

What the compiler generates:

# schemas.py (auto-generated)
class OrderSchema(ModelSchema):
    # ⚠️ USER REVIEW REQUIRED:
    # The compiler detected custom fields or methods in the DRF Serializer:
    #  - total
    #  - method:get_total
    # You will need to manually map these to Pydantic types or Resolve() blocks.
    class Meta:
        model = Order
        fields = ['id', 'status', 'total']

Your legacy DRF ViewSet:

# views.py
class OrderViewSet(viewsets.ModelViewSet):
    queryset = Order.objects.all()
    serializer_class = OrderSerializer

    def list(self, request): ...
    def create(self, request): ...

What the compiler generates:

# api.py (auto-generated)
@router.get('/order/', response=list[OrderSchema])
def list_order(request):
    """Automatically generated list view for OrderViewSet."""
    return Order.objects.all()

@router.post('/order/', response=OrderSchema)
def create_order(request, payload: OrderInSchema):
    """Automatically generated create view for OrderViewSet."""
    # TODO: Implement creation logic using payload.dict()
    pass

🚀 Installation

# Install from PyPI (recommended)
pip install drf-to-ninja

# Or install from source for development
git clone https://github.com/lektronik/drf-to-ninja-compiler.git
cd drf-to-ninja-compiler
python3 -m venv venv
source venv/bin/activate
pip install -e .

🛠 Usage

Simply point the compiler at your existing DRF files:

# Full migration — serializers, views, urls, and settings
drf2ninja -s myapp/serializers.py -v myapp/views.py -u myapp/urls.py --settings myapp/settings.py

# Use @api.get() syntax instead of @router.get()
drf2ninja -s myapp/serializers.py -v myapp/views.py --style api

# Preview without writing files
drf2ninja -s myapp/serializers.py --dry-run

# Write generated files to a directory
drf2ninja -s myapp/serializers.py -v myapp/views.py -o ./ninja_output/
Flag Description
-s, --serializers Path to DRF serializers.py
-v, --views Path to DRF views.py
-u, --urls Path to DRF urls.py
--settings Path to Django settings.py
--style Output style: router (default) or api
--dry-run Preview output without writing files
-o, --output Directory to write generated files

📖 Step-by-Step Migration Guide

This is the recommended workflow to migrate a DRF app to Django Ninja:

Step 1: Run the Compiler

drf2ninja -s myapp/serializers.py -v myapp/views.py -u myapp/urls.py --settings myapp/settings.py -o ./ninja_output/

This generates four files in ./ninja_output/:

  • schemas.py — Pydantic schemas (replaces serializers)
  • api.py — Ninja route handlers (replaces views)
  • urls.py — NinjaAPI wiring (replaces DRF router config)
  • migration_report.py — Settings migration guide

Step 2: Handle Flagged Code

The compiler flags anything it can't fully auto-translate with a ⚠️ USER REVIEW REQUIRED comment. Here's what to do for each case:

Flagged Pattern What It Means What To Do
SerializerMethodField A computed field using get_*() Use a Resolver in your Schema
Custom validate_*() DRF field validator Use Pydantic's @field_validator decorator
perform_create() / perform_update() Custom save logic in ViewSet Move the logic into your Ninja route function body
Custom @action methods Extra ViewSet endpoints Create a separate @router.get() / @router.post() for each
permission_classes DRF permission check Use Ninja's auth= parameter or custom auth callables
authentication_classes DRF auth backend Use HttpBearer, django_auth, or HttpBasicAuth from ninja.security
DEFAULT_THROTTLE_CLASSES DRF throttling Use django-ninja-extra or custom middleware (Ninja has no built-in throttle)
DEFAULT_FILTER_BACKENDS DRF filter backends Use FilterSchema or manual query parameters in Ninja

Step 3: Wire the API

In your main urls.py, add the Ninja API:

# urls.py
from ninja_output.api import router  # or api, depending on --style

from ninja import NinjaAPI

api = NinjaAPI()
api.add_router("/", router)

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

Step 4: Install Django Ninja

pip install django-ninja

Add "ninja" to INSTALLED_APPS in settings.py and run your project:

python manage.py runserver

Your new API documentation is automatically available at /api/docs.

Step 5: Verify and Clean Up

  • Visit /api/docs to confirm all endpoints are live
  • Run your existing test suite to catch regressions
  • Remove old DRF code once everything works
  • Uninstall DRF: pip uninstall djangorestframework

🔒 Security & Code Quality

This project uses pre-commit hooks to ensure code quality and security.

  • Formatting: black
  • Security Analysis: bandit

To set up the hooks locally:

pip install pre-commit
pre-commit install

🤝 Contributing

See CONTRIBUTING.md for setup instructions and guidelines.

pytest tests/  # Run the test suite (22 tests)

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

drf_to_ninja-0.1.2.tar.gz (19.3 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

drf_to_ninja-0.1.2-py3-none-any.whl (17.1 kB view details)

Uploaded Python 3

File details

Details for the file drf_to_ninja-0.1.2.tar.gz.

File metadata

  • Download URL: drf_to_ninja-0.1.2.tar.gz
  • Upload date:
  • Size: 19.3 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.3

File hashes

Hashes for drf_to_ninja-0.1.2.tar.gz
Algorithm Hash digest
SHA256 c55b813b643e9a935524ac19962502820283947755864a3df06e26e9ddfa8df4
MD5 11818d02a7615f11e7f1ebd277d8bdc3
BLAKE2b-256 24461790553cd52f0fa69b17e606befb15b5ce9c3ab01a7534e70a4dc46292aa

See more details on using hashes here.

File details

Details for the file drf_to_ninja-0.1.2-py3-none-any.whl.

File metadata

  • Download URL: drf_to_ninja-0.1.2-py3-none-any.whl
  • Upload date:
  • Size: 17.1 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.12.3

File hashes

Hashes for drf_to_ninja-0.1.2-py3-none-any.whl
Algorithm Hash digest
SHA256 d333ac27903258c950f14e61cd1640344d46c55ee014145889d8272fa2d86aaa
MD5 735a61e394a720f270f06c5ab7860ea0
BLAKE2b-256 2e50d3b704c0dfa3df6a9fd4c88c18082cfdb1435474287e58e6785bc1797492

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page