The Fix
Breaks cyclic references at connection close when there was a traceback, addressing a potential memory leak.
Based on closed aio-libs/aiohttp issue #10535 · PR/commit linked
@@ -0,0 +1,3 @@
@@ -0,0 +1,3 @@
+Break cyclic references at connection close when there was a traceback -- by :user:`bdraco`.
+
+Special thanks to :user:`availov` for reporting the issue.
async def main():
app = web.Application()
app.router.add_get('/stream', stream_handler)
runner = web.AppRunner(app)
await runner.setup()
site = web.TCPSite(runner, 'localhost', 8080)
await site.start()
client = Client()
client_task = asyncio.create_task(client.fetch_stream('http://localhost:8080/stream'))
await client_task
del client
del client_task
await asyncio.sleep(0.5) # Allow time for cleanup
print(f'Garbage objects: {get_garbage()}')
await runner.cleanup()
Re-run the minimal reproduction on your broken version, then apply the fix and re-run.
Option A — Apply the official fix\nBreaks cyclic references at connection close when there was a traceback, addressing a potential memory leak.\nWhen NOT to use: This fix is not applicable if cyclic references are not the root cause of memory issues.\n\n
Why This Fix Works in Production
- Trigger: Memory Leak Due to Cyclic References in Traceback
- Mechanism: Cyclic references in traceback objects prevent garbage collection of ClientResponse
- If left unfixed, this can cause silent data inconsistencies that propagate (bad cache entries, incorrect downstream decisions).
Why This Breaks in Prod
- Cyclic references in traceback objects prevent garbage collection of ClientResponse
- Surfaces as: Memory Leak Due to Cyclic References in Traceback
Proof / Evidence
- GitHub issue: #10535
- Fix PR: https://github.com/aio-libs/aiohttp/pull/10556
- Reproduced locally: No (not executed)
- Last verified: 2026-02-09
- Confidence: 0.70
- Did this fix it?: Yes (upstream fix exists)
- Own content ratio: 0.58
Discussion
High-signal excerpts from the issue thread (symptoms, repros, edge-cases).
“It certainly wouldn't be the first time I've seen problems with exception traces holding on to references”
“It looks like the websocket has the same issue Moving the cleanup here also fixes the problem and likely covers all the cases”
“Even if I add del client and del client_task I can still reproduce the leak so maybe a true leak”
Failure Signature (Search String)
- Memory Leak Due to Cyclic References in Traceback
Error Message
Stack trace
Error Message
-------------
Memory Leak Due to Cyclic References in Traceback
Minimal Reproduction
async def main():
app = web.Application()
app.router.add_get('/stream', stream_handler)
runner = web.AppRunner(app)
await runner.setup()
site = web.TCPSite(runner, 'localhost', 8080)
await site.start()
client = Client()
client_task = asyncio.create_task(client.fetch_stream('http://localhost:8080/stream'))
await client_task
del client
del client_task
await asyncio.sleep(0.5) # Allow time for cleanup
print(f'Garbage objects: {get_garbage()}')
await runner.cleanup()
What Broke
Memory leak observed with lingering ClientResponse objects after disconnection.
Why It Broke
Cyclic references in traceback objects prevent garbage collection of ClientResponse
Fix Options (Details)
Option A — Apply the official fix
Breaks cyclic references at connection close when there was a traceback, addressing a potential memory leak.
Fix reference: https://github.com/aio-libs/aiohttp/pull/10556
Last verified: 2026-02-09. Validate in your environment.
When NOT to Use This Fix
- This fix is not applicable if cyclic references are not the root cause of memory issues.
Verify Fix
Re-run the minimal reproduction on your broken version, then apply the fix and re-run.
Did This Fix Work in Your Case?
Quick signal helps us prioritize which fixes to verify and improve.
Prevention
- Track RSS + object counts after deployments; alert on monotonic growth and GC pressure.
- Add a long-running test that repeats the failing call path and asserts stable memory.
Related Issues
No related fixes found.
Sources
We don’t republish the full GitHub discussion text. Use the links above for context.