我使用 MongoDB 和 Motor.Asyncio 创建了一个带有 Quart 的 webapp。当应用程序尝试查询数据库时,会引发错误:
Task <Task pending coro=<ASGIHTTPConnection.handle_request()
running at /home/user/.local/lib/python3.7/site-packages/quart
/asgi.py:59> cb=[_wait.<locals>._on_completion() at /usr/lib/python3.7
/asyncio/tasks.py:440]> got Future <Future pending cb=[run_on_executor.
<locals>._call_check_cancel() at /home/user/.local/lib/python3.7/site-
packages/motor/frameworks/asyncio/__init__.py:80]> attached to a
different loop
我不明白为什么会发生这种情况,也不知道如何解决。
该应用程序一直运行没有问题,但我决定从 Python 3.6(在 Ubuntu-18.04 上)升级到 python 3.7.1。有了这个,我将 Quart 升级到 0.9.0。由于此升级,发生了上述错误。
该应用程序使用 Hypercorn 和 Nginx 从命令行运行。
在这种情况下,我不确定我的代码的哪些部分是相关的
我先导入 Quart,然后再导入 Motor:
# Mongodb / Gridfs with Motor
import motor.motor_asyncio
from pymongo import ReturnDocument
from bson.objectid import ObjectId
from bson.son import SON
client = motor.motor_asyncio.AsyncIOMotorClient()
db = client.myDataBase
fs = motor.motor_asyncio.AsyncIOMotorGridFSBucket(db)
在此之后,我添加:
app = Quart(__name__)
我试过在电机导入块之前移动它,它没有改变任何东西。
正如问题/答案中所建议的: RuntimeError: Task attach to a different loop 我添加了:
loop=asyncio.new_event_loop()
asyncio.set_event_loop(loop)
client = motor.motor_asyncio.AsyncIOMotorClient(io_loop=loop)
那并没有解决它。
这是第一次调用电机的块,错误发生的地方:
try:
session_info = await db.sessions.find_one(
{
'session_id': uuid.UUID(session_id)
},
{
'username':True,
'_id':False
}
)
except Exception as e:
print('error retrieving session info:', e)
我可以忽略错误并继续,但随后进行下一次调用并发生相同的错误。
我知道 Quart 在默认的 event_loop 上工作,应该不需要为电机创建一个特殊的循环。它在以前的版本中没有它的工作。所以我完全不知所措。