Обработка фидбэка

В Celery передавайте id, а постановку задачи делайте после commit. Отправка письма и сохранение статуса не атомарны; нужны идемпотентность и явные переходы состояний. Сам APIView также используется неверно.

Короткий ответ

Что ответить на собеседовании

В Celery передавайте id, а постановку задачи делайте после commit. Отправка письма и сохранение статуса не атомарны; нужны идемпотентность и явные переходы состояний. Сам APIView также используется неверно.

Подробный разбор

Ответ с пояснениями

Условие

В API-контроллере создаётся объект Feedback, после чего асинхронно вызывается задача change_status_feedback. В задаче меняется статус фидбэка, отправляется письмо и объект сохраняется.

Проверить:

  • Можно ли передавать feedback целиком в Celery-задачу (не лучше ли передать id);
  • Не возникнут ли проблемы сериализации объекта feedback;
  • Как работает send_mail() — блокирует ли он выполнение, есть ли исключения;
  • Гарантируется ли, что feedback.save() завершится успешно после отправки письма;
  • Корректно ли выставляется статус in_progress.
@app.task(name='change_status_feedback')
def change_status_feedback(feedback):
    feedback.status = 'in_progress'
    send_mail()
    feedback.save()

class CreateFeedbackAPIView(APIView):
    def create(self, request):
        serializer = self.get_serializer(data=request.data)
        serializer.is_valid(raise_exception=True)
        feedback = Feedback.objects.create(**serializer.validated_data)
        change_status_feedback.delay(feedback)
        return feedback

Ответ

В Celery передавайте id, а постановку задачи делайте после commit. Отправка письма и сохранение статуса не атомарны; нужны идемпотентность и явные переходы состояний. Сам APIView также используется неверно.

Обычный APIView вызывает post(), не create(), и не предоставляет get_serializer. Используйте CreateAPIView с сериализатором либо реализуйте post и верните Response.

Сохраните Feedback, затем transaction.on_commit(lambda: task.delay(feedback.pk)); worker заново читает запись. JSON-сериализатор Celery не сериализует экземпляр ORM автоматически. send_mail обычно блокирует выполняющий worker и может выбросить исключение. Установленный только в памяти in_progress не виден в БД до save, который тоже может упасть. Зафиксируйте переход состояния до отправки и предусмотрите повторы; для надёжной доставки используйте outbox и защиту от дублей, а не обещание exactly-once.

ИИ-помощник для собеседований

Хочешь уверенно проходить собеседования?

Попробуй ИИ-помощник для собеседований: слышит вас и собеседника, анализирует экран, подсказывает ответы в реальном времени, работает без VPN и не попадает в захват экрана.

Подробнее