Skip to content

Do a better job of communicating the problems with using nurseries/cancel scopes inside generators #638

Open
@miracle2k

Description

@miracle2k

I am aware of the issues with cleaning up async iterators, PEP 533 and the need for aclosing. However, if a closing is not used, which I overlook frequently, things can really blow up in your face:

import trio

async def gen_with_task():
    async with trio.open_nursery() as n:
        n.start_soon(trio.sleep_forever)
        while True:
            await trio.sleep(1)
            yield 1

async def main():
    async for f in gen_with_task():
        raise ValueError()

trio.run(main)

gives me:

Exception ignored in: <async_generator object gen_with_task at 0x10c7857b8>
RuntimeError: async generator ignored GeneratorExit
Traceback (most recent call last):
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 1229, in run
    result = run_impl(runner, async_fn, args)
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 1357, in run_impl
    runner.task_exited(task, final_result)
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 852, in task_exited
    self.tasks.remove(task)
KeyError: <Task '__main__.main' at 0x10c72c668>

The above exception was the direct cause of the following exception:

Traceback (most recent call last):
  File "triotest.py", line 14, in <module>
    trio.run(main)
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 1235, in run
    ) from exc
trio.TrioInternalError: internal error in trio - please file a bug!
Exception ignored in: <coroutine object _AsyncGeneratorContextManager.__aexit__ at 0x10c78f648>
Traceback (most recent call last):
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_util.py", line 84, in __aexit__
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_util.py", line 14, in __aexit__
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_impl.py", line 308, in aclose
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_impl.py", line 277, in athrow
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_impl.py", line 290, in _do_it
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_impl.py", line 197, in __next__
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/async_generator/_impl.py", line 209, in _invoke
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 311, in open_nursery
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/contextlib.py", line 130, in __exit__
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 198, in open_cancel_scope
  File "/Users/michael/.pyenv/versions/3.7.0/lib/python3.7/site-packages/trio/_core/_run.py", line 157, in _remove_task
KeyError: <Task '__main__.main' at 0x10c72c668>

Note that in addition to the internal trio exceptions, the original cause is not shown at all. This happens when the async generator had a task running in a nursery.

Maybe there is no way to handle this better - I can't tell, this is above my paygrade! But in case there is a way to show a clearer error message, I think it might be worth it.

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions