一.简介

Django REST framework是基于Django实现的一个RESTful风格API框架,能够帮助我们快速开发RESTful风格的API。

官网:https://www.django-rest-framework.org/

中文文档:https://q1mi.github.io/Django-REST-framework-documentation/

二. 安装与配置

1.安装

pip install djangorestframework

2.配置

如果想要获取一个图形化的页面,需要将 rest_framework 注册到项目的INSTALL_APPS中。

INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'bms.apps.BmsConfig',
'rest_framework',
]

三.DRF序列化

我们写项目想返回的是json数据,使用DRF的序列化工具serializer会非常方便

url:

    re_path('books/$',views.BooksView.as_view()),
re_path(r'book_pk/(?P<pk>\d+)$', views.BookDetailView.as_view()),

view:

from rest_framework.views import APIView
from app01.serializers import BookModelSerializer
class BooksView(APIView):
# 不带id的查询与新增
"""使用Django REST framework 内置的序列化"""
def get(self, request):
'''以JSON格式返回所有的书籍信息'''
# 1.查出所有的书籍信息
queryset = models.Book.objects.all()
# 2.使用serializers序列化
ser_obj = BookModelSerializer(queryset, many=True) # 多条数据many=True
return Response(ser_obj.data) def post(self, request):
'''创建资源'''
# 1.获取前端提交的数据
# 1.1 APIView
# self.request是谁? 不是Django原来的哪个request self._request才是原来的request
# print(request.data) # APIView 包装的数据
# 2.对数据做有效性校验
ser_obj = BookModelSerializer(data=request.data)
if ser_obj.is_valid():
ser_obj.save() # 调用的是BookSerializer类中的create方法,需要自己去实现
# 3. 拿到序列化的数据去数据库创建新记录
return Response("ok")
else:
return Response(ser_obj.errors) class BookDetailView(APIView):
'''查询具体的书籍,编辑书籍,删除书籍'''
def get(self, request, pk):
# 1,根据pk去查询具体的哪儿本书籍对象
book_obj = models.Book.objects.filter(pk=pk).first()
if book_obj:
# 2. 将书籍对象 序列化成 json格式的数据
ser_obj = BookModelSerializer(book_obj)
# 3. 返回响应
return Response(ser_obj.data)
else:
return Response("无效的书籍id") def put(self, request, pk):
"""修改具体某一本书"""
# 1. 根据pk去查询具体的那本书籍对象
book_obj = models.Book.objects.filter(pk=pk).first()
if book_obj:
# 2. 获取用户 发送过来的数据并且更新对象
# partial=True 允许局部更新,比如只改变部分数据(partial 局部的)
ser_obj = BookModelSerializer(instance=book_obj, data=request.data, partial=True) # form组件中也有类似的实现
if ser_obj.is_valid():
# 3. 保存并返回修改后的数据
ser_obj.save()
return Response(ser_obj.data)
else:
return Response(ser_obj.errors)
else:
return Response("无效的书籍id") def delete(self, request, pk):
'''删除具体某一本书'''
# 1. 根据pk去查询具体的那本书籍queryset对象;注意不是具体的书籍对象,书籍对象没有delete方法
book_obj = models.Book.objects.filter(pk=pk)
if book_obj:
# 删除书籍对象
book_obj.delete()
return Response("删除成功")
else:
return Response("无效的书籍id")
serializers.py
class BookSerializers(serializers.Serializer):
'''使用Serializer,序列化'''
id = serializers.IntegerField(required=False) # required=False 设置为非必须要字段
title = serializers.CharField(max_length=32)
pub_date = serializers.DateField()
CHOICES = ((1, 'Python'), (2, 'Go'), (3, 'Linux'))
# read_only=True 设置为只在查询字段时生效
category = serializers.CharField(source='get_category_display', read_only=True)
# read_only=True 设置为只在添加字段,或修改字段时生效
post_category = serializers.IntegerField(write_only=True) publisher = PublisherSerializer(read_only=True)
post_publisher = serializers.IntegerField(write_only=True) # many= True 当字段对应多条数据时使用
authors = AuthorSerializer(many=True, read_only=True)
post_authors = serializers.ListField(write_only=True) def validate_title(self, attrs):
"""类似于Form组件的局部勾子函数"""
# attrs就是需要检验的这个字段的值
print(attrs) # 红烧牛肉
print('-' * 120)
if '红烧牛肉' in attrs:
raise serializers.ValidationError('你是魔鬼吗?')
else:
return attrs def validate_post_publisher(self, attrs):
# 判断数据库里面有没有你制定的这个出版社
is_exist = models.Publisher.objects.filter(pk=attrs)
if is_exist:
return attrs
else:
raise serializers.ValidationError("你填写的出版社不存在!") # 全局钩子
# def validate(self, attrs):
# pass # 校验合格的数据,要想直接 .save()保存数据必须要重写这个方法
def create(self, validated_data):
# validated_data经过校验的有效数据
book_obj = models.Book.objects.create(
title=validated_data['title'],
pub_date=validated_data['pub_date'],
category=validated_data['post_category'],
publisher_id=validated_data['post_publisher'], #
)
book_obj.authors.set(validated_data['post_authors'])
return book_obj # 在更新数据的时候支持直接调用save()保存数据
def update(self, instance, validated_data):
# print(instance) # 查询出要改变的原数据
# print(validated_data) # 校验合格的更新数据
# 从validated_data中取出数据挨个字段更新
instance.title = validated_data.get('title', instance.title)
instance.pub_date = validated_data.get('pub_date', instance.pub_date)
instance.category = validated_data.get('post_category', instance.category)
instance.publisher_id = validated_data.get('post_publisher', instance.publisher_id)
# 永远都不要高估自己!
instance.save()
# 更新多对多字段的 authors
# 先取出当前书籍的所有作者id
author_list = instance.authors.all().values_list('id') # [(1,),(2,)] ==> [1, 2]
# 然后更新,没变就用原来的数据
instance.authors.set(validated_data.get('post_authors',[i[0] for i in author_list]))
# 返回更新后的数据
return instance # 使用modelserializers
class BookModelSerializer(serializers.ModelSerializer):
'''使用ModelSerializer,序列化'''
# SerializerMethodField 会自动去找 get_字段名 的方法执行(设置了SerializerMethodField)
category_info = serializers.SerializerMethodField(read_only=True) # 查到关联的对象
publisher_info = serializers.SerializerMethodField(read_only=True)
authors_info = serializers.SerializerMethodField(read_only=True) def get_category_info(self, book_obj):
# book_obj ==》 当前被序列化的那个书籍对象
return book_obj.get_category_display() def get_publisher_info(self, book_obj):
# book_obj.pulisher ==> 得到和我这本书关联的出版社对象 # return {
# "id": book_obj.publiser.id,
# "name": book_obj.publiser.name
# }
# ser_obj = PublisherSerializer(book_obj.publisher)
# return ser_obj.data
return PublisherSerializer(book_obj.publisher).data def get_authors_info(self, book_obj):
return AuthorSerializer(book_obj.authors.all(), many=True).data class Meta:
model = models.Book
fields = "__all__"
# depth 1 # 所有有关系的字段都变成 read_only
# exclude = [] # 排除某个字段
extra_kwargs = { # 每个字段的一些额外参数也可更改
'publisher': {'write_only': True},
'authors': {'write_only': True},
'category': {'write_only': True},
}

