fix: гонка dispatch-before-commit (search/plagiarism) + detached user в notify
All checks were successful
Deploy / deploy (push) Successful in 23s
All checks were successful
Deploy / deploy (push) Successful in 23s
Три бага, найденные при аудите прода: - search и documents диспатчили Celery-задачу ДО commit() — быстрый воркер читал задачу раньше, чем транзакция закоммичена, и падал «задача не найдена» (поиск не работал вовсе; плагиат спасала латентность скачивания из MinIO). Теперь коммитим до диспатча. - notify.send_task_done обращался к user.email/name и task.type ПОСЛЕ закрытия сессии → DetachedInstanceError, письма о завершении уходили в ретраи. Значения достаются внутри сессии. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -130,8 +130,13 @@ async def upload_for_plagiarism_check(
|
||||
"file_size_bytes": len(file_data),
|
||||
},
|
||||
)
|
||||
task.queue_position = 1
|
||||
task.eta_seconds = 120
|
||||
db.add(task)
|
||||
await db.flush()
|
||||
# Коммитим ДО диспатча — иначе воркер может прочитать задачу раньше коммита
|
||||
# (гонка dispatch-before-commit).
|
||||
await db.commit()
|
||||
await db.refresh(task)
|
||||
|
||||
celery_result = celery_app.send_task(
|
||||
"index.extract_and_check",
|
||||
@@ -140,11 +145,7 @@ async def upload_for_plagiarism_check(
|
||||
)
|
||||
|
||||
task.celery_task_id = celery_result.id
|
||||
task.queue_position = 1
|
||||
task.eta_seconds = 120
|
||||
|
||||
await db.commit()
|
||||
await db.refresh(task)
|
||||
|
||||
logger.info("Задача плагиата %s создана для пользователя %d", task.public_id, current_user.id)
|
||||
return TaskResponse.model_validate(task)
|
||||
|
||||
@@ -66,8 +66,13 @@ async def create_search_task(
|
||||
"category": data.category,
|
||||
},
|
||||
)
|
||||
task.queue_position = 1
|
||||
task.eta_seconds = ETA_PER_POSITION_SECONDS
|
||||
db.add(task)
|
||||
await db.flush() # получаем id и public_id
|
||||
# Коммитим ДО диспатча: иначе быстрый воркер прочитает задачу раньше, чем
|
||||
# транзакция закоммичена, и не найдёт её в БД (гонка dispatch-before-commit).
|
||||
await db.commit()
|
||||
await db.refresh(task)
|
||||
|
||||
celery_result = celery_app.send_task(
|
||||
"gpu.search_semantic",
|
||||
@@ -77,11 +82,7 @@ async def create_search_task(
|
||||
)
|
||||
|
||||
task.celery_task_id = celery_result.id
|
||||
task.queue_position = 1
|
||||
task.eta_seconds = ETA_PER_POSITION_SECONDS
|
||||
|
||||
await db.commit()
|
||||
await db.refresh(task)
|
||||
|
||||
logger.info("Задача поиска %s создана для пользователя %d", task.public_id, current_user.id)
|
||||
return TaskResponse.model_validate(task)
|
||||
|
||||
Reference in New Issue
Block a user