#serialization #django-rest-framework
#сериализация #django-rest-framework
Вопрос:
В DRF я часто сталкиваюсь с вопросом о погоде или нет, я должен создать пользовательский сериализатор для определенного представления. Всегда есть задача выяснить, можно ли модифицировать существующие сериализаторы, чтобы они делали то, что я хочу.
Пример:
class ProductReviewSerializer(serializers.ModelSerializer):
product_name = serializers.SerializerMethodField(read_only=True)
class Meta:
model = ProductReview
fields = (
'uuid',
'review_score',
'user',
'product',
)
read_only_fields = (
'uuid',
)
def get_product_name(self, obj):
something ...
Я использую этот сериализатор для создания новых экземпляров ProductReview
. Кроме того, я хочу использовать этот сериализатор также для обновления экземпляров ProductReview
. Для этого сериализатор должен проверять данные из конечной точки API, в которой опущено много полей, например. DRF API получает только JSON {review_score: 2)
. Для данного примера я не могу заставить сериализатор быть действительным, если я не объявлю кучу полей как read_only
, что, в свою очередь, не работает для создания новых экземпляров.
Сериализатор для редактирования ProductReviews, который принимает данные ( {review_score: ...}
) сверху, будет выглядеть примерно так:
class ProductReviewEditSerializer(serializers.ModelSerializer):
class Meta:
model = ProductReview
fields = (
'review_score',
)
Я чувствую, что создаю здесь некоторые глупые недостатки дизайна. Но не могли бы вы указать мне направление к лучшему решению?
Является ли создание большого количества отдельных сериализаторов правильным решением? Мое внутреннее чувство подсказывает мне, что у каждой модели должен быть только один сериализатор…
Ответ №1:
На самом деле это очень хороший вопрос. Я делюсь своей точкой зрения, когда мы должны использовать serializer. Будет здорово прочитать мысли других людей по этому поводу.
Зачем нам нужен сериализатор
- Самая важная причина в том, что мы не всегда доверяем пользовательскому вводу как идеальному. Возможно, какой-то злоумышленник намеревается нанести вред системе. Поэтому мы всегда должны проверять как можно более совершенный способ проверки пользовательских данных, прежде чем вносить какие-либо изменения в нашу модель / систему.
- Мы хотим, чтобы наш ответ был в устоявшемся формате. Может потребоваться добавить пару логических операций помимо обычного ответа на запрос базы данных.
Может ли один сериализатор выполнять все возможные задания
Я твердо верю, что это возможно в большинстве случаев. Тем не менее, есть некоторые случаи, когда это невозможно. Я обнаружил DRF-ModelSerializer
, что он очень эффективен для этой работы и к тому же очень хорошо организован. Если ваше определение модели организовано должным образом. Если требуется какой-либо дополнительный ответ get, мы всегда можем использовать SerializerMethodField
для этой работы.
Возможное решение вашей проблемы
У меня есть намерение, чтобы вы не передавали экземпляр модели, который вы хотите обновить с помощью данных вашего запроса. Для частичного обновления с помощью serialize мы должны сделать что-то вроде этого
serializer = ProductReviewSerializer(product_review_model_instance, data=request.data, partial=True)