ASGI Worker¶
Beta Feature
The ASGI worker is a beta feature introduced in Gunicorn 24.0.0. While it has been tested, the API and behavior may change in future releases. Please report any issues on GitHub.
Gunicorn includes a native ASGI worker that enables running async Python web frameworks like FastAPI, Starlette, and Quart without external dependencies like Uvicorn.
Quick Start¶
# Install gunicorn
pip install gunicorn
# Run an ASGI application
gunicorn myapp:app --worker-class asgi --workers 4
For FastAPI applications:
gunicorn main:app --worker-class asgi --bind 0.0.0.0:8000
Features¶
The ASGI worker provides:
- HTTP/1.1 with keepalive connections
- WebSocket support for real-time applications
- Lifespan protocol for startup/shutdown hooks
- Optional uvloop for improved performance
- SSL/TLS support
Configuration¶
Worker Class¶
Set the worker class to asgi:
gunicorn myapp:app --worker-class asgi
Or in a configuration file:
# gunicorn.conf.py
worker_class = "asgi"
Event Loop¶
Control which asyncio event loop implementation to use:
| Value | Description |
|---|---|
auto |
Use uvloop if available, otherwise asyncio (default) |
asyncio |
Use Python's built-in asyncio event loop |
uvloop |
Use uvloop (must be installed separately) |
gunicorn myapp:app --worker-class asgi --asgi-loop uvloop
To use uvloop, install it first:
pip install uvloop
Lifespan Protocol¶
The lifespan protocol lets your application run code at startup and shutdown. This is essential for frameworks that need to initialize database connections, caches, or background tasks.
| Value | Description |
|---|---|
auto |
Detect if app supports lifespan, enable if so (default) |
on |
Always run lifespan protocol (fail if unsupported) |
off |
Never run lifespan protocol |
gunicorn myapp:app --worker-class asgi --asgi-lifespan on
Example FastAPI application using lifespan:
from contextlib import asynccontextmanager
from fastapi import FastAPI
@asynccontextmanager
async def lifespan(app: FastAPI):
# Startup: initialize resources
print("Starting up...")
yield
# Shutdown: cleanup resources
print("Shutting down...")
app = FastAPI(lifespan=lifespan)
Root Path¶
When running behind a reverse proxy that mounts your application at a subpath,
set root_path so your application knows its mount point:
gunicorn myapp:app --worker-class asgi --root-path /api
This is equivalent to the SCRIPT_NAME in WSGI applications.
Worker Connections¶
Control the maximum number of concurrent connections per worker:
gunicorn myapp:app --worker-class asgi --worker-connections 1000
Note
Unlike sync workers, the --threads option has no effect on ASGI workers.
Use --worker-connections to control concurrency.
WebSocket Support¶
The ASGI worker supports WebSocket connections out of the box. No additional configuration is required.
Example with Starlette:
from starlette.applications import Starlette
from starlette.routing import WebSocketRoute
async def websocket_endpoint(websocket):
await websocket.accept()
while True:
data = await websocket.receive_text()
await websocket.send_text(f"Echo: {data}")
app = Starlette(routes=[
WebSocketRoute("/ws", websocket_endpoint),
])
Production Deployment¶
With Nginx¶
upstream gunicorn {
server 127.0.0.1:8000;
}
server {
listen 80;
server_name example.com;
location / {
proxy_pass http://gunicorn;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
# WebSocket support
location /ws {
proxy_pass http://gunicorn;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
proxy_set_header Host $host;
}
}
Recommended Settings¶
For production ASGI deployments:
# gunicorn.conf.py
worker_class = "asgi"
workers = 4 # Number of worker processes
worker_connections = 1000 # Max connections per worker
keepalive = 5 # Keepalive timeout
timeout = 120 # Worker timeout
graceful_timeout = 30 # Graceful shutdown timeout
# Performance tuning
asgi_loop = "auto" # Use uvloop if available
asgi_lifespan = "auto" # Auto-detect lifespan support
Comparison with Other ASGI Servers¶
| Feature | Gunicorn ASGI | Uvicorn | Hypercorn |
|---|---|---|---|
| Process management | Built-in | External | Built-in |
| HTTP/2 | No | No | Yes |
| WebSocket | Yes | Yes | Yes |
| Lifespan | Yes | Yes | Yes |
| uvloop support | Yes | Yes | Yes |
Gunicorn's ASGI worker provides the same process management, logging, and configuration capabilities you're familiar with from WSGI deployments.
Troubleshooting¶
Lifespan startup failed¶
If you see "ASGI lifespan startup failed", your application may not properly
implement the lifespan protocol. Either fix the application or set
--asgi-lifespan off.
Connection limits¶
If you're hitting connection limits, increase --worker-connections or add
more workers with --workers.
Slow responses under load¶
Try using uvloop for better performance:
pip install uvloop
gunicorn myapp:app --worker-class asgi --asgi-loop uvloop
See Also¶
- Settings Reference - All ASGI-related settings
- Deploy - General deployment guidance
- Design - Worker architecture overview