[Python-Dev] PEP 550 v4

Yury Selivanov yselivanov.ml at gmail.com
Tue Aug 29 18:01:40 EDT 2017


On Tue, Aug 29, 2017 at 5:45 PM, Greg Ewing <greg.ewing at canterbury.ac.nz> wrote:
[..]
> What you seem to be suggesting is that generators shouldn't
> leak context changes even when you *don't* use a with-statement.

Yes, generators shouldn't leak context changes regardless of what and
how changes the context inside them:

  var = new_context_var()

  def gen():
       old_val = var.get()
       try:
            var.set('blah')
            yield
            yield
            yield
       finally:
          var.set(old_val)

with the above code, when you do "next(gen())" it would leak the state
without PEP 550.  "finally" block (or "with" block wouldn't help you
here) and corrupt the state of the caller.

That's the problem the PEP fixes.  The EC interaction with generators
is explained here with a great detail:
https://www.python.org/dev/peps/pep-0550/#id4

We explain the motivation behind desiring a working context-local
solution for generators in the Rationale section:
https://www.python.org/dev/peps/pep-0550/#rationale

Basically half of the PEP is about isolating context in generators.

> If you're going to to that, you'd better make sure that the
> same thing applies to regular functions, otherwise you've
> introduced an inconsistency.

Regular functions cannot pause/resume their execution, so they can't
leak an inconsistent context change due to out of order or partial
execution.

PEP 550 positions itself as a replacement for TLS, and clearly defines
its semantics for regular functions in a single thread, regular
functions in multithreaded code, generators, and asynchronous code
(async/await).  Everything is specified in the High-level
Specification section.  I wouldn't call slightly differently defined
semantics for generators/coroutines/functions an "inconsistency" --
they just have a different EC semantics given how different they are
from each other.

Drawing a parallel between 'yield from' and function calls is
possible, but we shouldn't forget that you can 'yield from' a
half-iterated generator.

Yury


More information about the Python-Dev mailing list