Cloud Run 中有很多“未捕获的信号:6”错误

Posted

技术标签:

【中文标题】Cloud Run 中有很多“未捕获的信号:6”错误【英文标题】:Lots of "Uncaught signal: 6" errors in Cloud Run 【发布时间】:2022-01-13 06:01:59 【问题描述】:

我在 GCP 中部署了一个 Python (3.x) 网络服务。每次 Cloud Run 关闭实例时,最明显的是在负载高峰之后,我会收到许多类似 Uncaught signal: 6, pid=6, tid=6, fault_addr=0.[CRITICAL] WORKER TIMEOUT (pid:6) 的日志,它们始终是信号 6。

该服务使用 FastAPI 和 Gunicorn 在 Docker 中通过此启动命令运行

CMD gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8080 app.__main__:app

服务使用 Terraform 部署,1 gig ram,2 cpu,超时设置为 2 分钟

resource "google_cloud_run_service" <ressource-name> 
  name     = <name>
  location = <location>

  template 
    spec 
      service_account_name = <sa-email>
      timeout_seconds = 120
      containers 
        image = var.image
        env 
          name = "GCP_PROJECT"
          value = var.project
        
        env 
          name = "BRANCH_NAME"
          value = var.branch
        
        resources 
          limits = 
            cpu = "2000m"
            memory = "1Gi"
          
        
      
    
  
  autogenerate_revision_name = true

我已经尝试在 Cloud Run 中调整资源和超时,使用 gunicorn 的 --timeout 和 --preload 标志,因为人们在谷歌搜索问题时似乎总是建议这样做,但都没有成功。我也不知道为什么工人超时。

【问题讨论】:

【参考方案1】:

扩展正确的最佳答案,您正在使用 GUnicorn,它是一个进程管理器,用于管理运行实际应用的 Uvicorn 进程。

当 Cloudrun 想要关闭实例时(可能是因为没有请求),它会发送一个信号 6 给进程 1。但是,GUnicorn 作为管理器占据了这个进程,不会将它传递给Uvicorn 工作人员进行处理 - 因此您会收到 未处理信号 6

最简单的解决方案是直接运行 Uvicorn 而不是通过 GUnicorn(可能使用较小的实例)并允许通过 Cloudrun 处理扩展部分。

CMD ["uvicorn", "app.__main__:app", "--host", "0.0.0.0", "--port", "8080"]

【讨论】:

这是一个有趣/有用的答案。 我自己在这个错误通知上苦苦挣扎了一段时间,直到深入研究它,当我测试向 fastapi / uvicorn 应用程序添加信号处理程序时,它什么也没做 - 直到我发现它是 GUnicorn 占用进程 1 而不是转发这个。本质上,我们使用 GUnicorn 进行扩展——通过 GUnicorn 提升 Uvicorn 进程同时处理多个请求。由于我们在 CloudRun 环境中并且可以将正在进行的请求设置为我们喜欢的任意数量,我们可以让 Uvicorn 处理他的请求,并从 Cloudrun 获得扩展。 感谢您的信息!虽然我已经用其他答案解决了我的问题,但我确信这是在互联网上流传的有用信息。【参考方案2】:

除非您启用了始终分配 CPU,否则后台线程和进程可能会在所有 HTTP 请求返回后停止接收 CPU 时间。这意味着后台线程和进程可能会失败,连接可能会超时等。除了设置 --cpu-no-throttling 标志外,我想不出使用 Cloud Run 运行后台工作人员有什么好处。可以终止未处理请求的 Cloud Run 实例。

信号 6 表示 abort 终止进程。这可能意味着您的容器由于缺少处理请求而被终止。

Run more workloads on Cloud Run with new CPU allocation controls

What if my application is doing background work outside of request processing?

【讨论】:

是否有一些关于如何运行 python web 服务的最佳实践?在谷歌文档中,他们也使用 guniorn 尽管参数略有不同。请参阅:cloud.google.com/run/docs/quickstarts/build-and-deploy/python 现在我复制了他们的论点(必须添加 -k 才能使 fastapi 工作),看看这是否可行 @JeremySchiemann 我指的是 Ahmet 的 Google Cloud Run 常见问题解答。 github.com/ahmetb/cloud-run-faq Cloud Run 基本上是一个简单的 HTTP 请求/响应系统。除此之外的大多数服务器设置都不是必需的。 谢谢,这对我帮助很大。仅使用一名工作人员并将超时设置为 0 已经为我修复了它。但常见问题解答将被收藏!

以上是关于Cloud Run 中有很多“未捕获的信号:6”错误的主要内容,如果未能解决你的问题,请参考以下文章

docker run报错

我可以为 Terraform for GCP 赋予管理员角色吗? (Cloud Run 域映射示例)

Terraform:Cloud Run 服务上的 Cloud Endpoints?

Spring Cloud Gateway 动态修改请求参数解决 # URL 编码错误传参问题

Cloud Run 完全托管连接到 Cloud SQL:这是不是支持 SQL Server?

将 Cloud Armor 与 Cloud Run 结合使用并避免绕过