Обращайся к этому гайду, если не знаешь, куда писать ту или иную часть функциональности бэкенда.
И так, ты пишешь...
- Логику модели (например, вычисление данных, которые будут сохраняться в модели)
- Твоя цель - метод в классе модели. Если нужно дополнительно сохранять полученные данные - переопредели метод save
- Если ты хочешь перехватывать события сохранения/удаления объекта и нагружать их доп.логикой - тебе понадобятся сигналы pre_save/post_save/pre_delete/etc.
- Важно: при множественном добавлении/удалении объектов с помощью bulk_create или с помощью админки, сигналы не обрабатываются. Учитывай это при работе с сигналами.
- Валидацию данных (например, проверку на то, что создаваемая бронь стиралки не пересекается ни с какими другими бронями): уноси её в сериализатор
- Обрати внимание: чтобы отличить в сериализаторе процесс создания модели от процесса изменения - посмотри значение атрибута "pk". При создании primary key будет None, т.к. объект ещё не попал в базу данных
- Для проверки одного конкретного значения в отрыве от остальных - используй метод validate_<field_name>
- Для проверки объекта в целом (как в примере из п.2) - используй метод validate
- Проверку прав доступа
- Пиши нужные методы has_perm_<какое-нибудь действие> в файле permissions.py. Методы has_perm_<какое-нибудь действие> нужны только для сериализаторов, не используй их во вьюхах
- Пиши классы прав в файле permissions.py. Классы прав доступа нужны только для вьюх
- Не делай проверки на права доступа в методах get()/post()/etc. вьюхи или в сериализаторах - это не их область ответственности
- Не используй метод user.has_perm нигде, кроме файла permissions.py (это нужно на те случаи, когда логика проверки прав доступа сложнее, чем просто вызов user.has_perm.
Такое случается довольно часто, и копипаст логики проверки прав в этих случаях - это выстрел себе в ногу) - Во вьюхах используй только классы пермишнов. Если нужно динамически в зависимости от запроса определять уровень прав - используй метод get_permissions.
- Если тебе нужен контекст для использования в классе прав (например, при запросах к стиралке тебе всегда нужно знать, о какой компоненте стиралки речь) - можешь переопределить метод setup() вьюхи, в котором добавить атрибуты
- Не забывай вызвать super().setup(request, *args, **kwargs)
- Если берёшь параметры из kwargs (GET-параметров) или request.data (POST-параметры) - не забывай проверять их наличие в запросе и кидать эксепшн rest_framework.exceptions.ParseError
- Эндпоинт (вьюху)
- Фильтрацию объекта (например, тебе прилетел запрос отобразить список бронирований с момента X по момент Y):
- Переопредели метод get_queryset или get_object
- Сохранение/удаление объекта:
- В случае, когда тебе надо одновременно сохранить/изменить/удалить несколько объектов в одной вьюхе - используй хуки вьюхи (методы perform_create/perform_update/perform_destroy)
- Не забывай использовать @transaction.atomic, если тебе нужна консистентность при изменении нескольких объектов (например - создание