一.简介

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. 生成signature

    签名规则说明 1. 将参数先按键值排序(只做一级排序),进行key和value的拼接 2. 拼接完后,在最后面再拼接上分配的 appSecret 然后用sha1对拼接串加密 签名示例 假如传入参数: ...

  2. c# tcp udp 的使用场景

    之前用tcp实现了一个案例(远程协助),后来我考虑用udp去实现它,于是又研究了下udp,我发现理论上udp可以做到,但是有一些问题不知道会不会有瓶颈 我参照网上写了一个简单的示例如下 服务端接收.发 ...

  3. CSS中盒子垂直居中的常用方法

    在前端开发过程中,盒子居中是常常用到的.其中 ,居中又可以分为水平居中和垂直居中.水平居中是比较容易的,直接设置元素的margin: 0 auto就可以实现.但是垂直居中相对来说是比较复杂一些的.下面 ...

  4. 1.forEach():遍历数组,并为每个元素调用传入的函数; 举例:

    var a = [1,2,3]; var sum = 0; //传一个参数 a.forEach(function(v){ sum += v; }); console.log(sum);//6 //传三 ...

  5. day63-webservice 02.cxf环境搭建

    指定bin目录的目的是在docs窗口可以直接来执行这里面的命令. ANT这里面

  6. php常用 随机数

    <?php $number =range(1,50); //shuffle 将数组顺序随即打乱. shuffle($number); print_r($number); echo '<br ...

  7. ubuntu 12.04下搭建web服务器(MySQL+PHP+Apache) 教程

    最近,经理让我搭建一个服务器,我从网上找了一篇比较好的教程,按教程一步步执行感觉挺顺利,所以准备整理一下这个教程.尊重原版注明出处:http://news.2ky.cn/Linux/ubuntu-12 ...

  8. Java-Decimal

    import java.math.BigDecimal; import java.text.DecimalFormat; import java.text.NumberFormat; public c ...

  9. SQL Server 索引维护:系统常见的索引问题

    在很多系统中,比如本人目前管理的数据库,索引经常被滥用,甚至使用DTA(数据库引擎优化顾问)来成批创建索引(DTA目前个人认为它的真正用处应该是在发现缺失的统计信息,在以前的项目中,用过一次DTA,里 ...

  10. Log4php使用指南

      一.Log4php简介 Log4php是Log4xx系列日志组件之一,是Log4j迁移到php的版本,主要用来记录日志信息,支持多种输入目的地,包括:日志文件.日志回滚文件.数据库.日志服务器等等 ...