python-3.x - 如何让 celery worker 停止接收新任务(Kubernetes)

标签 python-3.x kubernetes celery django-celery celery-task

所以我们有一个 kubernetes 集群运行一些带有 celery worker 的 pod。我们正在使用 python3.6 来运行这些 worker,celery 版本是 3.1.2(我知道,真的很旧,我们正在努力升级它)。我们还设置了一些自动缩放机制来动态添加更多的 celery worker。

问题如下。所以假设我们在任何给定时间都有 5 名 worker 。然后很多任务来了,增加了 pod 的 CPU/RAM 使用率。这会触发自动缩放事件,比方说,再添加两个 celery worker pod。所以现在这两个新的 celery worker 承担了一些长时间运行的任务。在他们完成运行这些任务之前,kubernetes 创建了一个缩减事件,杀死了这两个 worker,并杀死了那些长时间运行的任务。

此外,由于遗留原因,如果任务未完成,我们没有重试机制(我们现在无法实现)。

所以我的问题是,有没有办法告诉 kubernetes 等待 celery worker 运行完所有待处理的任务?我想解决方案必须包括一些方法来通知 celery worker 使其也停止接收新任务。现在我知道 Kubernetes 有一些脚本来处理这种情况,但我不知道在这些脚本上写什么,因为我不知道如何让 celery worker 停止接收任务。

有什么想法吗?

最佳答案

我写了一个blog post正是关于那个主题 - 检查一下。

当 Kubernetes 决定终止一个 pod 时,它首先发送 SIGTERM 信号,这样您的应用程序就有时间正常关闭,之后如果您的应用程序没有结束 - Kubernetes 将通过发送 SIGKILL 信号终止它。

这段时间,从 SIGTERM 到 SIGKILL 可以通过 terminationGracePeriodSeconds 进行调整(更多信息 here)。

换句话说,如果最长的任务需要 5 分钟,请确保将此值设置为高于 300 秒的值。

Celery 为您处理这些信号,如您所见here (我想这也与您的版本相关):

应使用 TERM 信号完成关机。

When shutdown is initiated the worker will finish all currently executing tasks before it actually terminates. If these tasks are important, you should wait for it to finish before doing anything drastic, like sending the KILL signal.

如文档中所述,您可以设置 acks_late=True configuration因此,如果意外停止,任务将再次运行。

我没有找到文档的另一件事(几乎可以肯定我在某个地方看到过) - Celery worker 在获得 SIGTERM 后不会收到新任务 - 所以你应该安全地终止 worker(可能需要设置worker_prefetch_multiplier = 1)。

关于python-3.x - 如何让 celery worker 停止接收新任务(Kubernetes),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73204089/

相关文章:

node.js - 在我的Windows主机文件中添加LB IP后,无法连接使用浏览器上的ingress-nginx生成的Google Cloud Load Balancer

kubernetes - 将数据导入 Neo4j Kubernetes 集群

python - Celery link_error 引发 NotRegistered 异常

python - 如何在 python 3.6 中加载在 python 3.5 上训练的机器学习模型?

python-3.x - 预期整数类型 : Python 3. 5 类型提示和 Pycharm

python-3.x - ImportError : Please install apex from https://www. github.com/nvidia/apex 使用分布式和 fp16 训练

kubernetes - TLS引导(--token-auth-file),用户 “system:anonymous”无法创建证书签名请求

node.js - Node.js 项目的 Dockerfile 中的 Python 库

python - 如何在其他(已经启动的)任务完成后运行任务

python - 如果未指定,默认的 Celery 日志级别是多少?