Introduction to Fenrir Framework
Fenrir is a state-of-the-art, high-performance, hybrid Python web framework built on top of modern ASGI specifications. It elegantly merges the best programming paradigms from Python's most popular web frameworks into a single unified workspace.
Why Hybrid?
Instead of rewriting or separating your microservices into different paradigms, Fenrir allows you to leverage FastAPI validation, Flask context-locals, and Falcon resources simultaneously in the same event-loop.
Key Features
- ⚡ High-Speed ASGI Core: Extremely low-overhead routing and handler pipeline, achieving massive request throughput.
- 🧩 Framework Hybridization: Coexist Flask-style context-locals, FastAPI-style dependencies, Falcon-style class-based resources, and Sanic listeners.
- 📖 Auto-Generated OpenAPI Docs: Interactive Swagger UI (at
/docsor/openapi-docs) instantly generated from your Pydantic schemas. - 🔌 Modern Communications: Native WebSockets and Server-Sent Events (SSE) out of the box.
- 🛠️ Premium CLI Tooling: Visual route tables, interactive shell, in-memory benchmarking suite, and scaffold creators.
Installation & Setup
Fenrir requires Python 3.8+. Install the official release from PyPI:
pip install fenrir-framework
Scaffolding a New Project
Fenrir comes packed with a robust scaffolding CLI to get you up and running with a cleanly structured layout instantly.
# Create a new scaffolded project
fenrir new my_website
cd my_website
Serving the Application
You can run your app locally using the Asteri ASGI app server:
# Run with hot reloading on port 8088
fenrir run app:app --port 8088 --dev
FastAPI Paradigm (Validation & DI)
Fenrir native integration with Pydantic v2 allows for dynamic, type-safe parameters, automated body parsing, and Dependency Injection patterns.
Key Features
- Automatic request body deserialization and Pydantic schema validation.
- Dependency injection with
Depends()decorators. - Parameter resolution (
Query,Path,Header,Form,File).
from pydantic import BaseModel
from fenrir import Fenrir, Depends, Header
app = Fenrir()
class UserRegister(BaseModel):
username: str
email: str
age: int
async def verify_token(x_api_key: str = Header(default=None)):
if x_api_key != "secret-token":
raise ValueError("Invalid credentials")
return x_api_key
@app.post("/api/register")
async def register(
body: UserRegister,
token: str = Depends(verify_token)
):
return {"status": "success", "user": body.model_dump(), "auth": token}
Flask Paradigm (Context & Templating)
For rendering user interfaces or retrieving parameters imperatively, Fenrir provides thread/task-safe context locals and Jinja2 rendering.
Context variables (Thread safe)
Fenrir uses contextvars to ensure request, g, and session are perfectly isolated across asynchronous operations, resolving legacy executor thread-safety bugs.
Key Features
- Context locals:
request,g,session. - Jinja2 standard rendering using
render_template(). - Flask-style exception handler hooks (
@app.exception(ValueError)).
from fenrir import Fenrir, request, g, render_template
app = Fenrir()
@app.get("/welcome")
async def welcome():
# Retrieve query params via global request context-local
name = request.args.get("name", "Guest")
# Share state across middleware/routes using request global g
g.visit_count = g.get("visit_count", 0) + 1
return render_template("welcome.html", name=name, count=g.visit_count)
Falcon Paradigm (Class-Based Resources)
If you prefer class-based, REST-compliant designs with direct control over request and response objects, Fenrir supports Falcon-style resources.
Key Features
- Class view methods mapping to HTTP verbs (
on_get,on_post,on_put,on_delete). - Direct mutation of the response media:
resp.media = {...}. - Lightweight routing mapping:
app.add_route("/path", Resource()).
from fenrir import Fenrir
app = Fenrir()
class ItemResource:
async def on_get(self, req, resp, item_id: int):
resp.status = 200
resp.media = {
"item_id": item_id,
"msg": "Fetched via Falcon Class-Based view!"
}
async def on_post(self, req, resp, item_id: int):
data = req.json
resp.status = 201
resp.media = {
"item_id": item_id,
"received": data
}
app.add_route("/items/<item_id:int>", ItemResource())
Sanic Paradigm (Tasks, Listeners & Hooks)
Manage lifecycle actions and run concurrent async tasks in the background using Sanic-style event scheduling.
Key Features
- Lifecycle listeners:
before_server_start,after_server_stop. - Global middleware hooks:
@app.middleware("request")and@app.middleware("response"). - Non-blocking background loop runner:
app.add_task().
import asyncio
from fenrir import Fenrir
app = Fenrir()
@app.listener("before_server_start")
async def setup_db_pool(app_inst):
print("Database connection initiated!")
async def background_poller():
while True:
print("Polling metrics...")
await asyncio.sleep(60)
@app.listener("after_server_start")
async def run_poller(app_inst):
# Register background coroutine
app_inst.add_task(background_poller())
Bottle Paradigm (WSGI mounting)
Run older legacy applications synchronously inside the high-speed ASGI event loop with Bottle-style legacy mounting adapters.
Key Features
- Mount legacy synchronous WSGI apps seamlessly:
app.mount_wsgi(wsgi_app, prefix="/legacy"). - Standard redirection helper:
redirect(location). - Send assets:
send_file(path_or_file)and directory secure readersend_from_directory(dir, path).
from fenrir import Fenrir, redirect
from legacy_app import flask_wsgi_app # WSGI app
app = Fenrir()
# Mount the Flask WSGI app onto ASGI routing
app.mount_wsgi(flask_wsgi_app, prefix="/legacy")
@app.get("/old-docs")
async def old_docs():
# Legacy bottle-style redirection
return redirect("/docs")
CLI Command Reference
Fenrir includes a visual, rich command-line tool. Execute fenrir or python -m fenrir.cli inside your shell.
| Command | Description | Example |
|---|---|---|
fenrir run |
Serve application using Asteri v2.2.2 ASGI with reload/multiprocess | fenrir run app:app --port 8088 --dev |
fenrir routes |
Visual colorized structural table of registered HTTP and WS paths | fenrir routes app:app |
fenrir shell |
Spawns an interactive REPL with loaded application state | fenrir shell app:app |
fenrir bench |
Runs zero-network HTTPX benchmarks directly over the ASGI pipeline | fenrir bench app:app -i 1000 -p / |
fenrir new |
Scaffolds a cleanly organized responsive web project directory | fenrir new project_name |
fenrir info |
Inspects active environment, engine modules and route statistics | fenrir info app:app |