[Python-ideas] async/await in Python

Andrew Barnert abarnert at yahoo.com
Sun Apr 19 04:27:15 CEST 2015


On Apr 18, 2015, at 10:39, Yury Selivanov <yselivanov.ml at gmail.com> wrote:
> 
> Hi Steven,
> 
>> On 2015-04-18 1:11 PM, Steven D'Aprano wrote:
>> Nicely written and very complete! I only have a couple of little
>> niggles, which some might consider bike-shedding. See below.
> 
> Thanks a lot!
> 
>> 
>> 
>> On Fri, Apr 17, 2015 at 02:58:58PM -0400, Yury Selivanov wrote:
>> 
>> [...]
>>> From this point in this document we use the word *coroutine* to refer to
>>> functions declared using the new syntax.  *generator-based coroutine* is
>>> used where necessary to refer to coroutines that are based on
>>> generator syntax.
>> It concerns me that we will have two kinds of coroutines.
>> 
>> At the moment, we have two kinds of generator functions: those that are
>> used as generators, and those that are used as coroutines, depending on
>> whether they contain "yield expr" or "x = (yield expr)". That
>> distinction won't go away, but now we will have even more ambiguity of
>> language: there will be generators which are functions:
>> 
>>     def gen(): yield 1
>> 
>> generators which are not functions but the result of calling a generator
>> function:
>> 
>>     g = gen()
>> 
>> coroutines which are generators:
>> 
>>     def gen():
>>         x = (yield 1)
>>         y = (yield x+1)
>> 
>>     cr = gen()
>> 
>> and coroutines which are not generators:
>> 
>>     async def g():
>>         await spam()
>> 
>> Except that they will be implemented internally as generators. There
>> will be generators that use yield and generators which give a syntax
>> error with yield. My head hurts :-)
>> 
>> I think it will be hard to unambiguously talk about these things without
>> confusion, especially for people with limited asyncronous experience.
>> 
>> I don't have an answer to this, but I know that even the generator
>> versus generator-function ambiguity (both get called "generator")
>> sometimes leads to confusion. (E.g. below you talk about passing a
>> generator to types.async_def but it isn't clear to me whether you mean
>> the generator or the generator function.) There's been at least one
>> thread on python-list in the last few months about that. Is it possible
>> to use another name to distinguish generator-based coroutines from
>> async-based coroutines?
>> 
>> It's a pity we can't steal the name "goroutine" from Go. I've always
>> liked that name :-) but as I understand it, goroutines completely
>> unrelated to coroutines. Hmmm... maybe we could use pyroutines? *wink*
>> 
>> If the name must stay as-is, it would help to have an unambigous and
>> clear summary of the various generator-or-coroutine uses and how they
>> differ.
> 
> The PEP kind of addresses this, but calling current approach
> to do coroutines "generator-based coroutines", and the new
> ones as just "coroutines".

The only problem is that, when it's important to specify that you mean the new kind of coroutines explicitly, there's no obvious way to do so--if I say "async coroutines" someone may reasonably think I'm referring to "coroutines as user in asyncio".

I could say "PEP XXX coroutines" or "awaitable coroutines" or "non-yield-from coroutines" or probably various other things, but none of them are the first thing that comes to mind.

It definitely seems plausible that eventually the ambiguity will vanish, as nobody will talk about the other kind of coroutines except as an implementation detail for backporting code to 3.3/3.4 (which will itself probably not be common for that long) or porting the feature itself to other implementations. 

But it might be nice to have an official name that can be used when necessary until that happens. (I don't know what that name should be.)

> The internal implementation based on generators is something
> that was absolutely required to cover in the PEP in a great detail,
> but almost everybody will forget about that fact pretty soon.
> 
> The point of this PEP is to actually avoid any confusion, and
> to just have two separate concepts: coroutines and generators
> (the latter can still be used as a "coroutine-like" object,
> but hopefully nobody will do that at some point).
> 
>> 
>> 
>>> types.async_def()
>>> -----------------
>>> 
>>> A new function ``async_def(gen)`` is added to the ``types`` module. It
>>> applies ``CO_ASYNC`` flag to the passed generator's code object, so that it
>>> returns a *coroutine object* when called.
>>> 
>>> This feature enables an easy upgrade path for existing libraries.
>> When you say "the passed generator", do you mean the generator function or the generator object?
>> E.g. given:
>> 
>> def gen():
>>     yield 1
>> 
>> which do I use? async_def(gen()) or async_def(gen)?
> 
> It's generator-function.  It's a very good catch.
> 
> I've updated the PEP.
> 
> 
> Thanks!
> Yury
> _______________________________________________
> Python-ideas mailing list
> Python-ideas at python.org
> https://mail.python.org/mailman/listinfo/python-ideas
> Code of Conduct: http://python.org/psf/codeofconduct/


More information about the Python-ideas mailing list