Failures
Failures
GitHub
Home Docs Resource Exhaustion
HIGH

Resource Exhaustion

"What happens when capacity is exceeded?"

Invariant: System must bound resource use and shed load gracefully.

Applies To

APIs, connection pools, queues, file uploads

Why It Happens

A first-principles walkthrough of why unbounded work always finds a limit — connection pools, memory, queue depth, file size. How an unbounded `await file.read()` OOMs the process, and how bounded pools, token-bucket rate limiting, chunked streaming, and backpressure shed load gracefully instead of crashing.

How It Works Underneath

Every resource has a ceiling: file descriptors, DB connections, memory, queue depth. An unbounded await file.read() loads a 500 MB upload into RAM, the process OOMs, the orchestrator restarts it, the client retries the same upload, and the loop repeats. The fix is to bound: pool(max_size=20), TokenBucket(capacity=100), read(64*1024) chunked, and backpressure — when full, return 429, do not queue forever.

Cataloged Failure Modes

Code Comparison

Language:
Fragile (AI Happy Path) — Python resource-exhaustion_fragile.py
# NAIVE: Reading full file into RAM
@app.post("/upload")
async def upload(file: UploadFile):
    return {"size": len(await file.read())}
Resilient (Failures Verified) — Python
resource-exhaustion_safe.py
# IMPROVED: Chunked streaming with size caps
@app.post("/upload")
async def upload(file: UploadFile):
    while chunk := await file.read(64 * 1024):
        await stream_save(chunk)

Mitigation Patterns