Django Celery 连接错误:心跳丢失过多

11 投票
1 回答
7400 浏览
提问于 2025-04-17 15:31

问题

我该如何解决来自 Celery 的 ConnectionError: Too many heartbeats missed 错误?

示例错误

[2013-02-11 15:15:38,513: ERROR/MainProcess] Error in timer: ConnectionError('Too many heartbeats missed', None, None, None, '')
Traceback (most recent call last):
  File "/app/.heroku/python/lib/python2.7/site-packages/celery/utils/timer2.py", line 97, in apply_entry
    entry()
  File "/app/.heroku/python/lib/python2.7/site-packages/celery/utils/timer2.py", line 51, in __call__
    return self.fun(*self.args, **self.kwargs)
  File "/app/.heroku/python/lib/python2.7/site-packages/celery/utils/timer2.py", line 153, in _reschedules
    return fun(*args, **kwargs)
  File "/app/.heroku/python/lib/python2.7/site-packages/kombu/connection.py", line 265, in heartbeat_check
    return self.transport.heartbeat_check(self.connection, rate=rate)
  File "/app/.heroku/python/lib/python2.7/site-packages/kombu/transport/pyamqp.py", line 134, in heartbeat_check
    return connection.heartbeat_tick(rate=rate)
  File "/app/.heroku/python/lib/python2.7/site-packages/amqp/connection.py", line 837, in heartbeat_tick
    raise ConnectionError('Too many heartbeats missed')
ConnectionError: Too many heartbeats missed

应用概述

  • 这是一个使用 Celery 处理定时后台任务的 Django 应用
  • 托管在 Heroku 上
  • 有一个任务设置为每 15 分钟运行一次,通过设置 / celerybeat 来安排
  • 消息通过 CloudAMQP 插件处理
  • 进程运行方式如下:
    • web: newrelic-admin run-program gunicorn --workers=2 --worker-class=gevent someapp.wsgi:application
    • scheduler: newrelic-admin run-program python manage.py celery worker -B -E --maxtasksperchild=1000 --loglevel=WARNING

包版本

我认为相关的版本如下:

Django==1.4.3
amqp==1.0.8
billiard==2.7.3.20
celery==3.0.14
gevent==0.13.8
greenlet==0.4.0
kombu==2.5.6
raven==3.1.10

我目前尝试过的解决方法

  • 将错误与活动进行关联(似乎与用户访问应用、后台任务调用或应用闲置没有关联)
  • 在网上搜索,直到手指麻木
  • 将软件包升级到最新版本
  • 进行不同级别的日志记录
  • 使用 Sentry 捕获异常(在 Sentry 中没有出现)
  • 在本地开发环境中无法重现此错误,只在 Heroku 的生产环境中出现

可能相关的信息

  • 我不太确定这个错误是什么时候第一次出现的(大约一个月前?)
  • 可能与以下更改有关(在此之前不记得有过这个错误,但不太确定)
    • celery==3.0.13 升级到 celery==3.0.14
    • amqplib 更改为 amqp
    • kombu==2.4.8 升级到 kombu==2.5.4
  • 错误只出现在日志中(没有被 New Relic 或 getsentry.com 捕捉到)

1 个回答

9

这个问题发生的频率有多高呢?

可能是你的心跳监测功能没有正常工作。心跳支持是最近才引入的,所以可能会有一些bug。我这边无法重现这个问题,所以我需要更多的信息来搞清楚发生了什么。

你可以通过设置 BROKER_HEARTBEAT=0 来关闭心跳功能。如果这是个bug的话,工作程序应该能正常运行,但它就无法快速发现连接断开了。在某些环境下,无法检测到连接丢失是个问题(通常是因为特定的路由器或防火墙设置造成的)。

撰写回答