django
web服务器
web框架本质
- 对于所有的Web应用,本质上其实就是一个socket服务端,用户的浏览器其实就是一个socket客户端。
- 真实web框架一般会分为两部分:服务器程序和应用程序。
- 1)服务器程序:负责对socket服务器进行封装,并在请求到来时,对请求的各种数据进行整理
- 2)应用程序:负责具体的逻辑处理
socket创建web服务
1 | import socket |
django框架
django、tornado、flask框架比较
django: 重量级web服务器,包含了web开发中常用的功能、组件的框架;ORM、Session、Form、Admin、分页、中间件、信号、缓存….);
Flask: 封装功能不及Django完善,性能不及Tornado,但是Flask的第三方开源组件比丰富;
Tornado: 最大特性就是异步非阻塞、原生支持WebSocket协议;
以 京东、淘宝、楼下小卖部 比喻
django就像京东
,服务齐全,有自营商品,有自己的仓库,有自己的快递,一条龙服务,你懂的flask就像是淘宝
,自己没有商品,没有仓库,没有快递,但是你可以选择三方的(韵达,中通等)tornado就像是门口小卖部
,一个特点,快,不用等,但是东西很少,没有三方组件,需要自己动手写
使用参考
- 1)小型web应用设计的功能点不多,使用Flask比较合适;
- 2)大型web应用设计的功能点比较多,使用的组件也会比较多,使用Django(自带功能多不用去找插件);
- 3)如果追求性能可以考虑Tornado
MVC模式
- M全拼为Model,主要封装对数据库层的访问,对数据库中的数据进行增、删、改、查操作。
- V全拼为View,用于封装结果,生成页面展示的html内容。
- C全拼为Controller,用于接收请求,处理业务逻辑,与Model和View交互,返回结果。
MVT(Django设计模式)
- M全拼为Model,与MVC中的M功能相同,负责和数据库交互,进行数据处理。
- V全拼为View,与MVC中的C功能相同,接收请求,进行业务处理,返回应答。
- T全拼为Template,与MVC中的V功能相同,负责封装构造要返回的html(
或者是json数据
)。
1 | source ~/.bashrc # 执行virtualenvwrapper安装脚本 |
环境安装
virtualenvwrapper使用
1 | mkvirtualenv test1 # 创建虚拟环境 |
使用复习
1 | pip |
django安装
创建虚拟环境
1 | mkvirtualenv djenv # 创建虚拟环境 djenv |
安装Django 2.0.4
1 | pip install django==2.0.4 |
安装慢修改pip源
- 打开我的电脑在地址栏里输入:
%APPDATA%
后回车,然后就进入了C:\Users\Lenovo\AppData\Roaming 这个路劲里面 - 添加文件:
C:\Users\Lenovo\AppData\Roaming \pip\pip.ini
文件,写一下内容
1 | [global] |
创建django项目
创建django项目
1 | (djenv) c:\tmp>workon djenv ## 进入虚拟环境 |
工程目录说明
1 | C:. |
运行开发服务器
- 在开发阶段,为了能够快速预览到开发的效果
- django提供了一个纯python编写的轻量级web服务器,仅在开发阶段使用。
- 可以不写IP和端口,默认IP是127.0.0.1,默认端口为8000
1 | python manage.py runserver ip:端口 |
配置setting.py
配置模板路径
1 | TEMPLATES = [ |
配置静态目录
1 | #像ccs和js这些静态文件如果想要使用必须在这里配置路径 |
注释CSRF
1 | MIDDLEWARE = [ |
修改时区
1 | ## LANGUAGE_CODE = 'en-us' |
创建子应用三部曲
创建子应用
1 | (djenv) c:\tmp\mysite> python manage.py startapp app01 |
1 | C:. |
注册子应用
1 | INSTALLED_APPS = [ |
配置主路由
mysite\urls.py
1 | from django.contrib import admin |
添加子路由
app01/urls.py
1 | from django.urls import path, re_path |
创建视图
app01/views.py
1 | from django.shortcuts import render, HttpResponse |
PyCharm打开项目
添加虚拟环境
- 文件 –》 设置 –》项目:mysite –》 python解释器
添加解释器
配置跨域
1 | 1. 安装包 |
路由配置
Django路由分发
mysite/urls.py
1 | # mysite/urls.py |
普通url
app01/urls.py
1 | from django.urls import path, re_path |
app01/views.py
1 | from django.shortcuts import HttpResponse |
正则的url (\d+)
app01/urls.py
1 | from django.urls import path, re_path |
app01/views.py
1 | from django.shortcuts import HttpResponse |
正则分组(?P<nid>\d+)
- 基于正则分组
(?P<nid>\d+)
,可以不考虑接收参数顺序 (推荐)
app01/urls.py
1 | from django.urls import path, re_path |
app01/views.py
1 | from django.shortcuts import HttpResponse |
使用name构建自己想要的url
app01/urls.py
1 | from django.urls import path, re_path |
app01/views.py
1 | from django.shortcuts import HttpResponse |
反解出url中的name
- 根据request.path中的绝对路径反解出url中的name名字
1 | resolve_url_obj = resolve(request.path) # request.path路径: /student/homework_detail/52 |
请求与响应
请求request
常见request内容
1 | # 1、request.POST # 获取post请求数据 |
app01/views.py
1 | def login(request): |
data.html
1 | <form action="/login/" method="post" enctype="multipart/form-data"> |
响应
HttpResponse
- 需要手动将字符串转化成json字符串并相应到前端
- 传到到前端的是json字符串,还需要手动进行转化
1 | import json |
JsonResponse
- JsonResponse继承HttpResponse
- 数据类型装自动换成json字符串并相应到前端,传到前端的是数据类型而非json字符串
1 | import json |
Response
- 是Django rest-framework框架中封装好的响应对象
- 但是只能在继承于rest-framework的APIView的视图类中使用. 比较推荐.
- 安装:
pip install djangorestframework==3.9.2
1 | from rest_framework.views import APIView |
render
- 返回html页面
1 | def index(request): |
redirect
- 重定向到新的页面
1 | return redirect('https://www.baidu.com') |
类视图
类视图
函数视图弊端
- 以函数的方式定义的视图称为函数视图,函数视图便于理解。
- 但是遇到一个视图对应的路径提供了多种不同HTTP请求方式的支持时
- 便需要在一个函数中编写不同的业务逻辑,代码可读性与复用性都不佳。
1 | def register(request): |
类视图引入
- 在Django中也可以使用类来定义一个视图,称为类视图。
- 使用类视图可以将视图对应的不同请求方式以类中的不同方法来区别定义。
类视图的好处
- 1)代码可读性好
- 2)类视图相对于函数视图有更高的复用性, 如果其他地方需要用到某个类视图的某个特定逻辑,直接继承该类视图即可
类视图原理
- 1)调用流程 as_view–>view–>dispatch
- 2)getattr(‘对象’,’字符串’)
1 | from django.views import View |
类视图添加装饰器
1、 dispatch是父类中用来反射的函数,找对应的函数(比对应函数先执行)
- 2、 比如你发送post请求就可以通过dispatch找到对应的post函数进行处理,get就会找到get函数处理
添加路由
1 | from django.urls import path, re_path |
定义一个装饰器
1 | def my_decorator(func): |
为特定请求方法添加装饰器
- 在类视图中使用为函数视图准备的装饰器时,不能直接添加装饰器
- 需要使用method_decorator将其转换为适用于类视图方法的装饰器。
- method_decorator装饰器使用name参数指明被装饰的方法
1 | from django.shortcuts import HttpResponse |
为特定请求方法添加装饰器
1 | from django.shortcuts import HttpResponse |
类视图Mixin扩展类
- 使用面向对象多继承的特性,可以通过定义父类(作为扩展类)
- 在父类中定义想要向类视图补充的方法,类视图继承这些扩展父类,便可实现代码复用。
- 定义的扩展父类名称通常以Mixin结尾。
1 | class ListModelMixin(object): |
中间件
初识中间件
什么是中间件
- Django中间件是修改 Django request 或者 response 对象的钩子
- 可以理解为是介于 HttpRequest 与 HttpResponse 处理之间的一道处理过程。
- Django中间件作用:
- 修改请求,即传送到 view 中的 HttpRequest 对象。
- 修改响应,即 view 返回的 HttpResponse 对象。
中间件处理过程
- 1、首先客户端发起请求,会将请求交给settings.py中排在最前面的中间件
- 2、前面中间件收到请求会调用类中的process_request方法处理,然后交给下一个中间件的process_request函数
- 3、到达最后一个中间件的process_request函数处理后会到达url路由系统
- 4、然后从路由系统直接跳转到第一个中间件的process_view函数,依次向后面中间的process_view传递
- 最后到达views.py处理函数,获取网页中的数据
- 5、获取的数据会交给最后一个中间件的process_response方法处理,然后依次向前面的中间件process_response
- 方法提交请求的内容,最后由最前面的中间件将请求数据返回到客户端
- 6、在任一中间件的process_request和process_view方法中有返回值就会直接返回给process_response
生命周期图解
- 1、首先会交给中间件,中间件处理后交给路由系统
- 2、路由系统
- 1:Django程序会到urls.py文件中找到对应请求的处理函数(视图函数)
- 3、视图函数
- 1:视图函数会找到对应的html模板文件
- 2:然后到数据库中取得数据替换html模板中的内容
- 3:使用static中的js和css文件结合对html渲染
- 4:最后Django将最终渲染后的html文件返回给中间件
- 4、中间件再调用process_response方法处理,最后交给用户
.中间件使用
创建存放中间件的文件夹
- 在工程目录下创建任意目录,这里创建路径为:
/project/middle/m1.py
- 在工程目录下创建任意目录,这里创建路径为:
settings.py中注册中间件
1 | MIDDLEWARE = [ |
写处理函数test
- 在views.py文件中写处理函数test
1 | def test(request): |
定义中间件
- 在/project/middle/m1.py文件中定义中间件
1 | from django.utils.deprecation import MiddlewareMixin |
cookie
cookie
cookie简介
- 1.cookie实质就是客户端硬盘中存放的键值对,利用这个特性可以用来做用户验证
- 2.比如:{“username”: “dachengzi”} #再次访问url就会携带这些信息过来
前端操作cookie
- 说明: 使用下面方法操cookie必须先引入jquery.cookie.js
- 前端获取cookie值: var v = $.cookie(‘per_page_count’);
- 前端设置cookie值: $.cookie(‘per_page_count’,v);
后端操作cookie
- 说明: response = HttpResponse(…) 或 response = render(request, …)
- 后端设置cookie值: response.set_cookie(‘username’,”zhangsan”)
- 后端后去cookie值: request.COOKIES.get(‘username’)
设置cookie时常用参数
1 | def cookie(request): |
使用cookie实现用户登录、注销
views.py
1 | from django.shortcuts import render,HttpResponse,redirect |
login.html
1 | <!DOCTYPE html> |
CSRF原理
- 1、当用户第一次发送get请求时,服务端不仅给客户端返回get内容,而且中间包含一个随机字符串
- 2、这个字符串是加密的,只有服务端自己可以反解
- 3、当客户端发送POST请求提交数据时,服务端会验证客户端是否携带这个随机字符串, 没有就会引发csrf错误
- 4、如果没有csrf,那么黑客可以通过任意表单向我们的后台提交数据,不安全
session
Session
原理
1 | session操作依赖cookie |
- 1.基于Cookie做用户验证时:敏感信息不适合放在cookie中
- 2.用户成功登陆后服务端会生成一个随机字符串并将这个字符串作为字典key,将用户登录信息作为value
- 3.当用户再次登陆时就会带着这个随机字符串过来,就不必再输入用户名和密码了
- 4.用户使用cookie将这个随机字符串保存到客户端本地,当用户再来时携带这个随机字符串
- 服务端根据这个随机字符串查找对应的session中的值,这样就避免敏感信息泄露
Cookie和Session对比
- 1、Cookie是保存在用户浏览器端的键值对
- 2、Session是保存在服务器端的键值对
setting.py配置session
- 公用配置
1 | # 1、SESSION_COOKIE_NAME = "sessionid" # Session的cookie保存在浏览器上时的key,即:sessionid=随机字符串(默认) |
- settings.py中配置使用session五种方法
1 | #1 数据库(默认) #将session数据保存到数据库中 |
操作session
1 | def index11(request): #request.session中存放了所有用户信息 |
session登录和注销
session实现用户十秒免登陆,以及注销功能
主要功能说明
- 1.session默认使用数据库session,使用前必须先执行下面命令
- python manage.py makemigrations
- python manage.py migrate
- 2.settings.py中配置每次用户访问都会推辞更新时间
- SESSION_SAVE_EVERY_REQUEST = True
- 3.实现10s免登陆关键步骤
- 1)设置session : request.session[‘is_login’] = True
- 2)设置10s超时: request.session.set_expiry(10)
- 3)获取session : request.session.get(‘is_login’)
views.py
1 | from django.shortcuts import render,HttpResponse,redirect |
login.html
1 |
|
index.html
1 |
|
settings.py
1 | SESSION_SAVE_EVERY_REQUEST = True |
model以及数据连接
创建数据库
创建mysql库
1 | mysql> create database testdb charset utf8; # 创建数据库 |
创建用户并授权
1 | # 1、创建用户 |
配置django
安装PyMySQL
1 | pip install PyMySQL |
主动修改为pymysql
- Django默认使用MySQLdb模块链接MySQL,但在python3中还没有MySQLdb
- 主动修改为pymysql,在project同名文件夹下的__init__文件中添加如下代码即可
1 | from pymysql import install_as_MySQLdb |
修改DATABASES配置
1 | DATABASES = { |
创建表
1 | python manage.py makemigrations |
定义模型
定义模型举例
- 模型类被定义在”应用/models.py”文件中。
- 模型类必须继承自Model类,位于包django.db.models中。
1 | from django.db import models |
源信息Meta
1 | from django.db import models |
字段
常用字段
1 | from django.db import models |
不常用字段
1 | URLField(CharField) |
参数
选项 | 说明 |
---|---|
null | 如果为True,表示允许为空,默认值是False |
blank | 如果为True,则该字段允许为空白,默认值是False |
db_column | 字段的名称,如果未指定,则使用属性的名称 |
db_index | 若值为True, 则在表中会为此字段创建索引,默认值是False |
default | 默认 |
primary_key | 若为True,则该字段会成为模型的主键字段,默认值是False,一般作为AutoField的选项使用 |
unique | 如果为True, 这个字段在表中必须有唯一值,默认值是False |
related_name | 在关联查询中,代替单一对象查找多对象 对象名小写_set(book.heroinfo_set.all() 的写法 |
auto_now_add | 只在数据添加的时候,记录时间 |
auto_now | 数据添加和更新的时候,记录时间 |
一对多创建表
创建一对多表
1 | from django.db import models |
可选参数
1 | 1、to, # 要进行关联的表名 |
#1.3 一对多基本查询
1 | from django.shortcuts import render,HttpResponse |
正向反向查
related_query_name设置
1 | from django.db import models |
正向方向查
1 | from django.shortcuts import HttpResponse |
values和values_list
1 | from django.shortcuts import HttpResponse |
多对多
不创建第三张表推荐
(法1)
- 第一种: 自己不创建第三张关系表,有m2m字段: 根据queryset对象增删改查(推荐)
创建表
1 | from django.db import models |
根据queryset对象操作
1 | from django.shortcuts import HttpResponse |
自己创建第三张关系表(法2)
- 第二种: 自己创建第三张关系表,无 m2m 字段,自己链表查询
1 | from django.db import models |
根据外检ID操作(法3)
- 第三种: 自己不创建第三张关系表,有m2m字段: 根据数字id增删改查
创建表
1 | from django.db import models |
根据id增删改查
1 | from django.shortcuts import HttpResponse |
ManyToManyField参数
- 创建m2m多对多时ManyToManyField可以添加的参数
1 | 1、to, # 要进行关联的表名 |
values和values_list
1 | from django.shortcuts import HttpResponse |
一大波Model操作
基本操作
1 | from django.shortcuts import HttpResponse |
进阶操作
进阶操作:牛掰掰的双下划线
1 | 1、大于,小于 |
时间过滤
- 根据天/小时进行过滤
1 | from django.utils import timezone |
F()和Q()查询
F()
- F() —- 专门取对象中某列值的操作
- 作用:F()允许Django在未实际链接数据的情况下具有对数据库字段的值的引用
1 | from django.shortcuts import HttpResponse |
Q()
Q查询基本使用
- 1、Q对象(django.db.models.Q)可以对关键字参数进行封装,从而更好地应用多个查询
- 2、可以组合使用 &(and),|(or),~(not)操作符,当一个操作符用于两个Q的对象,它产生一个新的Q对象
- 3、如: Q(Q(nid=8) | Q(nid__gt=10)) & Q(caption=’root’)
1 | from django.shortcuts import HttpResponse |
动态添加查询条件
- 动态添加多个and和or查询条件
项目中动态添加or查询条件
1 | def table_search(request,admin_class,object_list): |
or动态添加多个查询条件
1 | # or动态添加多个查询条件 |
and和or结合查询
1 | # and和or结合查询 |
aggregate和annotate
aggregate聚合函数
- 作用:从数据库中取出一个汇总的集合
aggregate求最大值、最小值、平局值等
1 | from django.db.models import Count,Avg,Max,Sum |
实现聚合group by查询
- **作用:**对查询结果进行分组,比如分组求出各年龄段的人数
- 注: annotate后面加filter过滤相当于原生sql语句中的having
1 | from django.db.models import Count, Avg, Max, Min, Sum |
aggregate和annotate区别
- Aggregate作用是从数据库取出一个汇总的数据(比如,数量,最大,最小,平均等)
- 而annotate是先按照设定的条件对数据进行分组,然后根据不同组分别对数据进行汇总
DRF框架
web开发两种模式
前后端不分离
- 前端看到的效果都是由后端控制的
- 后端通过渲染之后给前端返回完整的html页面,前端与后端的耦合度很高
前后端分离
- 后端仅返回前端所需的数据,至于数据怎么进行展示
- 由前端自己进行控制,前端与后端的耦合度很低
开发模式对比
前后端不分离
:完整的页面是在后端生成的,后端给前端返回完整的页面,前端只是进行展示。前后端分离
:完整的页面是在前端生成的,后端只给前端返回所需的数据,前端将数据填充在页面上。优缺点比较:
- 前后端不分离适合于纯网页的应用,前后端分离可以对接不同类型的客户端。
开发模式 | 优点 | 缺点 |
---|---|---|
前后端不分离 | 利于SEO(搜索引擎优化) | 仅适合于纯网页的应用 |
前后端分离 | 可以对接不同类型的客户端 | 不利于SEO(搜索引擎优化) |
Restful风格
RESTFUL风格
什么是RESTful风格
详情查看博客地址:https://www.cnblogs.com/xiaonq/p/10053234.html
什么是RESTful
- REST与技术无关,代表的是
一种软件架构风格
(REST是Representational State Transfer的简称,中文翻译为“表征状态转移”) - REST从资源的角度类审视整个网络,它将分布在网络中某个节点的
资源通过URL进行标识
- 所有的数据,不过是通过网络获取的还是
操作(增删改查)
的数据,都是资源,将一切数据视为资源是REST区别与其他架构风格的最本质属性 - 对于REST这种面向资源的架构风格,有人提出一种全新的结构理念,即:面向资源架构(ROA:Resource Oriented Architecture)
web开发本质
- 对数据库中的表进行增删改查操作
- Restful风格就是把所有数据都当做资源,对表的操作就是对资源操作
- 在url同通过 资源名称来指定资源
- 通过 get/post/put/delete/patch 对资源的操作
RESTful设计规范
URL路径
面向资源编程
: 路径,视网络上任何东西都是资源,均使用名词表示(可复数),不要使用动词
1 | # 不好的例子:url中含有动词 |
请求方式
- 访问同一个URL地址,采用不同的请求方式,代表要执行不同的操作
- 常用的HTTP请求方式有如下四种:
请求方式 | 说明 |
---|---|
GET | 获取资源数据(单个或多个) |
POST | 新增资源数据 |
PUT | 修改资源数据 |
DELETE | 删除资源数据 |
- 例如
1 | GET /books # 获取所有图书数据 |
过滤信息
过滤,分页,排序
:通过在url上传参的形式传递搜索条件- 常见的参数:
1 | ?limit=10 # 指定返回记录的数量。 |
响应状态码
- 重点状态码
1 | '''1. 2XX请求成功''' |
- 详细状态码
1 | '''1. 2XX请求成功''' |
DRF框架作用
DRF核心任务
DRF核心任务
- 序列化:将对象转换为字典或者json的过程。
- 反序列化:将字典或json转换保存到对象中的过程。
- RestAPI核心工作:
- 将数据库中的数据序列化为前端所需的格式,并进行返回。
- 将前端传递的数据反序列化保存为模型类对象,并保存到数据库。
- 在开发REST API接口时,视图中主要做了三件事:
- ① 将请求的数据(如:JSON格式)转换为模型类对象
- ② 操作数据库
- ③ 将模型类对象转换为响应的数据(如:JSON格式)
序列化
- 广义的概念:将一种数据转换为另外一种格式的过程。
- 本课程特指:
将对象转换为字典或json的过程
。
反序列化
- 广义的概念:和序列化相反的转换过程。
- 本课程特指:将字典或json转换为对象的过程。
Django REST framework 简介
作用
- Django REST framework可以帮助我们大大提高REST API的开发速度。
- 在序列化与反序列化时,虽然操作的数据可能不同,但是过程是相似的,这部分操作DRF框架进行了封装。
- 在开发REST API的视图时,虽然每个视图操作的数据可能不同
- 但增、删、改、查的基本流程是一样的,这部分代码DRF框架也进行了封装。
- 增:校验请求数据 → 反序列化-将数据保存到对象中 → 保存数据到数据库 → 将保存的对象序列化返回
- 删:判断要删除的数据是否存在 → 执行数据库删除 → 返回响应
- 改:判断要修改的数据是否存在 → 校验请求的数据 → 反序列化-将数据保存到对象中 → 保存数据到数据库 → 将保存的对象序列化返回
- **查(1个或多个)**:查询数据库 → 将数据序列化返回
特点
- 提供了定义序列化器的方法,使用序列化器可以进行数据的序列化和反序列化
- 提供了丰富的类视图、Mixin扩展类、子类视图、视图集,简化视图代码的编写
- 多种身份认证和权限控制方式的支持
- 内置了限流系统
- 直观的API web界面
- 可扩展性,插件丰富
参考资料:DRF框架官方文档(opens new window)
**总结
**:
- 作用:快速开发RestAPI接口。
- 特点:进行了大量封装,提高API开发速度。
- 核心功能:序列化器和视图。
04.环境安装与使用
安装djangorestframework
- DRF框架依赖于Django,
需要先安装Django环境,再安装djangorestframework
1 | pip install djangorestframework==3.11.0 # 安装djangorestframework |
- 创建django环境
1 | # ① 创建一个名为django2.2的虚拟环境 |
DRF配置
创建一个测试项目
1 | (django2.2) C:\Users\Lenovo> cd C:\tmp |
DRF应用注册
- setting.py中注册djangorestframework
1 | INSTALLED_APPS = [ |
路由分发
drf_demo/urls.py
1 | from django.contrib import admin |
定义模型
1 | from django.db import models |
- 创建表
1 | (django2.2) C:\tmp\drf_demo> python manage.py makemigrations |
DRF框架功能演示
步骤1:创建序列化器类
- 在
book
应用中新建serializers.py
用于保存所要创建的序列化器类。
1 | from rest_framework import serializers |
小知识:
- model:指定该序列化器类所对应的模型类
- fields:指定依据模型类的哪些字段生成对应序列化器类的字段,__all__代表所有
步骤2:编写视图
book/views.py
1 | from rest_framework.viewsets import ModelViewSet |
小知识:
- queryset:指定视图在进行数据查询时所使用的查询集
- serializer_class:指定视图在进行序列化或反序列化时所使用的序列化器类
步骤3:定义路由
book/urls.py
1 | from django.urls import re_path |
- 小知识:什么是路由Router?
- 答:动态生成视图集中的处理方法的url配置项。
步骤四:测试接口
测试获取所有图书接口
1 | http://127.0.0.1:8000/book/book/ |
- 返回结果
1 | { |
测试创建图书接口
测试修改图书接口
1 | http://127.0.0.1:8000/book/book/1/ |
测试删除数据接口
1 | http://127.0.0.1:8000/book/book/1/ |
Serializer
Serializer介绍
- Serializer三个作用
- 第一:序列化
- 第二: 反序列化
- 第三:数据校验
定义Serializer
1 | # -*- coding: utf-8 -*- |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
#1.2 序列化:作用1
1 | class APIViewBookInfoViewSet(APIView): |
#1.3 反序列化:作用2
1 | # 创建 |
#1.4 字段校验:作用3
1 | class BookInfoSerializer1(serializers.Serializer): |
序列化&反序列化
book/models.py
1 | from django.db import models |
book/serializers.py
1 | # -*- coding: utf-8 -*- |
book/views.py
1 | from rest_framework.views import APIView |
[ book/urls.py
1 | from django.urls import re_path,path |
测试接口
get获取数据
1 | [ |
post添加数据
put修改数据
嵌套序列化
book/serializers.py
1 | from rest_framework import serializers |
查询结果
1 | [ |
字段类型和选项参数
通用参数
- 无论哪种字段类型都可以使用的选项参数。
参数名称 | 说明 |
---|---|
read_only | 表明该字段仅用于序列化输出,默认False |
write_only | 表明该字段仅用于反序列化输入,默认False |
required | 表明该字段在反序列化时必须输入,默认True |
default | 序列化和反序列化时使用的默认值 |
error_messages | 包含错误编号与错误信息的字典 |
label | 用于HTML展示API页面时,显示的字段名称 |
注:定义序列化器类的字段时,如果没有指定read_only和write_only,则这两个参数默认值都为False,表明对应的字段既在序列化时使用,也在反序列化时使用。
常用字段类型
字段 | 字段构造方式 |
---|---|
BooleanField | BooleanField() |
NullBooleanField | NullBooleanField() |
CharField | CharField(max_length=None, min_length=None, allow_blank=False, trim_whitespace=True) |
EmailField | EmailField(max_length=None, min_length=None, allow_blank=False) |
RegexField | RegexField(regex, max_length=None, min_length=None, allow_blank=False) |
SlugField | SlugField(max_length=50, minlength=None, allow_blank=False) 正则字段,验证正则模式 [-a-zA-Z0-9-]+ |
URLField | URLField(max_length=200, min_length=None, allow_blank=False) |
UUIDField | UUIDField(format=’hex_verbose’) format: 1) 'hex_verbose' 如"5ce0e9a5-5ffa-654b-cee0-1238041fb31a" 2) 'hex' 如 "5ce0e9a55ffa654bcee01238041fb31a" 3)'int' - 如: "123456789012312313134124512351145145114" 4)'urn' 如: "urn:uuid:5ce0e9a5-5ffa-654b-cee0-1238041fb31a" |
IPAddressField | IPAddressField(protocol=’both’, unpack_ipv4=False, **options) |
IntegerField | IntegerField(max_value=None, min_value=None) |
FloatField | FloatField(max_value=None, min_value=None) |
DecimalField | DecimalField(max_digits, decimal_places, coerce_to_string=None, max_value=None, min_value=None) max_digits: 最多位数 decimal_palces: 小数点位置 |
DateTimeField | DateTimeField(format=api_settings.DATETIME_FORMAT, input_formats=None) |
DateField | DateField(format=api_settings.DATE_FORMAT, input_formats=None) |
TimeField | TimeField(format=api_settings.TIME_FORMAT, input_formats=None) |
DurationField | DurationField() |
ChoiceField | ChoiceField(choices) choices与Django的用法相同 |
MultipleChoiceField | MultipleChoiceField(choices) |
FileField | FileField(max_length=None, allow_empty_file=False, use_url=UPLOADED_FILES_USE_URL) |
ImageField | ImageField(max_length=None, allow_empty_file=False, use_url=UPLOADED_FILES_USE_URL) |
ListField | ListField(child=, min_length=None, max_length=None) |
DictField | DictField(child=) |
ModelSerializer
ModelSerializer
ModelSerializer特点
- ModelSerializer是Serializer类的子类
- 相对于Serializer,增加了以下功能:
- 基于模型类字段自动生成序列化器类的字段
- 包含默认的create()和update()方法的实现
定义ModelSerializer语法
1 | from rest_framework import serializers |
查看自动生成字段
1 | (django2.2) C:\tmp\drf_demo>python manage.py shell -i ipython |
ModelSerializer使用
book/serializers.py
1 | # -*- coding: utf-8 -*- |
查询结果
1 | [ |
多对多序列化
1 | # -*- coding: utf-8 -*- |
APIVIEW
DRF全局配置
settings.py注册
- 注册
1 | INSTALLED_APPS = [ |
全局配置DRF
1 | # 过滤器 |
APIView基本使用
book/models.py
1 | from django.db import models |
book/serializers.py
1 | # -*- coding: utf-8 -*- |
book/views.py
1 | from rest_framework.views import APIView |
book/urls.py
1 | from django.urls import re_path,path |
测试接口
get获取数据
1 | [ |
post添加数据
put修改数据
自定义分页
自定义分页
1 | from rest_framework.views import APIView |
测试分页效果
1 查找第一页,每页显示两条数据
认证权限
使用自带权限
1 | # 注:认证类都在 `rest_framework.authentication` 模块中 |
自定义权限
自定义权限
1 | from rest_framework.permissions import BasePermission |
使用自定义权限
1 | # 注:认证类都在 `rest_framework.authentication` 模块中 |
限流
全局配置
DEFAULT_THROTTLE_RATES
可以使用second
、minute
、hour
或day
来指明限流周期。
1 | REST_FRAMEWORK = { |
指定视图配置
- 也可以某个视图中通过
throttle_classes
属性来指定某视图所使用的限流控制类
1 | from rest_framework.throttling import AnonRateThrottle |
过滤
自定义过滤
1 | from django_filters.rest_framework import DjangoFilterBackend |
测试过滤功能
http://127.0.0.1:8000/book/book1/?btitle=西游记
排序
配置排序
1 | from django_filters.rest_framework import DjangoFilterBackend |
测试排序功能
http://127.0.0.1:8000/book/book1/?ordering=-id
初始化项目结构
初始化项目结构
1 | └─shiyanlou_project # 项目根路径 |
创建Django项目
1 | root@dev:shiyanlou_project# workon syl |
使用pycharm打开项目
1.右击—->编辑配置—–>
PYTHONUNBUFFERED 1 DJANGO_SETTINGS_MODULE syl.settings
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
- 
- 2.文件---->设置----->
- 
- 3.文件---->设置----->
- 
### 创建user模型
#### 创建用户模型user
```python
python ../manage.py startapp user # 创建user模型
1
在setting.py中注册user模型(第一步)
1 | INSTALLED_APPS = [ |
- 要想让pycharm识别要这样操作
syl/urls.py添加主路由(第二步)
1 | urlpatterns = [ |
syl/settings.py中添加apps路径
1 | # 把apps目录插入,到系统包搜索路径第一个位置中 |
创建 user/urls.py子路由文件(第三步)
1 | from django.urls import path |
重写Django默认认证用户模型
重写django user表
1 | from django.db import models |
syl/settings.py中注册
1 | # 注册自己的用户模型类: 应用名.模型名,指定我们重写的User表进行身份验证 |
配置mysql
1 | '''1.创建mysql数据库''' |
生成表
1 | python manage.py makemigrations |
python中的三种路径
操作系统绝对路径(第一种)
- django 静态文件查找, 模板查找(第一种)
1 | # 去配置好的 文件夹 中查找指定的文件 |
django 导包路径(第二种)
- 第一:
当期文件夹
- 第二:
sys.path
1 | 导包之前, 包的上级路径, 需要存在于 python system 的 path |
django模型引用(第三种)
1 | 想使用 一个 models.py 文件中的模型 |
ModelViewSet
DRF初始化
- 1.DRF框架的8个核心功能
1 | 1.认证(用户登录校验用户名密码或者token是否合法) |
2.相关包
1 | '''1.序列化相关''' |
安装DRF
1 | pip install djangorestframework==3.11.0 # 安装djangorestframework |
在syl/settings.py中注册
1 | INSTALLED_APPS = [ |
syl/settings.py配置DRF
1 | # 过滤器 |
DRF使用
- 认证、权限、限流、分页、过滤、序列化
user/urls.py
- ModelViewSet注册路由三部曲
1 | from django.urls import include, path |
1 | [<URLPattern '^user/$' [name='user-list']>, |
serializers.py
- 创建
user/serializers.py
写序列化器 - 功能一:数据校验,
创建/修改数据
- 在创建数据或者修改数据时校验用户提交的数据是否合法
- 用户名必须是8位以上,邮箱、手机号是合法的
- 功能二:序列化
- 把通过model查询的queryset对象转换成JSON格式
1 | from rest_framework import serializers |
user/views.py
1 | from django.http import HttpResponse |
测试接口
查询 接口
- 查询路由
1 | #1.查询所有用户 |
- 增加(POST)
1 | #1.增加用户 |
- 修改(PUT)
1 | # 修改用户信息 |
- 删除(DELETE)
1 | # 删除用户 |
自定义认证权限
测试全局权限
功能
- 在浏览器中,打开任意接口,未登录用户只能发送get请求,只有登录用户才能发送post等请求
1 | # http://192.168.56.100:8888/user/user/ |
测试自定义权限
功能
注:自定义权限会覆盖settings.py中配置的全局权限
- 1.自定义权限(
其实应该写到一个单独的文件内进行公用,这里先写到这里进行测试
)
1 | # 自定义权限(局部) |
- 2.
user/viesws.py视图函数中指定当前视图要用的
权限类
1 | class UserViewSet(viewsets.ModelViewSet): |
限流
syl/settings.py中配置限流
1 | http://192.168.56.100:8888/user/apiview/ |
序列化
user/serialzers.py
1 | from rest_framework import serializers |
自定义分页
1 | http://192.168.56.100:8888/user/user/?page=1&page_size=1 |
1
- 1.
user/views.py
中定义自定义分页类
1 | # 分页(局部):自定义分页器 局部 |
- 2.
user/views.py
视图函数中使用
1 | class UserViewSet(viewsets.ModelViewSet): |
过滤和排序
- 测试url
1 | #1.过滤:查询 用户名(tom),激活的用户 |
user/views.py
视图函数中配置过滤和排序字段
1 | class UserViewSet(viewsets.ModelViewSet): |
多对多序列化
1 | # -*- coding: utf-8 -*- |
其他用法
views.py
1 | from rest_framework import viewsets, status |
serializers.py
1 | class DAppSerializer(DynamicFieldsSerializerMixin, serializers.ModelSerializer): |
filters.py
1 | class DAppFilter(FilterSet): |