You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flask使用AsyncHTMLSession报错signal only works in main thread咨询

问题修复方案

错误根本原因

  • 报错来自requests-html依赖的底层渲染库pyppeteer:pyppeteer初始化时会默认尝试注册SIGINT信号处理逻辑,而信号操作仅允许在主解释器的主线程中执行
  • Flask 2.0+的异步视图默认运行在子线程/子解释器上下文中,不满足信号操作的权限要求,单独运行爬取脚本时是在主线程执行,因此不会触发报错
  • Windows系统本身对POSIX信号的支持存在天然缺陷,进一步放大了该问题

无需引入任务队列的直接修复方案

方案1:禁用pyppeteer信号注册(优先推荐)

arender()方法支持透传参数给底层的pyppeteer启动方法,直接添加handle_sigint=False参数即可关闭信号注册逻辑,代码修改如下:

# 原代码
await r.html.arender(你的原有参数)
# 修改后代码
await r.html.arender(handle_sigint=False, 你的原有参数)

该方案对原有业务逻辑侵入最小,Windows环境下直接生效。

方案2:调整Flask运行模式(适合开发测试场景)

如果方案1不生效,可调整ASGI服务器的运行配置,让所有请求逻辑都运行在主解释器的主线程中:

  • 若使用uvicorn启动Flask,执行命令:uvicorn 你的启动文件:app --workers 1 --threads 1
  • 若使用werkzeug开发服务器,启动时添加参数:app.run(threaded=False)
    注意该方案会降低服务并发能力,仅适合并发量低的小型场景使用。

什么时候需要引入任务队列

如果满足以下任意场景,才建议引入Celery、RQ等任务队列组件:

  • 单次爬取任务耗时超过30秒,会导致HTTP请求超时
  • 存在多用户同时触发爬取的高并发需求
  • 需要支持爬取进度查询、失败重试等高级特性
    如果只是低频次、短耗时的爬取需求,上述两种修复方案完全可以满足需求,不需要额外引入任务队列增加架构复杂度。

内容的提问来源于stack exchange,提问作者PythonJohn

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.02 21:57:04