如何在 Jupyter Notebook 中使用 django 3.0 ORM 而不会触发异步上下文检查?

Posted

技术标签:

【中文标题】如何在 Jupyter Notebook 中使用 django 3.0 ORM 而不会触发异步上下文检查?【英文标题】:How to use django 3.0 ORM in a Jupyter Notebook without triggering the async context check? 【发布时间】:2019-11-30 19:15:03 【问题描述】:

Django 3.0 正在添加asgi / async support and with it a guard around making synchronous requests in an async context。同时,IPython just added top level async/await support,它似乎在默认事件循环内运行整个解释器会话。

不幸的是,这两个伟大的加法相结合意味着 jupyter notebook 中的任何 django ORM 操作都会导致 SynchronousOnlyOperation 异常:

SynchronousOnlyOperation: You cannot call this from an async context - use a thread or sync_to_async.

正如异常消息所说,可以将每个 ORM 调用包装在 sync_to_async() 中,例如:

images = await sync_to_async(Image.objects.all)()

但这不是很方便,特别是对于通常会在属性查找时隐式解析的相关字段。

(我尝试了%autoawait off 魔术,但它不起作用,快速浏览the docs 我假设这是因为 ipykernels 总是在 asyncio 循环中运行)

那么有没有办法在 django 中禁用异步上下文检查中的同步或在同步上下文中运行 ipykernel?


对于上下文:我编写了一个数据科学包,它使用 django 作为后端服务器,但还在 ORM 之上公开了一个基于 jupyter 的接口,允许您清理/注释数据、跟踪机器学习实验和运行训练作业一个 jupyter 笔记本。

【问题讨论】:

【参考方案1】:

对我有用

os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"

顺便说一句,我使用命令启动我的笔记本

./manage.py shell_plus --notebook

【讨论】:

我试过这个。它仍然显示 jupyter 中的错误。我应该把os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true"放在哪里。我在 jupyter 内部尝试过,还添加到 settings.py 中。但是我的 jupyter 仍然出错 我放在笔记本里 也为我工作。只需将其添加到 settings.py 并在笔记本上运行 shell_plus 在我将 Django 从 3.0.0 更新到 3.0.6 之前,这个解决方案没有给我结果。 @dmmfll,我在 3.0,它根本不工作。然后看到你的评论,升级到 3.0.6 现在可以使用了,谢谢【参考方案2】:

与其他答案相反,我建议从 shell 运行:

env DJANGO_ALLOW_ASYNC_UNSAFE=true ./manage.py shell_plus --notebook

并且不修改任何配置文件或启动脚本。

这样做的好处是这些检查似乎仍然有用,几乎在其他任何地方都启用(例如,通过runserver 在本地调试或运行测试时)。通过文件禁用很容易在太多地方禁用它们,从而否定它们的优势。

请注意,大多数 shell 都提供了调用以前调用的命令行的简单方法,例如在 Bash 或 Zsh 中 Ctrl+R 后跟 notebook 会找到你最后一次运行包含“笔记本”的东西。在鱼壳下只需输入 notebook 并按向上箭头键开始反向搜索。

【讨论】:

【参考方案3】:

现在我打算只使用forked version of django with a new setting to skip the async_unsafe check。一旦 ORM 获得异步支持,我可能不得不重写我的项目以支持它并删除标志。

编辑:现在有一个 PR 可以添加一个 env 变量 (DJANGO_ALLOW_ASYNC_UNSAFE) 以禁用检查 (https://github.com/django/django/pull/12172)

【讨论】:

此更改现在计划用于3.0.1【参考方案4】:

我加了

os.environ["DJANGO_ALLOW_ASYNC_UNSAFE"] = "true" 代码在您项目的 setting.py 中一直到文件,然后

命令python3 manage.py shell_plus --notebook

如果你用的是python3还是用python

就是这样。为我工作。

【讨论】:

以上是关于如何在 Jupyter Notebook 中使用 django 3.0 ORM 而不会触发异步上下文检查?的主要内容,如果未能解决你的问题,请参考以下文章

如何修改jupyter notebook的默认工作路径

如何修改jupyter notebook的默认工作路径

如何在 Jupyter Notebook 中显示文件中的图像?

如何在别的电脑打开 jupyter notebook

在使用 jupyter notebook 时如何在 pandas 中使用 Dataframe 时查看完整数据? [复制]

如何在 Jupyter Notebook 中使用 Python 库调试错误