Criar um AsyncResult
objeto a partir do id da tarefa é a forma recomendada no FAQ para obter o status da tarefa quando a única coisa que você tem é o id da tarefa.
No entanto, a partir do Celery 3.x, existem advertências significativas que podem morder as pessoas se não derem atenção a elas. Realmente depende do cenário de caso de uso específico.
Por padrão, o Celery não registra um estado de "execução".
Para que o Celery registre que uma tarefa está em execução, você deve definir task_track_started
como True
. Aqui está uma tarefa simples que testa isso:
@app.task(bind=True)
def test(self):
print self.AsyncResult(self.request.id).state
Quando task_track_started
é False
, que é o padrão, a exibição do estado é PENDING
mesmo que a tarefa tenha sido iniciada. Se você definir task_track_started
como True
, o estado será STARTED
.
O estado PENDING
significa "Não sei".
Um AsyncResult
com o estado PENDING
não significa nada mais do que o fato de que Celery não conhece o status da tarefa. Isso pode ser por uma série de razões.
Por um lado, AsyncResult
pode ser construído com ids de tarefa inválidos. Essas "tarefas" serão consideradas pendentes pelo Celery:
>>> task.AsyncResult("invalid").status
'PENDING'
Ok, então ninguém vai alimentar ids obviamente inválidos para AsyncResult
. É justo, mas também tem efeito que AsyncResult
também considerará uma tarefa que foi executada com sucesso, mas que o aipo esqueceu como sendo PENDING
. Novamente, em alguns cenários de casos de uso, isso pode ser um problema. Parte do problema gira em torno de como o Celery está configurado para manter os resultados das tarefas, porque depende da disponibilidade das "marcas para exclusão" no backend de resultados. ("Tombstones" é o termo usado na documentação do Celery para os blocos de dados que registram como a tarefa terminou.) O uso AsyncResult
não funcionará se task_ignore_result
for True
. Um problema mais irritante é que o Celery expira as marcas de exclusão por padrão. oresult_expires
configuração padrão é 24 horas. Portanto, se você iniciar uma tarefa e registrar a id no armazenamento de longo prazo, e mais 24 horas depois, criar um AsyncResult
com ela, o status será PENDING
.
Todas as "tarefas reais" começam no PENDING
estado. Portanto, realizar PENDING
uma tarefa pode significar que a tarefa foi solicitada, mas nunca avançou além disso (por qualquer motivo). Ou pode significar que a tarefa foi executada, mas Celery esqueceu seu estado.
Ai! AsyncResult
não vai funcionar para mim. O que mais eu posso fazer?
Prefiro controlar as metas do que as tarefas em si . Eu mantenho algumas informações sobre as tarefas, mas elas são secundárias para manter o controle dos objetivos. As metas são armazenadas em armazenamento independente do Aipo. Quando uma solicitação precisa realizar um cálculo depende de algum objetivo ter sido alcançado, ele verifica se o objetivo já foi alcançado, se sim, então ele usa este objetivo em cache, caso contrário, ele inicia a tarefa que afetará o objetivo e envia para o cliente que fez a solicitação HTTP uma resposta que indica que ele deve esperar por um resultado.
Os nomes de variáveis e hiperlinks acima são para Celery 4.x. Em 3.x as variáveis e hiperlinks correspondentes são: CELERY_TRACK_STARTED
, CELERY_IGNORE_RESULT
, CELERY_TASK_RESULT_EXPIRES
.
x
?