Skip to main content

Rust-powered async Python web framework — start minimal, grow with rusjango add

Project description

Rusjango

Rust-powered async Python web framework

Start like Flask · Scale like Django · Perform like Rust · Build AI apps natively

Python Rust License: MIT Tests Phase


What is Rusjango?

Rusjango is a modern Python web framework with a Rust core. It is inspired by Django, FastAPI, Polars, and modern AI-native backend systems.

The core idea is simple:

A developer starts with three files and grows into a full enterprise framework — without ever changing frameworks.

rusjango new myapp          # three files: main.py, settings.py, pyproject.toml
rusjango add app users      # add a feature
rusjango add orm            # add another feature
rusjango add auth           # add another feature
rusjango remove app users   # safely remove what you no longer need

No bloat by default. Everything is opt-in.


Why Rusjango?

Problem with existing tools Rusjango solution
Django was built sync-first Fully async from the ground up
New Django project has too many files Three files: main.py, settings.py, pyproject.toml
Django ORM is not async-native Custom async-first ORM
Django admin UI feels outdated Modern React + Tailwind admin (Phase 5)
FastAPI has no built-in ORM or admin Native ORM + admin built in
Python-only frameworks have performance limits Rust-powered routing, middleware, serialization
No framework is AI-native Native LLM/RAG/agent module (Phase 9)
Features pile up and can't be removed Every feature is removable with rusjango remove

Features

Available now (Phase 1–3)

  • Minimal project scaffoldrusjango new creates exactly 3 files
  • Async HTTP routing@app.get, @app.post, @app.put, @app.delete
  • Path & query parameters — auto type coercion (int, float, bool, str)
  • JSON request body — parsed automatically, validated via Schema
  • Schema validation — lightweight typed request/response objects
  • Middleware system — composable ASGI middleware stack
  • Security middleware — host validation + X-Frame-Options / X-Content-Type-Options
  • App systemrusjango add app <name> scaffolds a self-contained app package
  • INSTALLED_APPS — auto-discovery and route mounting under /api/<app>/
  • Per-app Router isolation — each app owns its own route table, no cross-contamination
  • Async ORM — Django-style model API, fully async
  • SQLite support — via aiosqlite, zero config
  • PostgreSQL support — via asyncpg
  • ORM filter lookupsexact, gte, lte, gt, lt
  • Migrationsrusjango migrate creates tables from registered models
  • Dev server — uvicorn with auto-reload via rusjango dev
  • Rust CLI — fast binary with rich help output

Coming soon

Feature Phase
rusjango add docker Phase 4
rusjango add tests Phase 4
Full Schema validation (coercion, defaults, nested) Phase 4
Admin panel (React + Tailwind, auto CRUD) Phase 5
Auth system (JWT, sessions, argon2, roles) Phase 6
Auto API docs (OpenAPI) Phase 7
Background workers (Redis) Phase 8
AI/LLM native module (RAG, streaming, tool calls) Phase 9
Enterprise: audit logs, multi-tenancy, observability Phase 10

Quick Start

Prerequisites

Tool Version Install
Rust stable rustup.rs
uv latest docs.astral.sh/uv
Python 3.10+ via uv or system

1. Clone and build

git clone git@github.com:babar-xagi/Rusjango.git
cd Rusjango

# Install Python dependencies
uv sync

# Build the Rust extension (PyO3 / maturin)
uv run maturin develop -m python/rusjango/pyproject.toml

# Build the CLI binary
cargo build -p rusjango-cli

2. Create your first project

cargo run -p rusjango-cli -- new hello
cd hello
uv sync
cargo run -p rusjango-cli -- dev

Open http://127.0.0.1:8000 — you should see:

{ "message": "Hello Rusjango" }

After cargo install: Once you run cargo install --path cli from the repo root, you can use rusjango directly instead of cargo run -p rusjango-cli --.


Your First Project — Step by Step

Step 1 — Create project

rusjango new hello
cd hello

Generated structure:

hello/
├── main.py
├── settings.py
└── pyproject.toml

main.py:

from rusjango import Rusjango

app = Rusjango(settings="settings.py")

@app.get("/")
async def home():
    return {"message": "Hello Rusjango"}

app.load_installed_apps()

Step 2 — Run the server

rusjango dev
Rusjango running at http://127.0.0.1:8000
  Auto-reload enabled

Step 3 — Add an app

rusjango add app school

Creates apps/school/ and registers it in settings.py:

hello/
├── main.py
├── settings.py
├── apps/
│   └── school/
│       ├── __init__.py
│       └── api.py          ← routes are at /api/school/...
└── pyproject.toml

apps/school/api.py:

from rusjango import Router

router = Router()

@router.get("/students")
async def list_students():
    return [{"name": "Ali"}, {"name": "Sara"}]

