hualinux dj3 2.4:drf普通视图generics及例子

目录

一、关于通用视图generics

1.1 基于类的视图

1.2 关于通用视图

1.2.1 介绍

1.2.2 属性

1.2.3 方法

1.2.4 Mixins

1.2.5 具体的通用视图

1.2.6 其它

二、 drf通用视图generics基本写法

2.1 通用视图简洁写法

2.1.1 写法

2.1.2 作用

2.2 例子

三、例子

3.1 需求

3.2 实现代码

3.3 运行效果


前篇的view视图例子中,我使用的是APIView,但它没有提供有些现成的方法。

一般好的框架,都会提供一些使用频率很高的方法,比如CURD操作,那drf有不有这方面的类的有的,通用视图generics和视图集ViewSets都可以。这篇先讲前者。

本篇例子也是基于《使用drf改写django连接mysql》的项目代码基础上进行修改的。

一、关于通用视图generics

1.1 基于类的视图

drf中视图基本上是基于类的视图,如APIView、通用视图generic、后面的视图庥ViewSets等。

基于类的视图的主要优点之一是它们允许你组合一些可重用的行为。 REST framework通过提供许多预先构建的视图来提供常用的模式来利用这一优点。

1.2 关于通用视图

1.2.1 介绍

REST framework 提供的通用视图允许您快速构建与数据库模型密切映射的API视图。

如果通用视图不适合你的API的需求,你可以选择使用常规 APIView 类,或重用通用视图使用的mixins和基类来组成你自己的一组可重用的通用视图。

此类扩展了REST框架的 APIView 类,为标准list和detail view 添加了通常需要的行为。提供的每个具体通用视图是通过将 GenericAPIView 与一个或多个mixin类组合来构建的。

1.2.2 属性

以下属性控制着基本视图的行为。

  • queryset - 用于从视图返回对象的查询结果集。通常,你必须设置此属性或者重写 get_queryset() 方法。如果你重写了一个视图的方法,重要的是你应该调用 get_queryset() 方法而不是直接访问该属性,因为 queryset 将被计算一次,这些结果将为后续请求缓存起来。
  • serializer_class - 用于验证和反序列化输入以及用于序列化输出的Serializer类。 通常,你必须设置此属性或者重写get_serializer_class() 方法。
  • lookup_field - 用于执行各个model实例的对象查找的model字段。默认为 'pk'。 请注意,在使用超链接API时,如果需要使用自定义的值,你需要确保在API视图和序列化类都设置查找字段。
  • lookup_url_kwarg - 应用于对象查找的URL关键字参数。它的 URL conf 应该包括一个与这个值相对应的关键字参数。如果取消设置,默认情况下使用与 lookup_field相同的值。

上面的意思就是queryset和serializer_class两个属性必须有,如果没有就要重写对应的方法。如果没特殊要求一般添加这2个属性即可

1.2.3 方法

此类提供了一些基础方法

get_queryset(self)

get_object(self)

get_serializer_class(self)

...

这里不写了,自己看。

1.2.4 Mixins

Mixin 类提供用于提供基本视图行为的操作。注意mixin类提供动作方法,而不是直接定义处理程序方法,例如 .get() 和 .post(), 这允许更灵活的行为组成。

Mixin 类可以从 rest_framework.mixins导入。

有了这些Minis就可以直接调用现成的方法使用即可,如

ListModelMixin提供提供一个 .list(request, *args, **kwargs) 方法,实现列出结果集。

看名字都能猜个大概了,同理:

