【问题标题】:RuntimeError: Event loop is closed in asyncpraw pythonRuntimeError:事件循环在 asyncpraw python 中关闭
【发布时间】:2021-02-28 18:17:59
【问题描述】:

我正在尝试使用 asyncpraw 库,但我得到了 RuntimeError: Event loop is closed

这是我的代码和回溯。

代码

import asyncio
import asyncpraw

async def main():
    reddit = asyncpraw.Reddit('praw_ini_name')
    print('User is', await reddit.user.me())
    await reddit.close()

asyncio.run(main())

追溯

User is python_user
Exception ignored in: <function _ProactorBasePipeTransport.__del__ at 0x0000021D2898C1F0>
Traceback (most recent call last):
  File "C:\Program Files\Python39\lib\asyncio\proactor_events.py", line 116, in __del__
    self.close()
  File "C:\Program Files\Python39\lib\asyncio\proactor_events.py", line 108, in close
    self._loop.call_soon(self._call_connection_lost, None)
  File "C:\Program Files\Python39\lib\asyncio\base_events.py", line 746, in call_soon
    self._check_closed()
  File "C:\Program Files\Python39\lib\asyncio\base_events.py", line 510, in _check_closed
    raise RuntimeError('Event loop is closed')
RuntimeError: Event loop is closed

但是,如果我像这样启动事件循环,这不会发生(没有例外)

import asyncio
import asyncpraw

async def main():
    reddit = asyncpraw.Reddit('praw_ini_name')
    print('User is', await reddit.user.me())
    await reddit.close()

loop = asyncio.get_event_loop()
loop.run_until_complete(main())

我假设在较新的 python 版本中,启动事件循环的首选方式是我在第一个 sn-p 中展示的方式,那么为什么这不起作用?即使它打印输出,为什么我的代码会抛出异常?

我在 Python 3.9.2 上,asyncpraw 7.2.0。

我见过Asyncio Event Loop is ClosedPython3.x RuntimeError: Event loop is closedAiohttp, Asyncio: RuntimeError: Event loop is closed,我相信他们不是骗子。我的问题是为什么它适用于一个而不是另一个。

如果我不使用reddit.close(),我会得到以下信息

User is python_user
Unclosed client session
client_session: <aiohttp.client.ClientSession object at 0x0000025BAAAEF8B0>
Unclosed connector
connections: ['[(<aiohttp.client_proto.ResponseHandler object at 0x0000025BAAAF1640>, 174448.968)]']
connector: <aiohttp.connector.TCPConnector object at 0x0000025BAAAEFA90>

谢谢。

【问题讨论】:

    标签: python python-asyncio praw asyncpraw


    【解决方案1】:

    asyncio.run 明确地在完成时关闭循环。

    asyncio.run(coro, *, debug=False)

    [...]
    这个函数总是创建一个新的事件循环并在最后关闭它。

    这意味着一旦main 完成,事件循环就可用于清理。必须改为通过async generators 或同步进行确定性清理。

    当手动管理循环而不调用loop.close() 时,循环仍然可用于安排清理回调。请注意,这并不一定意味着清理实际上是运行,除非循环被显式恢复。


    具体问题是known issue with aiohttp 3.x

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-08-15
      • 1970-01-01
      • 2022-10-06
      • 1970-01-01
      • 2019-01-04
      • 1970-01-01
      • 2022-07-15
      相关资源
      最近更新 更多