Django REST framework序列化的更多相关文章

  1. Django REST Framework序列化器

    Django序列化和json模块的序列化 从数据库中取出数据后,虽然不能直接将queryset和model对象以及datetime类型序列化,但都可以将其转化成可以序列化的类型,再序列化. 功能需求都 ...

  2. [Django REST framework - 序列化组件、source、钩子函数]

    [Django REST framework - 序列化组件.source.钩子函数] 序列化器-Serializer 什么是rest_framework序列化? 在写前后端不分离的项目时: 我们有f ...

  3. Django Rest framework序列化流程

    目录 一 什么是序列化 二 Django REST framework配置流程之Serializer 三 Django REST framework配置流程之ModelSerializer 一 什么是 ...

  4. 02 Django REST Framework 序列化

    01-创建序列化类 # 方式一: publish_list = models.Publish.objects.all() # 导入序列化组件 from django.core import seria ...

  5. python学习-- Django REST framework 序列化数据操作

    一.为什么要返回json数据? 一般来说前端要用到从后台返回的数据来渲染页面的时候,这时候后台就需要向前端返回json类型的数据,简单直观便于理解 ,就类似于 {"xxx":{[& ...

  6. Django REST Framework 序列化和校验 知识点

    DRF序列化 Django ORM对象 --> JSON格式的数据 序列化 JSON格式的数据 --> Django ORM数据 反序列化 需要两个工具: from rest_framew ...

  7. django rest framework 序列化组件总结

    序列化组件总结 一. 序列化组件本质上为了实现前后端分离,而进行json序列化的一个组件形式,极大方便了解析数据的作用 二. 所有序列化是基于APIView 解析器实现的,通过内部的多继承关系方便实现 ...

  8. 在django restful framework中设置django model的property

    众所周知,在django的model中,可以某些字段设置@property和setter deleter getter,这样就可以在存入数据的时候进行一些操作,具体原理请参见廖雪峰大神的博客https ...

  9. django restful framework 一对多方向更新数据库

    目录 django restful framework 序列化 一 . 数据模型: models 二. 序列化: serializers 三, 视图: views 四, 路由: urls 五. 测试 ...

随机推荐

  1. Deep Learning 学习笔记(5):Regularization 规则化

    过拟合(overfitting): 实际操作过程中,无论是线性回归还是逻辑回归,其假设函数h(x)都是人为设定的(尽管可以通过实验选择最优). 这样子就可能出线“欠拟合”或者“过拟合”现象. 所谓过拟 ...

  2. 【树莓派智能门锁】使用脚本控制GPIO来开锁【4】

    假定你已经通过此文章或者其他方式完成了树莓派的基本配置 [树莓派]RASPBIAN镜像初始化配置 我们通过VNC View连接到树莓派查看一下~ 1.更新一下基本的设置:更新一下源,把python-d ...

  3. Java面向对象-package import关键字

    Java面向对象-package import关键字 package包关键字,在java中,有包的概念,主要是用来归类 分类作用: 便于项目的开发和维护: 这里截取随便截取一个我最近在开发的一个开源工 ...

  4. 【知识碎片】JavaScript篇

     40.选择器组合 逗号是多选择器空格 是子子孙孙尖括号 只找儿子 39.失去焦点事件blur $("input").blur(function(){ $("input& ...

  5. LINUX的SSH下FTP到远程服务器Entering Passive Mode失败解决

    LINUX 系统FTP连接远程服务器经常出现在传输文件或者发出 ls命令时候出现 "Entering Passive Mode "然后就再也无法运作了.该工作主要是因为LINUX的 ...

  6. jquery slideDown效果

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8&quo ...

  7. 浏览器get请求到java后台的值是乱码

     get方式提交的参数编码,只支持iso8859-1编码. 因此,如果里面有中文,在后台就需要转换编码,如下 String zhongwen = request.getParameter(" ...

  8. linux标准目录结构

    初学Linux,首先需要弄清Linux 标准目录结构 / root --- 启动Linux时使用的一些核心文件.如操作系统内核.引导程序Grub等. home --- 存储普通用户的个人文件 ftp ...

  9. Bean管理注解的例子

  10. Learning from Imbalanced Classes

    https://www.svds.com/learning-imbalanced-classes/ 下采样即 从大类负类中随机取一部分,跟正类(小类)个数相同,优点就是降低了内存大小,速度快! htt ...