Network code owns a resource, not just a returned value. A socket-backed response must close after success, oversized input, decoding failure or cancellation. Put the read inside a context manager so ownership is visible.
Hosted exercises use a supplied transport callable that returns a fake response with status, getheaders(), read(n) and context-manager methods. The downloadable adapter uses a real HTTP connection to the local fixture server. Both satisfy the same boundary.
Reading everything and checking its length afterward does not bound the read. Reading exactly the limit can silently hide truncation. Request limit + 1, then accept only lengths at most limit. The returned bytes remain undecoded until the next lesson.
The supplied wrapper validates finite positive timeouts and integer byte limits before effects. A Boolean is not accepted as an integer limit even though bool subclasses int in Python.
limit = 4
for body in [b"", b"abcd", b"abcde", b"abcdefgh"]:
probe = body[:limit+1]
print("read", len(probe), "accepted", len(probe) <= limit)Be precise about time. Our timeout is passed to supported blocking socket operations. It is not an overall wall-clock deadline: several operations or repeated trickling reads can take longer. The later retry wait budget bounds deliberate sleeps, not all network runtime. These are separate limits.
The accepted body cap also does not independently prove peak process memory; the transport and parser have allocations of their own. In this small lab, the standard HTTP parser and a bounded read keep the teaching boundary practical without claiming a universal network hardening layer.
The wrapper maps timeout and transport errors to fixed ClientError codes instead of copying raw exception messages or headers into output. Tests inspect exact read size, timeout forwarding and cleanup effects, which catch bugs that a returned-value-only test would miss.
closed=[]
class Response:
def __enter__(self): return self
def __exit__(self,*args): closed.append(True)
try:
with Response():
raise ValueError("oversize")
except ValueError:
print("error handled")
print("closed", closed)Implement the bounded read. Test an exact-limit body, a one-byte overflow, an empty body, a non-byte fake and an exception during reading. Every acquired response must close.
Next we decide whether these bounded bytes are the successful JSON page the application actually requested.