Why can't I 'yield from' inside an async function?

Question:

In Python 3.6, I am able to use yield inside a coroutine. However I am not able to use yield from.

Below is my code. On line 3 I await another coroutine. On line 4 I try to yield from a file. Why won’t Python 3.6 allow me to do that?

async def read_file(self, filename):
    with tempfile.NamedTemporaryFile(mode='r', delete=True, dir='/tmp', prefix='sftp') as tmp_file:
        await self.copy_file(filename, tmp_file)
        yield from open(tmp_file)

Here’s the exception Python 3.6 raises for the above code:

  File "example.py", line 4
    yield from open(tmp_file)
    ^
SyntaxError: 'yield from' inside async function
Asked By: Akilesh

||

Answers:

According to PEP 525, which introduces asyncronous generators in Python 3.6:

Asynchronous yield from

While it is theoretically possible to implement yield from support for
asynchronous generators, it would require a serious redesign of the
generators implementation.

yield from is also less critical for asynchronous generators, since
there is no need provide a mechanism of implementing another
coroutines protocol on top of coroutines. And to compose asynchronous
generators a simple async for loop can be used:

async def g1():
    yield 1
    yield 2

async def g2():
    async for v in g1():
        yield v

As you can see, the answer boils down to “it would be too hard to implement, and you don’t need it anyway”.

Answered By: Zero Piraeus