DRF框架中的演变View

import json

from django.db import DatabaseError
from django.http import HttpResponse
from django.http import JsonResponse
from django.shortcuts import render
# Create your views here.

from django.views import View

# http://127.0.0.1:8000/books/

from rest_framework.authentication import SessionAuthentication
from rest_framework.decorators import action
from rest_framework.generics import GenericAPIView, CreateAPIView, ListAPIView, RetrieveAPIView, UpdateAPIView,DestroyAPIView, ListCreateAPIView, RetrieveUpdateDestroyAPIView
from rest_framework.mixins import ListModelMixin, CreateModelMixin, RetrieveModelMixin, UpdateModelMixin,DestroyModelMixin
from rest_framework.pagination import PageNumberPagination
from rest_framework.permissions import IsAuthenticated, AllowAny
from rest_framework.response import Response
from rest_framework.throttling import UserRateThrottle
from rest_framework.views import APIView
from rest_framework.viewsets import ModelViewSet

from books.models import BookInfo, HeroInfo
from books.serializers import BookInfoSerializer, HeroInfoSerializer, BookInfoModelSerializer, HeroInfoModelSerializer,BookInfoSerializerForModidyRead
View Code
def test(request):
    s = HeroInfoModelSerializer()
    print(s)
    return HttpResponse("OK")


print("使用view开始")
# http://127.0.0.1:8000/heros/id/
class HeroView(View):
    def get(self,request,pk):
        try:
            hero = HeroInfo.objects.get(pk=pk)
        except Exception as e:
            return HttpResponse(status=404)
        serializer = HeroInfoSerializer(hero)
        return JsonResponse(serializer.data)

class BooksView(View):
    def get(self, request):
        try:
            books = BookInfo.objects.all()
        except Exception as e:
            return HttpResponse(status=404)
        serializer = BookInfoSerializer(books,many=True)
        return JsonResponse(serializer.data,safe=False)

    def post(self, request):
        json_bytes = request.body
        json_str = json_bytes.decode()
        json_dict = json.loads(json_str)
        print(json_dict)
        # 校验参数
        serializer = BookInfoSerializer(data=json_dict)
        # 如果校验不成功直接抛出异常
        success = serializer.is_valid(raise_exception=True)
        print(success)
        if success:
            serializer.save()
        return JsonResponse(serializer.data,status=201)

# http://127.0.0.1:8000/books/id/
class BookView(View):

    def get(self, request, pk):
        try:
            book = BookInfo.objects.get(pk=pk)
        except Exception as e:
            return HttpResponse(status=404)
        serializer = BookInfoSerializer(book)
        return JsonResponse(serializer.data)

    def put(self, request, pk):
        try:
            book = BookInfo.objects.get(pk=pk)
        except Exception as e:
            return HttpResponse(status=404)
        json_bytes = request.body
        json_str = json_bytes.decode()
        json_dict = json.loads(json_str)
        print(json_dict)

        serializer = BookInfoSerializer(instance=book, data=json_dict,partial=True)
        # 如果校验不成功直接抛出异常
        success = serializer.is_valid(raise_exception=True)
        print(success)
        if success:
            serializer.save()
        return JsonResponse(serializer.data,status=201)

    def delete(self, request, pk):
        try:
            book = BookInfo.objects.get(pk=pk)
        except Exception as e:
            return HttpResponse(status=404)

        book.delete()
        return HttpResponse(status=204)
View Code
print("使用View结束")


print("使用APIView开始")
# 利用APIView中强大的request和response
# request中的request.data可以自动帮我们进行解码操作,因为其中含有DRF的Parser解析器,会自动的根据
#     content-type解析数据,将解析的数据添加到Request类中,
# response可以根据我们的请求给我们返回我们需要的数据,用户想要什么界面就可以直接渲染出想要的结果
class BooksView(APIView):
    def get(self, request):
        books = BookInfo.objects.all()
        serializer = BookInfoModelSerializer(books,many=True)
        return Response(serializer.data)

    def post(self, request):
        # 校验参数
        serializer = BookInfoModelSerializer(data=request.data)
        # 如果校验不成功直接抛出异常
        success = serializer.is_valid(raise_exception=True)
        if success:
            serializer.save()
        return Response(serializer.validated_data,status=201)

# http://127.0.0.1:8000/books/id/
class BookView(APIView):

    def get(self, request, pk):
        book = BookInfo.objects.get(pk=pk)
        serializer = BookInfoModelSerializer(book)
        return Response(serializer.data)

    def put(self, request, pk):
        book = BookInfo.objects.get(pk=pk)
        serializer = BookInfoModelSerializer(instance=book, data=request.data,partial=True)
        # 如果校验不成功直接抛出异常
        success = serializer.is_valid(raise_exception=True)
        if success:
            serializer.save()
        return Response(serializer.validated_data,status=201)

    def delete(self, request, pk):
        book = BookInfo.objects.get(pk=pk)
        book.delete()
        return HttpResponse(status=204)
        
View Code
print("使用APIView结束")

print("使用GenericAPIView开始")
class BooksView(GenericAPIView):
    queryset = BookInfo.objects.all()
    serializer_class = BookInfoModelSerializer

    def get(self, request):
        books = self.get_queryset()
        serializer = self.get_serializer(books,many=True)
        return Response(serializer.data)

    def post(self, request):
        # 校验参数
        serializer = self.get_serializer(data=request.data)
        # 如果校验不成功直接抛出异常
        print(request.data)
        success = serializer.is_valid(raise_exception=True)
        print(success)
        if success:
            serializer.save()
        return Response(serializer.validated_data,status=201)

