如何在Django Python Web框架中使用Serializers


原文地址:如何在Django Python Web框架中使用Serializers

序列化是将数据转换为可以存储或传输的格式,然后对其进行重构的过程。序列化后的程序可以直接保存到数据库中,当反序列化时原来的数据类型将保持不变。本篇文章分享了Django中的Seralizers的使用示例。

序列化将数据转换为可以存储或传输的格式,然后对其进行重构以供使用。DRF具有最著名的串行器。

序列化是将数据转换为可以存储或传输的格式,然后对其进行重构的过程。开发应用程序或将数据存储在数据库,内存中或将其转换为文件时一直使用它。

假设您正在为一个电子商务网站创建软件,并且您有一个订单,该订单记录某人在某个日期以某种价格购买了一种产品:

class Order:
    def __init__(self, product, customer, price, date):
        self.product = product
        self.customer = customer
        self.price = price
        self.date = date

现在,假设您想从键值数据库中存储和检索订单数据。幸运的是,它的接口可以接受并返回字典,因此您需要将对象转换为字典:

def serialize_order(order):
    return {
        'product': order.product,
        'customer': order.customer,
        'price': order.price,
        'date': order.date
    }

并且,如果您想从该数据库中获取一些数据,则可以获取dict数据并将其转换为Order对象:

def deserialize_order(order_data):
    return Order(
        product=order_data['product'],
        customer=order_data['customer'],
        price=order_data['price'],
        date=order_data['date'],
    )

处理简单数据非常简单,但是当您需要处理由复杂属性组成的复杂对象时,这种方法就无法很好地扩展。您还需要处理不同类型的字段的验证,这是手动完成的大量工作。

那就是框架的序列化器很方便的地方。它们使您可以创建带有少量样板的序列化器,这些样板可用于复杂的情况。

Django随附一个序列化模块,可让您将模型“翻译”为其他格式:

from django.core import serializers
serializers.serialize('json', Order.objects.all())

它涵盖了Web应用程序最常用的情况,例如JSON,YAML和XML。但是您也可以使用第三方序列化程序或创建自己的序列化程序。您只需要在settings.py文件中注册它:

# settings.py
SERIALIZATION_MODULES = {
    'my_format': appname.serializers.MyFormatSerializer,
}

要创建自己的MyFormatSerializer,您需要实现.serialize()方法并接受queryset和其他选项作为参数:

class MyFormatSerializer:
    def serialize(self, queryset, **options):
        # serious serialization happening

现在,您可以将查询集序列化为新格式:

from django.core import serializers

serializers.serialize('my_format', Order.objects.all())

您可以使用options参数来定义序列化程序的行为。例如,如果要定义要在处理时使用嵌套序列化,ForeignKeys或者只希望数据返回其主键,则可以将flat=Trueparam作为选项传递并在方法中进行处理:

class MyFormatSerializer:
    def serializer(self, queryset, **options):
        if options.get('flat', False):
            # don't recursively serialize relationships
        # recursively serialize relationships

DRF串行器

在Django社区中,Django REST框架 (DRF)提供了最著名的序列化器。尽管您可以使用Django的序列化器来构建将在API中响应的JSON,但REST框架中的序列化器具有出色的功能,可帮助您处理并轻松验证复杂数据。

在订购示例中,您可以创建一个序列化器,如下所示:

from restframework import serializers

class OrderSerializer(serializers.Serializer):
    product = serializers.CharField(max_length=255)
    customer = serializers.CharField(max_lenght=255)
    price = serializers.DecimalField(max_digits=5, decimal_places=2)
    date = serializers.DateField()

并轻松序列化其数据:

order = Order('pen', 'renato', 10.50, date.today())
serializer = OrderSerializer(order)

serializer.data
# {'product': 'pen', 'customer': 'renato', 'price': '10.50', 'date': '2020-08-16'}

为了能够从数据返回实例,您需要实现两个方法-创建和更新:

from rest_framework import serializers

class OrderSerializer(serializers.Serializer):
    product = serializers.CharField(max_length=255)
    customer = serializers.CharField(max_length=255)
    price = serializers.DecimalField(max_digits=5, decimal_places=2)
    date = serializers.DateField()

    def create(self, validated_data):
        # perform order creation
        return order

    def update(self, instance, validated_data):
       # perform instance update
       return instance

之后,您可以通过调用is_valid()以验证数据以及save()创建或更新实例来创建或更新实例:

serializer = OrderSerializer(**data)
## to validate data, mandatory before calling save
serializer.is_valid()
serializer.save()

模型序列化器

序列化数据时,通常需要从数据库(因此,从模型)进行数据处理。ModelSerializer与ModelForm一样,提供了一个API,用于根据模型创建序列化器。假设您有一个订购模型:

from django.db import models


class Order(models.Model):
    product = models.CharField(max_length=255)
    customer = models.CharField(max_length=255)
    price = models.DecimalField(max_digits=5, decimal_places=2)
    date = models.DateField()    

您可以为它创建一个序列化器,如下所示:

from rest_framework import serializers


class OrderSerializer(serializers.ModelSerializer):
    class Meta:
        model = Order
        fields = '__all__'

Django自动在序列化器中包含所有模型字段,并创建createupdate方法。

在基于类的视图(CBV)中使用序列化器

像带有Django CBV的Forms一样,序列化程序可以与DRF很好地集成。您可以设置serializer_class属性,以便序列化器可用于视图:

from rest_framework import generics


class OrderListCreateAPIView(generics.ListCreateAPIView):
    queryset = Order.objects.all()
    serializer_class = OrderSerializer

您还可以定义get_serializer_class()方法:

from rest_framework import generics


class OrderListCreateAPIView(generics.ListCreateAPIView):
    queryset = Order.objects.all()
   
    def get_serializer_class(self):
        if is_free_order():
            return FreeOrderSerializer
        return OrderSerializer

CBV中还有其他与序列化程序交互的方法。例如,get_serializer()返回已实例化的序列化器,而get_serializer_context()返回创建实例时将传递给序列化器的参数。对于创建或更新数据的视图,存在createupdate使用is_valid要保存的方法验证数据的视图,以及调用序列化程序的save方法的perform_createperform_update

 

评论

登录后评论

服务器优惠活动

Top