Runnable example
Async batch fetcher with bounded concurrency
Implement a resilient async batcher with Semaphore concurrency control, exponential backoff for transient failures, and per-item error isolation.
The problem
Unbounded asyncio.gather concurrency leads to socket exhaustion, 429 rate limiting, and cascading server failures. A production batch fetcher must bound concurrency, retry transient failures, fail fast on permanent errors, and keep one bad item from crashing the batch.
The contract
- Bound concurrent requests with asyncio.Semaphore instead of unbounded gather.
- Retry transient failures — 429, 503, timeouts — with bounded exponential backoff.
- Fail fast on permanent errors such as 400 and 404 without retrying them.
- Isolate per-item failures and return structured success and error records.
Verify it locally
From the root of the FlyPython repository, reproduce the broken starter first, then verify the reviewed solution:
python examples/async-fetcher/verify.py starter --expect-failurepython examples/async-fetcher/verify.py solutionHand it to a coding agent
- Clone the repository and reproduce the starter failure with the command above.
- Give the task contract ↗ to your coding agent and allow changes only in
starter/fetcher.py. - Run
python examples/async-fetcher/verify.py starterand treat any failure as unfinished work. - Compare the patch with the reference solution ↗ — the goal is the same contract with a small, readable diff, not identical syntax.
Keep going
Where this example sits in the roadmap.
Reviewed 2026-09-02 · Repository content version 1. Continue with the related learning path, the repository directory, or the MCP migration guide for the specification background.