Skip to content
>_devvkit
$devvkit learn --librarie starlette-guide

Starlette Guide

[python][async][asgi][api]
Python
Install
pip install starlette
# or: uv add starlette
# or: poetry add starlette

Starlette is the foundation for many Python async frameworks (FastAPI builds on it). It provides ASGI support, WebSocket handling, background tasks, streaming responses, and middleware in a minimal package.

The routing system supports path parameters, method-based dispatching, and sub-app mounting. Starlette handles both HTTP and WebSocket connections on the same port. Middleware wraps the ASGI app chain.

Starlette's test client uses httpx for async integration testing. It includes a Server-Sent Events (SSE) streaming response and integrates with Jinja2 for templating when needed.

Setup

Basic appASGI Starlette app.
from starlette.applications import Starlette
from starlette.responses import JSONResponse
from starlette.routing import Route

async def homepage(request):
    return JSONResponse({"hello": "world"})

async def about(request):
    return JSONResponse({"message": "About us"})

app = Starlette(routes=[
    Route("/", homepage),
    Route("/about", about),
])

Routing

Path parametersURL parameters.
async def user_detail(request):
    user_id = request.path_params["user_id"]
    return JSONResponse({"user_id": user_id})

Route("/users/{user_id:int}", user_detail)
Route("/users/{username:str}", user_detail)
Route("/files/{path:path}", file_download)
Mount sub-appMount other ASGI apps.
from starlette.staticfiles import StaticFiles

app.mount("/static", StaticFiles(directory="static"), name="static")
app.mount("/api", api_app)

Middleware

Custom middlewareWrap request/response.
from starlette.middleware.base import BaseHTTPMiddleware

class TimingMiddleware(BaseHTTPMiddleware):
    async def dispatch(self, request, call_next):
        start = time.time()
        response = await call_next(request)
        elapsed = time.time() - start
        response.headers["X-Elapsed"] = str(elapsed)
        return response

app.add_middleware(TimingMiddleware)

WebSockets

WebSocketHandle WS connections.
from starlette.websockets import WebSocket

async def ws_endpoint(websocket: WebSocket):
    await websocket.accept()
    while True:
        data = await websocket.receive_text()
        await websocket.send_text(f"Echo: {data}")

Route("/ws", endpoint=ws_endpoint)

Background Tasks

Background taskRun after response.
from starlette.background import BackgroundTask

async def send_email(email: str):
    ...  # send email

async def create_user(request):
    data = await request.json()
    task = BackgroundTask(send_email, email=data["email"])
    return JSONResponse({"ok": True}, background=task)

Testing

Test clientAsync test client.
from starlette.testclient import TestClient

def test_homepage():
    client = TestClient(app)
    response = client.get("/")
    assert response.status_code == 200
    assert response.json() == {"hello": "world"}