Step 4 — Add the ORM

rusjango add orm
rusjango migrate

Adds models.py and schemas.py to every app, creates migrations/, configures SQLite:

# apps/school/models.py
from rusjango.orm import Model, Integer, String

class Student(Model):
    id = Integer(primary_key=True)
    name = String(max_length=100)
    age = Integer(nullable=True)
# apps/school/api.py  (upgraded automatically)
from rusjango import Router
from .models import Student
from .schemas import StudentCreate, StudentOut

router = Router()

@router.get("/students")
async def list_students():
    students = await Student.all()
    return [StudentOut.from_dict(s.to_dict()).dict() for s in students]

@router.post("/students")
async def create_student(data: StudentCreate):
    student = await Student.create(name=data.name, age=data.age)
    return StudentOut.from_dict(student.to_dict()).dict()

Step 5 — Remove what you don't need

rusjango remove app school
This will remove the 'school' app and unregister it from settings.py.
Do you want to continue? [y/N]

Safe by default. Always asks before deleting.


API Reference

Route decorators

@app.get("/path")
@app.post("/path")
@app.put("/path/{id}")
@app.delete("/path/{id}")

Path parameters

@app.get("/students/{id}")
async def get_student(id: int):      # auto-cast to int
    return {"id": id}

Query parameters

@app.get("/students")
async def list_students(limit: int = 10, search: str = ""):
    ...

Request body

from rusjango import Schema

class StudentCreate(Schema):
    name: str
    age: int

@app.post("/students")
async def create_student(data: StudentCreate):
    return data.dict()

HTTP exceptions

from rusjango import HTTPException

@app.get("/admin")
async def admin():
    raise HTTPException(403, detail="Forbidden")

Per-app Router

# apps/school/api.py
from rusjango import Router

router = Router()   # always create a fresh instance per app

@router.get("/students")
async def list_students():
    return []

ORM Reference

Model definition

from rusjango.orm import Model, Integer, String, Text, Boolean

class Post(Model):
    id      = Integer(primary_key=True)
    title   = String(max_length=200)
    body    = Text(nullable=True)
    active  = Boolean(default=True)

CRUD

# Create
post = await Post.create(title="Hello", body="World")

# Read
post = await Post.get(id=1)              # raises DoesNotExist if not found
posts = await Post.all()
posts = await Post.filter(active=True).all()

# Filter lookups: exact (default), gte, lte, gt, lt
posts = await Post.filter(id__gte=5).all()

# Update
await Post.filter(id=1).update(title="Updated")

# Delete
await Post.filter(id=1).delete()

Database settings

# settings.py — SQLite (default)
DATABASE = {
    "ENGINE": "sqlite",
    "NAME": "db.sqlite3",
    "ASYNC": True,
}

# PostgreSQL
DATABASE = {
    "ENGINE": "postgresql",
    "URL": "postgresql://user:pass@localhost:5432/mydb",
    "ASYNC": True,
}

CLI Reference

Command Description
rusjango new <name> Create a minimal 3-file project
rusjango dev Start dev server (uvicorn + auto-reload)
rusjango dev --host 0.0.0.0 --port 9000 Custom host/port
rusjango dev --no-reload Disable auto-reload
rusjango add app <name> Scaffold apps/<name>/ and register it
rusjango remove app <name> Remove app (prompts for confirmation)
rusjango remove app <name> --yes Remove without prompting
rusjango add orm Enable async ORM (SQLite by default)
rusjango remove orm Disable ORM, keep model files
rusjango migrate Create database tables from models

Planned commands:

Command Phase
rusjango add admin / remove admin Phase 5
rusjango add auth / remove auth Phase 6
rusjango add docker / remove docker Phase 4
rusjango add tests / remove tests Phase 4
rusjango add worker / remove worker Phase 8
rusjango add ai / remove ai Phase 9
rusjango add payments / remove payments Phase 10

Project Structure

