芹菜中未经处理的异常会冻结工人



我正在通过 redis 后端在 docker 中运行芹菜。我有

  • 芹菜打容器
  • 芹菜工人容器
  • 瑞迪斯容器

芹菜工作器容器生成 6 个工作进程。如果芹菜任务遇到异常,则辅助角色(所有辅助角色)将停止消耗作业。我尝试稍微调试一下进程,似乎单个进程将卡在读取pipe而其余进程将卡在futex调用上。

调试信息:

# Worker 1
$ sudo strace -p 15959 -s 10000
strace: Process 15959 attached
read(4, ^Cstrace: Process 15959 detached
<detached ...>
# Worker 2 through N
$ sudo strace -p 15960 -s 10000
strace: Process 15960 attached
futex(0x7f95c3f94000, FUTEX_WAIT_BITSET|FUTEX_CLOCK_REALTIME, 0, NULL, 0xffffffff^Cstrace: Process 15960 detached
<detached ...>
$ sudo lsof -p 15958
COMMAND   PID USER   FD      TYPE DEVICE SIZE/OFF   NODE NAME
celery  15958 root  txt       REG  0,197    32248 264184 /usr/local/bin/python3.5
...
celery  15958 root    4r     FIFO   0,12      0t0 348559 pipe  # frozen here

奇怪的是,工人将永久处于冻结状态,除非发生以下 2 件事之一:

  1. 重新启动工作线程 (docker restart celery-worker)
  2. 快速启动芹菜。

我觉得"快速启动芹菜"很有趣。通过发出此命令,所有工作人员都会"醒来"并恢复活力并开始消耗任务,直到下一个异常。

docker exec -it celery-worker celery -A CELERY_APP inspect active

在这里,工人又复活了。

$ sudo strace -p 15958 -s 10000
strace: Process 15958 attached
read(4, "336", 4)                 = 4
read(4, "2003K2(MjnNccelery.app.tracen_fast_trace_tasknq(X"tasks.status_taskq1X$0071bf9972-cf5b-4a20-a8b7-ce4d7921fe0dq2}q3(Xtparent_idq4NX4langq5X2pyq6X3etaq7NX5groupq10NX7expiresqtNXttimelimitqn]qv(NNeX6originqfX21gen1@03e7668436e5qrX10argsreprq16X2()q17Xnkwargsreprq20X2{}q21X10reply_toq22X$005ad0db0b-a759-375c-b173-07598914633eq23X4taskq24h1X16correlation_idq25X$0071bf9972-cf5b-4a20-a8b7-ce4d7921fe0dq26X7root_idq27X$0071bf9972-cf5b-4a20-a8b7-ce4d7921fe0dq30X7retriesq31KXrdelivery_infoq32}q33(X10priorityq34KX10exchangeq35Xq36Xvredeliveredq37NXvrouting_keyq X6celeryq!uX6shadowq"NX2idq#h2uCM[[], {}, {"chord": null, "chain": null, "errbacks": null, "callbacks": null}]q$X20application/jsonq%X5utf-8q&tq'}q(tq)206q*.", 798) = 798
futex(0x7f95c3f94000, FUTEX_WAKE, 1)    = 1
write(7, "342003K(MjnNG@327204T2132121\KnNtq206q1.", 32) = 32
getpid()                                = 10

知道这是为什么吗?这是一个错误吗?我可以配置一些东西,以便芹菜不会在任务异常时挂起?

我正在使用eventlet并且我正在使用默认的pre-fork池运行工作线程。切换到eventlet池似乎已经解决了问题。

celery worker -A CELERY_APP --pool eventlet

相关内容

  • 没有找到相关文章

最新更新