名字提供的方法作用
ListModelMixin.list(request, *args, **kwargs) 列出结果集
CreateModelMixin.create(request, *args, **kwargs) 创建和保存一个新的model实例
RetrieveModelMixin.retrieve(request, *args, **kwargs实现返回响应中现有模型的实例
UpdateModelMixin .update(request, *args, **kwargs) 实现更新和保存现有模型实例
DestroyModelMixin .destroy(request, *args, **kwargs) 实现删除现有模型实例

注:上面这些方法实现都已经帮你写好了,直接使用就行了。如果不符合你的要求你可以重写些方法。

具体看官方文档

1.2.5 具体的通用视图

具体的通用视图

名字作用http方法
CreateAPIView 用于 仅创建 端点。提供一个 post 方法处理程序。
ListAPIView 用于 只读 端点以表示模型实例集合 。提供一个 get 方法处理程序。
RetrieveAPIView用于只读 端点以表示单个模型实例。提供一个 get 方法处理程序。
DestroyAPIView 用于只删除端点以表示单个模型实例。
提供一个 delete 方法处理程序。
UpdateAPIView 用于只更新端点以表示单个模型实例。提供一个 put和patch方法处理程序。
ListCreateAPIView用于读写端点以表示模型实例的集合。提供一个 get 和 post 方法的处理程序
RetrieveUpdateAPIView用于 读取或更新 端点以表示 单个模型实例。提供 get, put 和 patch 方法的处理程序。
RetrieveDestroyAPIView用于 读取或删除 端点以表示 单个模型实例。提供 get 和 delete 方法的处理程序。
RetrieveUpdateDestroyAPIView 提供 get, put, patch 和 delete方法的处理程序。

1.2.6 其它

都看官方文档吧,不想写重复的事

二、 drf通用视图generics基本写法

2.1 通用视图简洁写法

2.1.1 写法

通过上面介绍知道drf通用视图generics的写法,拿我的stu为例子,代码如下:

class StuList(generics.ListCreateAPIView):
    queryset = Stu.objects.all()
    serializer_class = StudentSerializer

当你配置路由映射时,使用get方法得到的结果集的值,即  Stu.objects.all() 的执行结果。

2.1.2 作用

上面3行代码是什么意思呢?

我使用了ListCreateAPIView视图,它提供了提供一个 get 和 post 方法的处理程序。按住ctrl不放,点一下 .ListCreateAPIView 会进入该类,如下图所示:

上图中有: ListModelMixin、CreateModelMixin和GenericAPIView

ListModelMixin提供list方法、 .create方法,刚好对应着ListCreateAPIView的get和post。

drf框架自动帮我们关联了,当get操作就转给这个类的list方法,当post操作就转给create方法。而且这2个方法已经写好默认了,一般情况下你不用修改,直接使用就行了。

 

2.2 例子

我们试下基于《使用drf改写django连接mysql》代码基础上进行一下修改。把APIView部分及url.py配置部分去掉,改成:

from django.http import HttpResponse
from rest_framework import generics
from app.models import Stu
from app.serializers import StudentSerializer

# 主页,普通的django代码
def index(request):
    return HttpResponse("hello django")

# 使用drf通用视图,queryset和serializer_class属性不能少
class StuList(generics.ListCreateAPIView):
    queryset = Stu.objects.all()
    serializer_class = StudentSerializer

url.py部分为:

from django.urls import path
from app import views

urlpatterns = [
    # 主页url映射
    path('', views.index, name="index"),
    # 配置通用视图映射
    # as_view()意思是把类中的方法变成对应的http方法:get、post、pub、delete等
    path('sid/', views.StuList.as_view(), name='stu-list')
]

.as_view作用:

使用视图函数时,django完成URL解析之后,会直接把request对象以及URL解析器捕获的参数(比如re_path中正则表达捕获的位置参数或关键字参数)丢给视图函数,但是在类视图中,这些参数不能直接丢给一个类,所以就有了as_view方法,这个方法只做一件事就是返回一个闭包,这个闭包像视图函数一样接收url解析器传送过来的参数。

 运行一下看一下效果:http://127.0.0.1:8000/sid/,如下图所示:

默认列出了全部。

如果我想一开始只列出第1个呢。可以使用  queryset = Stu.objects.filter(sid='001'),效果如下:

注:不能使用 Stu.objects.get(sid='001') 因为返回的并不是有集合,只是一个stu对象,queryset属性规定是一个集合。

三、例子

3.1 需求

上面例子中的get是没有参数的,如果我想像《使用drf改写django连接mysql》中基于学号查学生成绩这么办,那么就要重写list了。

3.2 实现代码

上面的代码改写如下,添加多一个list方法

from django.http import HttpResponse
from rest_framework import generics
from rest_framework.response import Response
from app.models import Stu
from app.serializers import StudentSerializer


# 主页,普通的django代码
def index(request):
    return HttpResponse("hello django")


# 使用drf通用视图,queryset和serializer_class属性不能少
class StuList(generics.ListCreateAPIView):
    queryset = Stu.objects.all()
    serializer_class = StudentSerializer

    def list(self, request, stuSid):
        # Note the use of `get_queryset()` instead of `self.queryset`
        queryset = Stu.objects.get(sid=stuSid)
        # 不能使用 添加many参数,(queryset, many=True),否则会变成多个对象或查询集
        # 'Stu' object is not iterable
        serializer = StudentSerializer(queryset)
        return Response(serializer.data)

url.py改写如下:

path('sid/<str:stuSid>', views.StuList.as_view(), name='stu-list')

3.3 运行效果

打开浏览器输入  http://127.0.0.1:8000/sid/011,011是sid为011的意思

注:最后不能添加斜杠,http://127.0.0.1:8000/sid/011/ 的话会报错出现404

为什么会这样,因为它把sid看成了'011/',所以报错,找不到。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值