Rusjango/
├── Cargo.toml                    # Rust workspace (core + CLI)
├── pyproject.toml                # uv workspace root
├── PROGRESS.md                   # Phase-by-phase build tracker
│
├── crates/rusjango-core/         # PyO3 Rust extension
│   └── src/
│       ├── lib.rs                # Python module entry point
│       └── router.rs             # Future: Rust-accelerated routing
│
├── cli/                          # rusjango binary (clap)
│   └── src/
│       ├── main.rs               # Command definitions
│       ├── new.rs                # rusjango new
│       ├── add.rs                # rusjango add app
│       ├── remove.rs             # rusjango remove app
│       ├── orm.rs                # rusjango add/remove orm + migrate
│       ├── dev.rs                # rusjango dev
│       ├── project.rs            # Template rendering, project root detection
│       └── settings.rs           # settings.py manipulation (regex-based)
│
├── python/rusjango/              # Python package (maturin)
│   ├── pyproject.toml
│   └── src/rusjango/
│       ├── __init__.py           # Public API: Rusjango, Router, Schema, HTTPException
│       ├── app.py                # Rusjango application class + route decorators
│       ├── routing.py            # Route compilation, param extraction, handler dispatch
│       ├── asgi.py               # ASGI helpers: read_body, send_json, send_error
│       ├── middleware.py         # Middleware stack builder
│       ├── security.py           # SecurityMiddleware
│       ├── schema.py             # Schema base class
│       ├── settings.py           # settings.py loader
│       ├── config.py             # pyproject.toml discovery
│       ├── apps.py               # INSTALLED_APPS loader + router mounting
│       ├── exceptions.py         # HTTPException, error envelope
│       ├── server.py             # Dev server (uvicorn)
│       └── orm/
│           ├── model.py          # Model metaclass + CRUD
│           ├── fields.py         # Integer, String, Text, Boolean
│           ├── query.py          # QuerySet (lazy, chainable)
│           ├── sql.py            # SQL generation (parameterized, injection-safe)
│           └── connection.py     # aiosqlite / asyncpg connection management
│
├── templates/                    # .tpl files for code generation
│   ├── project/                  # rusjango new templates
│   ├── app/                      # rusjango add app templates
│   └── orm/                      # rusjango add orm templates
│
├── examples/
│   └── hello/                    # Working example project (school app + ORM)
│
└── docs/                         # Documentation (14 files)
    ├── 00-overview.md
    ├── 01-architecture.md
    ├── 02-getting-started.md
    ├── 03-cli-reference.md
    ├── 04-api-design.md
    ├── 05-orm-guide.md
    ├── 06-settings-reference.md
    ├── 07-middleware.md
    ├── 08-schema-validation.md
    ├── 09-progress.md
    ├── 10-contributing.md
    └── internals/
        ├── rust-core.md
        ├── python-layer.md
        └── orm-internals.md

Development Setup

# 1. Clone
git clone git@github.com:babar-xagi/Rusjango.git
cd Rusjango

# 2. Python deps
uv sync

# 3. Build Rust extension (PyO3 / maturin)
uv run maturin develop -m python/rusjango/pyproject.toml

# 4. Build CLI
cargo build -p rusjango-cli

# 5. Run tests
cd python/rusjango
uv run pytest tests/ -v

Testing

tests/test_import.py        package version importable
tests/test_asgi.py          routing, path params, POST body, HTTPException (5 tests)
tests/test_apps.py          INSTALLED_APPS loading, multi-app router isolation (3 tests)
tests/test_config.py        pyproject.toml project root discovery
tests/test_orm.py           ORM CRUD, filters, update, delete — SQLite (3 tests)
cd python/rusjango
uv run pytest tests/ -v
# 13 passed in ~0.5s

Architecture

┌──────────────────────────────────────────────────────┐
│  Developer Layer (Python)                            │
│  @app.get("/")  |  class Student(Model)  |  Schema   │
├──────────────────────────────────────────────────────┤
│  Framework Layer (Python)                            │
│  routing · ASGI · middleware · ORM query builder     │
├──────────────────────────────────────────────────────┤
│  Core Layer (Rust — PyO3)                            │
│  routing acceleration · serialization · conn pool   │
│  (current: version stub + future expansion)          │
└──────────────────────────────────────────────────────┘
         ↑ served by uvicorn (ASGI 3.0)

Python-Rust boundary rule:

Rust handles heavy batch operations — routing, serialization, connection pooling. Python handles business logic — models, handlers, middleware.


Roadmap

Phase Goal Status
1 CLI + minimal API framework ✅ Complete
2 Add/Remove app system ✅ Complete
3 Async ORM foundation ✅ Complete
4 Schema validation + Docker + Tests scaffolding 🚧 In progress
5 Admin panel MVP (React + Tailwind) 📋 Planned
6 Auth system (JWT, sessions, argon2) 📋 Planned
7 API docs + developer experience 📋 Planned
8 Worker system (Redis background tasks) 📋 Planned
9 AI/LLM native module (RAG, streaming) 📋 Planned
10 Enterprise features (multi-tenancy, audit, metrics) 📋 Planned

See PROGRESS.md for full details and docs/09-progress.md for per-phase file references.


Documentation

All docs live in docs/:

