DRF的序列化组件

摘要:
其余部分中的url表示唯一的资源。http请求方法区分用户行为。url GET的设计规范:127.0.0.1:9001/books/#获取所有数据GET:127.0.0.1:9001/books/{id}#获取单个数据POST:127.0.0.1:29001/books/#添加数据DELETE:127.0.0.1:ISO9001/books/{id}#删除数据PUT:
rest

rest下的url

url唯一代表资源,http请求方式来区分用户行为

url的设计规范

GET: 127.0.0.1:9001/books/        # 获取所有数据

GET: 127.0.0.1:9001/books/{id}      # 获取单条数据

POST: 127.0.0.1:9001/books/      # 增加数据

DELETE: 127.0.0.1:9001/books/{id}    # 删除数据

PUT: 127.0.0.1:9001/books/{id}      # 修改数据

数据响应规范

GET: 127.0.0.1:9001/books/        # 返回[{}, {}, {}]

GET: 127.0.0.1:9001/books/{id}      # {} 单条数据

POST: 127.0.0.1:9001/books/        # {} 添加成功的数据

DELETE: 127.0.0.1:9001/books/{id}    # "" 返回空

PUT: 127.0.0.1:9001/books/{id}      # {} 更新后完整的数据

错误处理

{ "error": "message" }

解析器组件
  • 解析器组件是用来解析用户请求的数据的(application/json), content-type

  • 必须继承APIView

  • request.data触发解析

APIView的使用

rest_framework是一个app需要在settings里设置

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
    'rest_framework',  
]

pip install djangorestframework

from rest_framework.views import APIView

class LoginView(APIView):
def get(self, request):
pass
序列化组件

Django自带的serializer

from django.serializers import serialize  # 引入
​
origin_data = Book.objects.all()
serialized_data = serialize("json", origin_data)

DRF的序列化组件

接口设计

from rest_framework import serializers  #引入

创建一个序列化类

DRF的序列化组件第1张DRF的序列化组件第2张
class BookSerializer(serializers.ModelSerializer):
    class Meta:
        model = Book
        # model字段
        fields = ('title',
                  'price',
                  'publish',
                  'authors',
                  'author_list',
                  'publish_name',
                  'publish_city'
                  )
        # 只需写入不需要展示的字段
        extra_kwargs = {
            'publish': {'write_only': True},
            'authors': {'write_only': True}
        }
    # source为自定义需要展示的信息
    publish_name = serializers.CharField(max_length=32, read_only=True, source='publish.name')
    publish_city = serializers.CharField(max_length=32, read_only=True, source='publish.city')
    # 多对多字段需要自己手动获取数据,SerializerMethodField()
    author_list = serializers.SerializerMethodField()
​
    def get_author_list(self, book_obj):
        # 拿到queryset开始循环 [{}, {}, {}, {}]
        authors = list()
​
        for author in book_obj.authors.all():
            authors.append(author.name)
​
        return authors
创建序列化类

开始序列化

get接口(查询多条数据) & post接口

class BookView(APIView):
    def get(self, request):
        # 获取queryset
        origin_data = Book.objects.all()
        # 开始序列化
        serialized_data = BookSerializer(origin_data, many=True)
        return Response(serialized_data.data)
    def post(self, request):
        verified_data = BookSerializer(data=request.data)
        if verified_data.is_valid():
            book = verified_data.save()
            authors = Author.objects.filter(nid__in=request.data['authors'])
            book.authors.add(*authors)
            return Response(verified_data.data)
        else:
            return Response(verified_data.errors)

get(查询单条数据)&put接口&delete接口

class BookFilterView(APIView):
    def get(self, request, nid):
        book_obj = Book.objects.get(pk=nid)
        serialized_data = BookSerializer(book_obj, many=False)
        return Response(serialized_data.data)
​
    def put(self, request, nid):
        book_obj = Book.objects.get(pk=nid)
        verified_data = BookSerializer(data=request.data, instance=book_obj)
        if verified_data.is_valid():
            verified_data.save()
            return Response(verified_data.data)
        else:
            return Response(verified_data.errors)
​
    def delete(self, request, nid):
        book_obj = Book.objects.get(pk=nid).delete()
        return Response()

缺点:

serializers.Serializer无法插入数据,只能自己实现create字段太多,不能自动序列化

接口设计优化

使用视图组件的mixin进行接口逻辑优化

导入mixin

