[Python-Dev] PEP 567 v2 (original) (raw)

Nathaniel Smith njs at pobox.com
Tue Jan 9 02🔞01 EST 2018


On Thu, Jan 4, 2018 at 9:42 PM, Guido van Rossum <guido at python.org> wrote:

On Thu, Jan 4, 2018 at 7:58 PM, Nathaniel Smith <njs at pobox.com> wrote:

This does make me think that I should write up a short PEP for extending PEP 567 to add context lookup, PEP 550 style: it can start out in Status: deferred and then we can debate it properly before 3.8, but at least having the roadmap written down now would make it easier to catch these details. (And it might also help address Paul's reasonable complaint about "unstated requirements".) Anything that will help us kill a 550-pound gorilla sounds good to me. :-) It might indeed be pretty short if we follow the lead of ChainMap (even using a different API than MutableMapping to mutate it). Maybe copycontext() would map to newchild()? Using ChainMap as a model we might even avoid the confusion between Lo[gi]calContext and ExecutionContext which was the nail in PEP 550's coffin. The LC associated with a generator in PEP 550 would be akin to a loose dict which can be pushed on top of a ChainMap using cm = cm.newchild(). (Always taking for granted that instead of an actual dict we'd use some specialized mutable object implementing the Mapping protocol and a custom mutation protocol so it can maintain ContextVar cache consistency.)

The approach I took in PEP 568 is even simpler, I think. The PEP is a few pages long because I wanted to be exhaustive to make sure we weren't missing any details, but the tl;dr is: The ChainMap lives entirely inside the threadstate, so there's no need to create a LC/EC distinction -- users just see Contexts, or there's the one stack introspection API, get_context_stack(), which returns a List[Context]. Instead of messing with new_child, copy_context is just Context(dict(chain_map)) -- i.e., it creates a flattened copy of the current mapping. (If we used new_child, then we'd have to have a way to return a ChainMap, reintroducing the LC/EC mess. Plus it would allow for changes to the Context's inside one ChainMap to "leak" into the child or vice-versa.) And Context push/pop is just push/pop on the threadstate's ChainMap's '.maps' attribute.

-n

-- Nathaniel J. Smith -- https://vorpus.org



More information about the Python-Dev mailing list