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

> On Thu, Jan 4, 2018 at 6:09 PM, Guido van Rossum <gu...@python.org> wrote:
> > However you've not convinced me that it would be better to make Context
> > implement the full MutableMapping interface (with `__delitem__` always
> > raising). There are use cases for inspecting Context, e.g. a debugger
> that
> > wants to print the Context for some or all suspended tasks. But I don't
> see
> > a use case for mutating a Context object that's not the current context,
> and
> > when it is the current context, ContextVar.set() is more direct. I also
> > don't see use cases for other MutableMapping methods like pop() or
> update().
> > (And clear() falls under the same prohibition as __delitem__().)
>
> I was looking at this again, and I realized there's some confusion.
> I've been repeating the thing about not wanting to implement
> __delitem__ too, but actually, I think __delitem__ is not the problem
> :-).
>
> The problem is that we don't want to provide ContextVar.unset() --
> that's the operation that adds complication in a PEP 550 world. If you
> have a stack of Contexts that ContextVar.get() searches, and set/unset
> are only allowed to mutate the top entry in the stack, then the only
> way to implement unset() is to do something like
> context_stack[-1][self] = _MISSING, so it can hide any entries below
> it in the stack. This is extra complication for a feature that it's
> not clear anyone cares about. (And if it turns out people do care, we
> could add it later.)
>

Ah yes, that's it.

A stack of Contexts could have the same semantics as ChainMap, in which
__delitem__ deletes the key from the first mapping if present and otherwise
raises KeyError even if it is present in a later mapping.

That's enough to implement var.reset(), but not enough to implement
arbitrary var.unset().

I'm fine with only having var.reset() and not var.unset().


> Deleting entries from individual Context objects shouldn't create
> conceptual problems. OTOH I don't see how it's useful either. I don't
> think implementing MutableMapping would actually cause problems, but
> it's a bunch of extra code to write/test/maintain without any clear
> use cases.
>

The implementation would have to maintain cache consistency, but that's not
necessarily a big deal, and it only needs to be done in a few places.

But I agree that the a case hasn't been indicated yet. (I like being able
to specify ContextVar's behavior using Context as a MutableMapping, but
that's not a real use case.)


> 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
copy_context() would map to new_child()? 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.new_child(<dict>). (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.)

-- 
--Guido van Rossum (python.org/~guido)
_______________________________________________
Python-Dev mailing list
Python-Dev@python.org
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: 
https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com

Reply via email to