2012-03-16 43 views
50

Đối với một nhiệm vụ như thế này:nhiệm vụ Thử lại cần tây với mũ lại tắt

from celery.decorators import task 

@task() 
def add(x, y): 
    if not x or not y: 
     raise Exception("test error") 
    return self.wait_until_server_responds(

nếu nó ném một ngoại lệ và tôi muốn thử nó từ phía daemon, làm thế nào có thể áp dụng một mũ quay trở lại thuật toán, tức là sau khi 2^2, 2^3,2^4 vv giây?

Cũng là thử lại được duy trì từ phía máy chủ, sao cho nếu nhân viên đó bị giết thì nhân viên tiếp theo sẽ sinh ra nhiệm vụ thử lại?

Trả lời

96

Thuộc tính task.request.retries chứa số cố gắng cho đến nay, vì vậy bạn có thể sử dụng để thực hiện mũ back-off:

from celery.task import task 

@task(bind=True, max_retries=3) 
def update_status(self, auth, status): 
    try: 
     Twitter(auth).update_status(status) 
    except Twitter.WhaleFail as exc: 
     self.retry(exc=exc, countdown=2 ** self.request.retries) 

Để ngăn chặn một Thundering Herd Problem, bạn có thể cân nhắc việc thêm một jitter ngẫu nhiên để mũ của bạn backoff:

import random 
self.retry(exc=exc, countdown=int(random.uniform(2, 4) ** self.request.retries)) 
+0

Bạn có biết đây là lần thử lại phía máy chủ hay ứng dụng khách được giữ không? Nếu khách hàng được giữ để chờ đợi thì nó xấu. –

+2

Theo như tôi biết thuộc tính đếm ngược đặt dấu phẩy cho tác vụ tại phần phụ trợ MQ (ví dụ: RabbitMQ). Vì vậy, nó không được đặt ở phía khách hàng. – idanzalz

+0

khách hàng không được chờ đợi trừ khi bạn thực hiện 'result.get()' là một yêu cầu rõ ràng để chờ kết quả sẵn sàng, nhưng cũng có một đối số hết thời gian và có trạng thái RETRY để bạn có thể kiểm tra xem tác vụ có đang được thử lại (và lý do để thử lại là gì) – asksol

9

Tính đến Cần tây 4.2 (không phát hành được nêu), bạn sẽ có thể cấu hình các nhiệm vụ của bạn để sử dụng một backoff mũ tự động: http://docs.celeryproject.org/en/master/userguide/tasks.html#automatic-retry-for-known-exceptions

@app.task(autoretry_for=(Exception,), retry_backoff=2) 
def add(x, y): 
    ... 

Đừng để bị lừa bởi "Mới trong phiên bản 4.1". thông báo trong tài liệu, nó chưa được phát hành, hãy xem merge request

Các vấn đề liên quan