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

Docker Compose中Celery Worker接收SIGINT时能否优雅终止运行任务?

优雅终止Docker Compose中Celery任务的可行方案

以下是经过实践验证的几种方案,结合起来可以实现docker compose down时Celery任务的优雅终止:

1. 配置Celery Worker的超时参数

启动Celery Worker时,通过--soft-time-limit和--time-limit参数控制任务终止的时机:

celery -A your_project worker --loglevel=info --soft-time-limit=300 --time-limit=360
  • --soft-time-limit=300:给正在运行的任务300秒缓冲时间,任务收到终止信号后需在此时限内完成或主动退出
  • --time-limit=360:设置任务最大运行时长,超时后会被强制终止

2. 调整Docker Compose的停止等待时长

在docker-compose.yml中为Celery服务配置stop_grace_period,确保Docker等待足够时间让Celery处理完正在运行的任务:

services:
  celery_worker:
    build: .
    command: celery -A your_project worker --loglevel=info --soft-time-limit=300 --time-limit=360
    stop_grace_period: 6m  # 时长需大于time-limit,留足缓冲
    # 其他配置(如环境变量、依赖服务等)

默认情况下Docker仅等待10秒,设置更长的优雅停止周期可避免容器被强制杀死。

3. 给任务添加优雅退出逻辑

对于长时间运行的任务,可在代码中主动检查终止信号,执行必要清理操作后退出:

from celery import current_task

def long_running_task():
    for progress_step in range(100):
        # 检查是否收到终止通知
        if current_task.request.is_shutdown:
            # 执行清理:保存进度、关闭连接等
            save_task_progress(progress_step)
            close_external_connections()
            break
        # 执行任务核心逻辑
        execute_task_step(progress_step)

这样能避免任务被强制中断时出现数据丢失或资源泄漏。

4. 确保Celery Worker是容器的PID 1进程

如果通过shell脚本启动Celery,要避免shell成为PID 1(会导致信号无法正确传递给Celery):

  • 直接用Celery命令作为Docker服务的command,不要用bash -c包裹
  • 若必须用脚本启动,在脚本中使用exec celery ...,让Celery替换shell进程成为PID 1,确保信号能被正确接收

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.17 07:15:51