File What it covers
docs/00-overview.md Project vision, problems solved, user types, tech stack
docs/01-architecture.md Monorepo layout, 3-layer arch, request lifecycle
docs/02-getting-started.md Full setup guide from scratch
docs/03-cli-reference.md Every CLI command with options and examples
docs/04-api-design.md Routes, params, body, Schema, Router, middleware
docs/05-orm-guide.md Models, fields, CRUD, filters, migrations
docs/06-settings-reference.md Every settings key explained
docs/07-middleware.md Middleware system, custom middleware
docs/08-schema-validation.md Schema class, validation, limitations
docs/09-progress.md Phase tracker with file references
docs/10-contributing.md How to add features, code style, PR checklist
docs/internals/rust-core.md PyO3, maturin, clap internals
docs/internals/python-layer.md ASGI, routing dispatch, settings isolation
docs/internals/orm-internals.md Metaclass, SQL generation, connection lifecycle

Contributing

  1. Read docs/10-contributing.md
  2. Set up the dev environment (see Development Setup)
  3. Run the test suite and make sure it passes
  4. Open a pull request with a clear description

Development rules:

  • Keep the default project tiny — never generate unnecessary files
  • Every feature must be removable
  • Every CLI command must update settings.py automatically
  • Dangerous commands must ask for confirmation
  • ORM must be async-first
  • Rust speeds up internals — Python owns business logic
  • Documentation is written alongside code, not after

License

MIT — see LICENSE


Built with Python · Rust · PyO3 · maturin · clap · uvicorn · aiosqlite · asyncpg

Project details


Download files

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

Source Distributions

No source distribution files available for this release.See tutorial on generating distribution archives.

Built Distributions

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

rusjango-0.1.1-cp38-abi3-win_amd64.whl (125.4 kB view details)

Uploaded CPython 3.8+Windows x86-64

rusjango-0.1.1-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (256.2 kB view details)

Uploaded CPython 3.8+manylinux: glibc 2.17+ x86-64

rusjango-0.1.1-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (252.1 kB view details)

Uploaded CPython 3.8+manylinux: glibc 2.17+ ARM64

rusjango-0.1.1-cp38-abi3-macosx_11_0_arm64.whl (227.1 kB view details)

Uploaded CPython 3.8+macOS 11.0+ ARM64

rusjango-0.1.1-cp38-abi3-macosx_10_12_x86_64.whl (227.8 kB view details)

Uploaded CPython 3.8+macOS 10.12+ x86-64

File details

Details for the file rusjango-0.1.1-cp38-abi3-win_amd64.whl.

File metadata

  • Download URL: rusjango-0.1.1-cp38-abi3-win_amd64.whl
  • Upload date:
  • Size: 125.4 kB
  • Tags: CPython 3.8+, Windows x86-64
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.1.0 CPython/3.13.12

File hashes

Hashes for rusjango-0.1.1-cp38-abi3-win_amd64.whl
Algorithm Hash digest
SHA256 da15c394081329c4d1e9859d674ea02ce0bfa304260b678b864b93b7ffd6f53c
MD5 37ebb33ae50006724ed1b0650121bce8
BLAKE2b-256 6d730e6740ba3c9da15a226e90bba5c5811a27613b942e17f339575faf89edad

See more details on using hashes here.

File details

Details for the file rusjango-0.1.1-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for rusjango-0.1.1-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 5e9dfff632f246137766679b5677d4139927281f3d69b8a6ff939f673a456002
MD5 b76362e3209a02d640d67002c062be4b
BLAKE2b-256 cc73c292a836820b408d5acc40b4f91dd312c7feb4f7f05259ba68e07117c372

See more details on using hashes here.

File details

Details for the file rusjango-0.1.1-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for rusjango-0.1.1-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 ada0687f6bbdd70066f60a622d94ee9cf88368b9df57331fa901b5877fd18bf2
MD5 450bb7ab1f5050fab3320ea98438c8b3
BLAKE2b-256 8a512550effceaee20487d9957c7ad28a372cff008290851b84cd811010f98de

See more details on using hashes here.

File details

Details for the file rusjango-0.1.1-cp38-abi3-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for rusjango-0.1.1-cp38-abi3-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 c3020195e7ba9ea9564404fddd3115e1d975bb9fe881bbab1a126910f224814a
MD5 28f1550577a00595cc4a174fa9578565
BLAKE2b-256 65a3a086ff01f7565557fc1f5eef48133161b121c5fbe91048e95ed76dfafaff

See more details on using hashes here.

File details

Details for the file rusjango-0.1.1-cp38-abi3-macosx_10_12_x86_64.whl.

File metadata

File hashes

Hashes for rusjango-0.1.1-cp38-abi3-macosx_10_12_x86_64.whl
Algorithm Hash digest
SHA256 a27e455926cf4d6d556b0108e627cdf85820653521a7fa0e5d82bfed021b6a4b
MD5 7d9a0ba9bec0896700062a8912a78a21
BLAKE2b-256 75bb759b77e168e58d294e03d35909e7cc7d5425d3601711a66d07eac75e2525

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