两个视图基类
两个视图基类
9.1 APIView基本视图类
9.1.1 APIView与django的view的区别
View是Django默认的视图基类,APIView是REST framework提供的所有视图的基类, 继承自Django的View,对Django中的View进行了拓展,具备了认证、授权、限流、不同请求数据的解析的功能。
-
APIView的request与view的request不同
-
APIView具有身份验证,权限限制,限流等功能
authentication_classes 身份认证 permission_classes 权限检查 throttle_classes 流量控制
-
APIView视图方法可以返回REST framework的Response对象,视图会为响应数据设置(render)符合前端要求的格式;
9.1.2 基于APIView实现五个接口
序列化器
from rest_framework import serializers
from app.models import studentsInfo
class StudentModelSerializer(serializers.ModelSerializer):
"""学生信息序列化器"""
class Meta:
model = studentsInfo
fields = ["id", "name", "sex", "age", "classroom", "info"]
read_only_fields = ["id"]
extra_kwargs = {
"age": {
"min_value": 0,
"max_value": 100,
"error_messages": {
"min_value": "the age must be age>=0",
"max_value": "the age must be age<=100"
}
}
}
视图
from rest_framework.views import APIView
from rest_framework.response import Response
from rest_framework import status
from app.models import studentsInfo
from .serializers import StudentModelSerializer
"""
post /students/ 添加一个学生
GET /students/ 获取所有学生信息
GET /students/<pk>/获取一个学生信息
PUT /students/<pk>/ 更新一个学生信息
DELETE /students/<pk>/ 删除一个学生信息
一个路由对应一个视图类,把5个api接口分为两个视图类来写
"""
class StudentView(APIView):
def post(self, request):
serializer = StudentModelSerializer(data=request.data)
serializer.is_valid(raise_exception=True)
serializer.save()
return Response(serializer.data, status=status.HTTP_201_CREATED)
def get(self, request):
data = studentsInfo.objects.all()
serializer = StudentModelSerializer(instance=data, many=True)
return Response(serializer.data,status=status.HTTP_200_OK)
class StudentAPIView(APIView):
def get(self, request, pk):
try:
student = studentsInfo.objects.get(id=pk)
except studentsInfo.DoesNotExist:
return Response({"message": "没有该学生的相关信息"},status=status.HTTP_204_NO_CONTENT)
serializer = StudentModelSerializer(instance=student)
return Response(serializer.data,status=status.HTTP_200_OK)
def put(self, request, pk):
try:
student = studentsInfo.objects.get(id=pk)
except studentsInfo.DoesNotExist:
return Response({"message": "没有该学生的相关信息,您可以添加此学生哦!"}, status=status.HTTP_204_NO_CONTENT)
serializer = StudentModelSerializer(instance=student, data=request.data)
serializer.is_valid(raise_exception=True)
serializer.save()
return Response(serializer.data, status=status.HTTP_201_CREATED)
def delete(self, request, pk):
try:
studentsInfo.objects.get(id=pk).delete()
except studentsInfo.DoesNotExist:
return Response({"message": "没有该学生的相关信息,可能已经删除过啦"}, status=status.HTTP_204_NO_CONTENT)
return Response({"message": "删除成功"}, status=status.HTTP_200_OK)
路由
from django.urls import path, re_path
from . import views
urlpatterns = [
path('students/', views.StudentView.as_view()),
re_path(r'^students/(?P<pk>\d+)/$', views.StudentAPIView.as_view())
]
总路由
from django.contrib import admin
from django.urls import path, include
urlpatterns = [
path('viewdemo/', include('viewdemo.urls')),
]
9.2 GenericAPIView通用视图类
9.2.1 GenericAPIView的介绍
GenericAPIView 继承自 APIView,主要增加了操作序列化和数据库查询的方法,作用是为下面 Mixin 扩展类的执行提供方法支持。通常在使用时,可搭配一个或多个 Mixin 扩展类。
- 指明视图使用的序列化器
① 通过属性:
serializer_class
② 通过方法:
get_serializer_class(self)
get_serializer(self, args, *kwargs)
- 数据库查询的属性与方法
指明使用的数据查询集
① 通过属性
queryset
② 通过方法
get_queryset(self)
get_object(self)
9.2.2 基于GenericAPIView实现五个接口
视图
from rest_framework.generics import GenericAPIView
from rest_framework.response import Response
from rest_framework import status
from app.models import studentsInfo
from .serializers import StudentModelSerializer
"""GenericAPIView通用视图类"""
class StudentGenericAPIView(GenericAPIView):
queryset = studentsInfo.objects.all()
serializer_class = StudentModelSerializer
def get(self, request):
"""获取所有数据"""
queryset = self.get_queryset()
serializer = self.get_serializer(instance=queryset, many=True)
return Response(serializer.data)
def post(self, request):
"""添加一名学生"""
serializer = self.get_serializer(data=request.data)
serializer.is_valid(raise_exception=True)
serializer.save()
return Response(serializer.data)
class StudentGenericAPIView2(GenericAPIView):
queryset = studentsInfo.objects.all()
serializer_class = StudentModelSerializer
def get(self, request, pk):
"""获取一条数据"""
queryset = self.get_object()
serializer = self.get_serializer(instance=queryset)
return Response(serializer.data)
def put(self, request, pk):
"""修改一条数据"""
instance = self.get_object()
serializer = self.get_serializer(instance=instance, data=request.data)
serializer.is_valid(raise_exception=True)
serializer.save()
return Response(serializer.data)
def delete(self, request, pk):
"""删除一条数据"""
self.get_object().delete()
return Response(status=status.HTTP_204_NO_CONTENT)
路由
from django.urls import path, re_path
from . import views
urlpatterns = [
# APIView
path('students/', views.StudentView.as_view()),
re_path(r'^students/(?P<pk>\d+)/$', views.StudentAPIView.as_view()),
# GenericAPIView
path('students2/', views.StudentGenericAPIView.as_view()),
re_path(r'^students2/(?P<pk>\d+)/$', views.StudentGenericAPIView2.as_view()),
]