requests: Add context manager for response object.#1121
Conversation
Signed-off-by: Phil Howard <github@gadgetoid.com>
| def __enter__(self): | ||
| return self | ||
|
|
||
| def __exit__(self, exc_type, exc_val, exc_tb): |
There was a problem hiding this comment.
A bit of a controversial take, but replacing the non-self arguments list with a single *_ saves 28 bytes.
I'd say it's safe to assume that a context manager will always pass the correct arguments to __exit__, although that way will look quite uglier than what you initially wrote :)
There was a problem hiding this comment.
A bit of a controversial take, but replacing the non-self arguments list with a single *_ saves 28 bytes.
I did a quick search of the codebase and picked the most common pattern. I did see *args and my personal preference would probably be _type, _value, _traceback to both flag as unused and keep it unambiguous 😆
Might not hurt to get some consensus on this and raise a PR to make every __exit__ in micropython-lib look the same.
Summary
When accessing
response.rawit's not always obvious you should callresponse.close()to close and free the socket. Since lwIP has a five socket limit by default this can very quickly result in cryptic ENOMEM errors.A context manager is widely understood to handle freeing resources on exit and permits the following, Pythonic pattern without leaking open sockets:
While I came up with this idea and wrote this code independently , this PR transpired to be partially a dupe of #278 but I have excluded the iteration features in favour of a clean, concise change in the hope it would be easier to consider.
Testing
This is a minor change adding well understood magic methods, I did a cursory check to make sure it would work.
Trade-offs and Alternatives
This is a very minor change for a lot of potential utility, though without associated documentation changes it's unlikely to receive adoption.
CPython's "requests" library has the concept of a
Session, which includes a context manager at a lower level, and implements get/post etc using a transient Session. This is a potentially useful concept in MicroPython because the time cost of re-opening a socket when TLS is involved is prohibitive - 300-400ms. I'm currently using a completely custom HTTP library to avoid this.This change also has some minor functional overlap with
urllib urequest'surlopenwhich is sometimes favoured for streaming requests.Generative AI
I did not use generative AI tools when creating this PR.