Django drf:序列化增删改查、局部与全局钩子源码流程、认证源码分析、执行流程

本文目录:

一、序列化类的增、删、改、查

二、局部和全局钩子源码流程

三、认证源码分析执行流程

 

 

 

一、序列化类的增、删、改、查

  用drf的序列化组件
   -定义一个类继承class BookSerializer(serializers.Serializer):
   -写字段,如果不指定source,字段名必须跟数据库字段名对应(source指定的值跟字段名不能重复)
   -source还可以指定方法
   -publish=serializers.SerializerMethodField()
   def get_publish(self,obj):
    obj.publish
    #obj.authors.all()
    
  - Serializer
  -ModelSerializer
   class Meta:
    # 指定表模型
    model = models.Book
    # 序列化所有字段
    fields = '__all__'
    # 只想序列化title和id这俩字段
    # fields = ['title', 'id']
    # exclude 和fields 不要连用
    # exclude = ['title']
    depth=1

# 先创建一个序列化的类继承ModelSerializer

# ModelSerializer跟表模型绑定序列化
from app import models


class BookSerializer(serializers.ModelSerializer):
    class Meta:
        # 指定表模型
        model = models.Book
        # 序列化所有的字段
        fields = '__all__'
        # 只想序列化title和id两个字段
        # fields = ['title','id']
        # exclude 和 fields不要连用
        # excude = ['title]
        # depth深度,表示链表的深度
        #不建议使用:下几层要取得参数不能控制,官方建议不要超过10,个人建议不超过3
        # depth = 1

    # publish = serializers.CharField(source='publish.name')
    # authors = serializers.SerializerMethodField()
    # def get_authors(self, obj):
    #     author_list = obj.authors.all()
    #     author_ser = AuthorSer(instance=author_list, many=True)
    #     return author_ser.data

    #为书名增加自定义需求
    title = serializers.CharField(max_length=6,min_length=3,error_messages={'max_length':'太长了'})

    #也有局部钩子函数
    def validate_title(self,value):
        from rest_framework import exceptions
        print(value)
        if value.startswith('tmd'):
            raise exceptions.ValidationError('不能以tmd开头')
        return value

 

#新增

from app.MySer import BookSerializer
from django.views import View
from rest_framework.views import APIView
from rest_framework.response import Response
from app import models

class Books(APIView):

    # 新增方法
    def post(self,request):
        response = {'status':100,'msg':'成功'}
        # book = request.data
        # 以往是提交字典,创建对象保存
        # 新方法时通过序列化组件保存,必须继承自ModelSerializer
        # data注意是data
        book_ser = BookSerializer(data=request.data)
        # is_valid提交的字段通过验证
        if book_ser.is_valid():
            book_ser.save()
            response['book']=book_ser.data
        else:
            response['msg'] = book_ser.errors
        return Response(response)

 

#删除

class Book(APIView):


    # 删除方法
    def delete(self,request,id):
        response = {'status': 100, 'msg': '删除成功'}
        book = models.Book.objects.filter(pk=id).delete()
        return Response(response)

 

# 修改

class Book(APIView):

    # 修改方法
    def put(self,request,id):
        response={'status':100,'msg':'成功'}
        book = models.Book.objects.filter(pk=id).first()
        # 修改的话需要把book对象传过来,实例化ser对象出来
        book_ser = BookSerializer(data=request.data,instance=book)
        # is_valid提交的字段校验通过
        if book_ser.is_valid():
            # save既可以修改,又可以更新
            book_ser.save()
            response['book'] = book_ser.data
        else:
            response['msg'] = book_ser.errors

        return Response(response)

 

# 查询所有

class Books(APIView):
    # 查询方法多个
    def get(self, request, *args, **kwargs):
        response = {'status': 100, 'msg': '成功'}
        book_list = models.Book.objects.all()
        # 第一个参数是要序列化的queryset对象,如果序列化多条,必须指定many=True
        # 问?什么情况下many=False,instance=单个对象的时候
        book_ser = BookSerializer(book_list, many=True)
        print(book_ser.data)
        response['books'] = book_ser.data
        return Response(response)

 

# 查询单个

class Book(APIView):
    # 查询单个方法
    def get(self,request, id):
        response = {'status':100,'msg':'成功'}
        book = models.Book.objects.filter(pk=id).first()
        book_ser = BookSerializer(book,many=False)
        response['book'] = book_ser.data
        return Response(response)

 

 

二、局部和全局钩子源码流程

 #为书名增加自定义需求
    title = serializers.CharField(max_length=6,min_length=3,error_messages={'max_length':'太长了'})

    #也有局部钩子函数
    def validate_title(self,value):
        from rest_framework import exceptions
        print(value)
        if value.startswith('tmd'):
            raise exceptions.ValidationError('不能以tmd开头')
        return value

 

 

三、认证源码分析执行流程

#Request对象的user方法
@property
def user(self):
the authentication classes provided to the request.
        if not hasattr(self, '_user'):
            with wrap_attributeerrors():
                self._authenticate()
        return self._user

def _authenticate(self):
        for authenticator in self.authenticators:
            try:
                user_auth_tuple = authenticator.authenticate(self)
            except exceptions.APIException:
                self._not_authenticated()
                raise
            #认证成功,可以返回一个元组,但必须是最后一个验证类才能返回
            if user_auth_tuple is not None:
                self._authenticator = authenticator
                self.user, self.auth = user_auth_tuple
                return

        self._not_authenticated()

self.authenticators

   def get_authenticators(self):
        return [auth() for auth in self.authentication_classes]

 

posted @ 2019-02-21 13:01  仗剑煮大虾  阅读(1072)  评论(0编辑  收藏  举报