All posts

Fix MemoryError in FastAPI in Production

Troubleshoot production FastAPI memory errors with profiling, connection pool tuning, and container resource configuration.

FastAPI Production Memory Errors

Production FastAPI services can slowly accumulate memory until the container is OOM-killed. Here's a systematic approach to finding and fixing the problem.

Profile Memory Usage

Add a debug endpoint (remove in production or protect it):

import tracemalloc
import os

tracemalloc.start()

@app.get("/debug/memory")
async def memory_stats():
    snapshot = tracemalloc.take_snapshot()
    top = snapshot.statistics('lineno')[:10]
    process_mb = os.popen('ps -o rss= -p %d' % os.getpid()).read().strip()
    return {
        "rss_mb": int(process_mb) / 1024,
        "top_allocations": [str(s) for s in top]
    }

Database Connection Pool

SQLAlchemy async sessions can leak if not properly scoped:

from sqlalchemy.ext.asyncio import create_async_engine, AsyncSession

engine = create_async_engine(
    DATABASE_URL,
    pool_size=10,
    max_overflow=5,
    pool_recycle=3600,  # Recycle connections hourly
    pool_pre_ping=True,
)

# Use dependency injection to ensure cleanup
async def get_db():
    async with AsyncSession(engine) as session:
        yield session

Container Configuration

resources:
  limits:
    memory: "512Mi"
  requests:
    memory: "256Mi"

Set Uvicorn's --limit-max-requests to recycle workers before they grow too large:

uvicorn main:app --workers 2 --limit-max-requests 5000 --limit-concurrency 50

Bugsly monitors process RSS over time and alerts when memory crosses configurable thresholds, giving you lead time before the OOM killer acts.

Try Bugsly Free

AI-powered error tracking that explains your bugs. Set up in 2 minutes, free forever for small projects.

Get Started Free