# http://127.0.0.1:8000/books/id/
class BookView(GenericAPIView):
    queryset = BookInfo.objects.all()
    # serializer_class = BookInfoModelSerializer
    # lookup_url_kwarg 指定的是路径中参数的名称,默认叫pk
    # lookup_field 指的是数据库中的字段
    # lookup_field = "id"

    def get_serializer_class(self):
        return BookInfoModelSerializer

    def get(self, request, pk):
        book = self.get_object()
        serializer = self.get_serializer(book)
        return Response(serializer.data)

    def put(self, request, pk):
        book = self.get_object()
        serializer = self.get_serializer(instance=book, data=request.data,partial=True)
        success = serializer.is_valid(raise_exception=True)
        if success:
            serializer.save()
        return Response(serializer.validated_data,status=201)

    def delete(self, request, pk):
        book = self.get_object()
        book.delete()
        return Response(status=204)
View Code
print("使用GenericAPIView以结束")

print("GenericAPIView的扩展类开始")
扩展类:针对于某一个类进行功能的扩展,只能够结合这个类进行使用,不能单独使用
子类:针对父类的功能进行扩展,可以单独使用
class BooksView(ListModelMixin,CreateModelMixin,GenericAPIView):
    queryset = BookInfo.objects.all()
    serializer_class = BookInfoModelSerializer

    def get(self, request):
        return self.list(request)

    def post(self, request):
        return self.create(request)

class BookView(RetrieveModelMixin,UpdateModelMixin,DestroyModelMixin,GenericAPIView):
    queryset = BookInfo.objects.all()
    serializer_class = BookInfoModelSerializer

    def get(self, request, pk):
        return self.retrieve(request,pk)

    def put(self, request, pk):
        return self.update(request,pk)

    def delete(self, request, pk):
        return self.destroy(request,pk)
View Code
print("GenericAPIView的扩展类以结束")

# ListAPIView  --> get()
# CreateAPIView --> post()
# ListCreateAPIView
#    get
#    post
# RetrieveAPIView  --> get()
# UpdateAPIView  --> put() patch()
# DestroyAPIView  --> delete()
# RetrieveUpdateAPIView  --> get() put() patch()
# RetrieveDestroyAPIView  --> get() delete()
# RetrieveUpdateDestroyAPIView  --> get() put() patch() delete()
class BooksView(ListCreateAPIView):
     queryset = BookInfo.objects.all()
     serializer_class = BookInfoModelSerializer


class BookView(RetrieveUpdateDestroyAPIView):
     queryset = BookInfo.objects.all()
     serializer_class = BookInfoModelSerializer
View Code
print("GenericAPIView的子类以结束")


print("使用视图集开始")
# 关于图书的这个资源,我们不想写两个类视图,我们就想写一个类
# 关于图书的操作:获取列表增加获取单个修改删除
#              list()create()
etrieve()update()destory()
# 视图集:视图集并不是必须的,如果你足够的懒,那么可以使用视图集
# 达到的效果:多个路径,只需要写一个class即可
# 注意:要在urls.py中来配置,不同路径不同请求方法  究竟应该调用哪个方法
# 视图集的功能:可以让我们通过不同的路径,访问到同一个class中不同方法
# 视图集中自定义动作的实现:
#   1在urls.py中配置好路径和这个class中哪个方法的映射关系
#   2在这个class中通过def的方式定义好方法,  这个方法中得要有request参数,可能会有pk
# http://127.0.0.1:8000/books/?page=2&page_size=2/
class LargeResultsSetPagination(PageNumberPagination):
    page_size = 2
    page_size_query_param = 'page_size'
    max_page_size = 10

class BookViewSet(ModelViewSet):
    """
        list:
        获取图书信息
        retrieve:
        获取 单个图书信息
        latest:
        获取图书的最新信息
        read:
        修改图书阅读量的数据

    """
    queryset = BookInfo.objects.all()
    # throttle_classes = (UserRateThrottle,)
    filter_fields = ('btitle', 'bread')
    pagination_class = LargeResultsSetPagination

    def get_permissions(self):
        if self.action == "latest":
            return [IsAuthenticated()]
        return [AllowAny()]

    # 我们可以通过视图集中的self.action决定当前是哪一种动作,通过不同的动作,返回不同的序列化器类的引用
    def get_serializer_class(self):
        if self.action == "read":
            return BookInfoSerializerForModidyRead
        return BookInfoModelSerializer

    @action(methods=["get"],detail=False)
    def latest(self,request):
        raise DatabaseError()

        book = BookInfo.objects.latest("id")
        s = self.get_serializer(book)
        return Response(s.data)

    @action(methods=["put"],detail=True)
    def read(self,request,pk):
        book = self.get_object()
        s = self.get_serializer(book,data=request.data)
        success = s.is_valid(raise_exception=True)
        if success:
            s.save()
        return Response(s.validated_data,status=201)
View Code
print("使用视图集ViewSet结束")

# 局部限流
class BookDetailView(RetrieveAPIView):
    queryset = BookInfo.objects.all()
    serializer_class = BookInfoModelSerializer
    authentication_classes = [SessionAuthentication]
    permission_classes = [IsAuthenticated]
    throttle_classes = (UserRateThrottle,)

# 局部过滤
class BookListView(ListAPIView):
    queryset = BookInfo.objects.all()
    serializer_class = BookInfoModelSerializer
    filter_fields = ('btitle', 'bread')
原文地址:https://www.cnblogs.com/wangxiongbing/p/10410039.html