from rest_framework.mixinx import (
                    ListModelMix,
                    CreateModelMixin,
                    DestroyModelMixin,
                    UpdateModelMixin,
                    RetrieveModelMixin
                )
from rest_framework.generics import GenericAPIView
​

定义序列化类

Class BookSerializer(serializers.ModelSerializer):
                  class Meta:
                      Book
                      fields = ()
                      ...如上

因为使用模块化编程,建议将定义的序列化类放在单独的模块中,再在view.py中导入

from .app_serializers import BookSerializer

定义视图类​

class BookView(ListModelMix, CreateModelMixin, GenericAPIView):
    # queryset和serializer_class是固定的写法
    queryset = Book.objects.all()
    serializer_class = BookSerializer      
    def get():
        return self.list() # 查询多条
            
    def post():
        return self.create()
                
class BookFilterView(RetrieveModelMixin, DestroyModelMixin, UpdateModelMixin, GenericAPIView):
    queryset = Book.objects.all()
    serializer_class = BookSerializer
​
    def get():
        return self.retrieve()  # 查询单条
def delete():
        return self.destroy()
​
    def put():
        return self.update()

注意:

查询单挑数据的url需要给查询的id进行正则分组

re_path(r'books/(?P<pk>d+)/$, views.BookFilterView.as_view())

使用视图组件的view进行接口逻辑优化

导入模块

from rest_framework import generics

视图类​

class BookView(generics.ListCreateAPIView)
    queryset = Book.objects.all()
    serializer_class = BookSerializer   
class BookFilterView(generics.RetrieveUpdateDestroyAPIView):
    queryset = Book.objects.all()
    serializer_class = BookSerializer

使用视图组件的viewset进行接口逻辑优化

导入模块

from rest_framework.viewsets import ModelViewSet

设计url

re_path(r'books/$, views.BookView.as_view({
    'get': 'list',
    'post': 'create'
    })),
re_path(r'books/(?P<pk>d+)/$', views.BookView.as_view({
    'get': 'retrieve',
    'delete': 'destroy',
    'put': 'update'
    }))

设计视图类

class BookView(ModelViewSet):
    queryset = Book.objects.all()
    serializer_class = BookSerializer

 

 

免责声明:文章转载自《DRF的序列化组件》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇layui实现分页Django 语法笔记下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

Akka系列(九):Akka分布式之Akka Remote

前言.... Akka作为一个天生用于构建分布式应用的工具,当然提供了用于分布式组件即Akka Remote,那么我们就来看看如何用Akka Remote以及Akka Serialization来构建分布式应用。 背景 很多同学在程序的开发中都会遇到一个问题,当业务需求变得越来越复杂,单机服务器已经不足以承载相应的请求的时候,我们都会考虑将服务部署到不同的...

高效的数据压缩编码方式 Protobuf

一. protocol buffers 是什么? Protocol buffers 是一种语言中立,平台无关,可扩展的序列化数据的格式,可用于通信协议,数据存储等。 Protocol buffers 在序列化数据方面,它是灵活的,高效的。相比于 XML 来说,Protocol buffers 更加小巧,更加快速,更加简单。一旦定义了要处理的数据的数据结构之...

OPENQUERY (Transact-SQL),跨数据库操作。

在指定的链接服务器上执行指定的传递查询。 该服务器是 OLE DB 数据源。 OPENQUERY 可以在查询的 FROM 子句中引用,就好象它是一个表名。OPENQUERY 也可以作为 INSERT、UPDATE 或 DELETE 语句的目标表进行引用。 但这要取决于 OLE DB 访问接口的功能。 尽管查询可能返回多个结果集,但是 OPENQUERY 只...

laravel框架使用生涯

手工安装laravel http://laravelacademy.org/resources-download 1、将下载的文件复制到虚拟主机目录 2、在Apache的配置文件配置一个虚拟主机【注意,需要指向 public目录下】 <VirtualHost *:80> DocumentRoot "C:phpStudyWWWlarav...

C# 对象二进制序列化

using System.Runtime.Serialization.Formatters.Binary;public class SerializationUnit{            /// <summary>    /// 把对象序列化为字节数组    /// </summary>    public static by...

java对象序列化、gzip压缩解压缩、加密解密

有时在应用中需要将java对象序列化存储起来,有的需要压缩,有的需要加密 EncryptUtil.java Java代码 packageorg.test.demo; importjava.io.UnsupportedEncodingException; importjava.security.InvalidKeyException; importj...