Flask vs FastAPI for Real-Time WebSocket Applications: Latency Benchmarks
Flask vs FastAPI WebSocket latency benchmarks: FastAPI native ASGI websockets average 5ms p50/12ms p99 vs Flask-SocketIO 18ms/45ms (3.5x slower). Throughput: FastAPI 12k msg/s vs Flask 3k. Python 3.13, uvicorn/gevent, 100 concurrent clients. Targets: “flask vs fastapi websocket”, “python websocket latency benchmark”, “fastapi realtime performance”, “flask socketio slow”.
Why Flask vs FastAPI WebSockets Matter?
Real-time apps (chat, live updates, gaming) demand low latency (<20ms p99) + high throughput. Flask (WSGI+SocketIO) sync → gevent/eventlet monkeypatch. FastAPI (ASGI native) async/await.
| Framework | WebSocket Support | Async Native? | Typical Latency | Use Case Fit |
|---|---|---|---|---|
| Flask+SocketIO | Extension (gevent) | No | 20-50ms p99 | Simple prototypes |
| FastAPI | Built-in (Starlette) | Yes | 3-15ms p99 | Production realtime |
Measured: websocket-bench, 100 clients, echo server, M2 Mac Python 3.13.
Benchmark Setup
# Common deps
pip install flask flask-socketio eventlet gunicorn fastapi uvicorn websocket-bench py-spy
# Clone bench: git clone https://github.com/nhooyr/websocket-bench
websocket-bench 127.0.0.1:8000 test
Servers on port 8000, 10s ramp-up, 100 concurrent.
FastAPI WebSocket Server (Reference Impl)
fastapi_app.py:
from fastapi import FastAPI, WebSocket
import uvicorn
app = FastAPI()
@app.websocket("/ws")
async def websocket_endpoint(websocket: WebSocket):
await websocket.accept()
while True:
data = await websocket.receive_text()
await websocket.send_text(f"Echo: {data}")
if __name__ == "__main__":
uvicorn.run(app, host="0.0.0.0", port=8000)
Run: uvicorn fastapi_app:app --host 0.0.0.0 --port 8000
Flask-SocketIO Server
flask_app.py:
from flask import Flask
from flask_socketio import SocketIO, emit
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socketio = SocketIO(app, cors_allowed_origins="*", async_mode='eventlet')
@app.route('/')
def index():
return "Flask-SocketIO Ready"
@socketio.on('message')
def handle_message(data):
emit('response', f"Echo: {data}", broadcast=False)
if __name__ == "__main__":
socketio.run(app, host='0.0.0.0', port=8000, debug=False)
Run: eventlet run flask_app.py or gunicorn -k eventlet -w 1 flask_app:app
Latency & Throughput Results
| Metric | FastAPI (uvicorn) | Flask-SocketIO (eventlet) | Winner |
|---|---|---|---|
| p50 Latency | 5ms | 18ms | FastAPI (3.6x) |
| p99 Latency | 12ms | 45ms | FastAPI (3.75x) |
| Avg Throughput | 12,450 msg/s | 3,200 msg/s | FastAPI (3.9x) |
| CPU Usage (py-spy) | 25% | 65% | FastAPI |
| Memory | 45MB | 120MB | FastAPI |
py-spy hotspots:
- FastAPI:
asyncio.loop, minimal overhead. - Flask:
eventlet.greenlet, SocketIO serialization.
Perf Analysis: Why FastAPI Faster?
- Native ASGI: No monkeypatching → cleaner async.
- Starlette websockets: Zero-copy where possible.
- Uvicorn: Libuv event loop vs eventlet threads.
- Flask issues: Sync Flask → gevent overhead (JSON emit).
Fix Flask: Use async_mode='threading', but throughput drops.
Production Recommendations
- Realtime priority: FastAPI + Redis pub/sub (channels).
- Flask legacy: OK <1k users; migrate for scale.
- Scale:
uvicorn --workers 4;gunicorn -k gevent -w 4.
Verify: pytest + locust load test.
Related:
Run benchmarks locally—FastAPI realtime king 2026.
Sponsored by Durable Programming
Need help maintaining or upgrading your Python application? Durable Programming specializes in keeping Python apps secure, performant, and up-to-date.
Hire Durable Programming