
I know I'm not the only one who is confused by at least some of the alternative terminology choices. I suspect I'm not the only one who sometimes missed part of the argument because I was distracted figuring out what the objects were, and forgot to verify what was being done and why. I also suspect that it could be much simpler to follow if the API were designed in the abstract, with the implementation left for later. So is the following API missing anything important? (1) Get the current (writable) context. Currently proposed as a sys.* call, but I think injecting to __builtins__ or globals would work as well. (2) Get a value from the current context, by string key. Currently proposed as key.get, rather env.__getitem__ (3) Write a value to the current context, by string key. Currently proposed as key.set, rather env.__setitem__ (4) Create a new (writable) empty context. (5) Create a copy of the current context, so that changes can be isolated. The copy will not be able to change anything in the current context, though it can shadow keys. (6) Choose which context to use when calling another function/generator/iterator/etc/ At this point, it looks an awful lot like a subset of ChainMap, except that: (A) The current mapping is available through a series of sys.* calls. (why not a builtin? Or at least a global, injected when a different environment is needed?) (B) Concurrency APIs are supposed to ensure that each process/thread/Task/worker is using its own private context, unless the call explicitly requests a shared or otherwise different context. (C) The current API requires users to initialize every key before it can be added to a context. This is presumably to support limits of the proposed implementation. If the semantics are right, and collections.ChainMap is rejected only for efficiency, please say so in the PEP. If the semantics are wrong, please explain how they differ. Sample code: olduser=env["username"] env["reason"] = "Spanish Inquisition" with env.copy(): env["username"] = "secret admin" foo() print ("debugging", env["foodebug"]) bar() with env.empty(): assert "username" not in env assert env["username"] is olduser -jJ