django rest framework 自定义返回方式


Posted in Python onJuly 12, 2020

大家在用Django Rest Framework的时候会发现默认继承后,增删改查的返回信息都是一段data,这是因为我实际是状态码和信息你在调用api的时候是看不到的,仅仅如此么?并不是这样,在我前端调用后端的时候,实际上相关的code和msg是能看得到的,但是我们在普通的调用api他只是单单的返回data信息,这个是不够我们满足需求的,毕竟我们不仅仅需要用前端需调用,下面我们来自定义Response返回信息

Django(2.0)

Django Rest Framework

Python3.6

1、自定义Response,继承rest framework的Response

#这个方法py文件我们可以写到任意地方,目的是在我们需要写一个Baseview的时候将放回方法引用

from django.utils import six
from rest_framework.response import Response
from rest_framework.serializers import Serializer

class JsonResponse(Response):
 """
 An HttpResponse that allows its data to be rendered into
 arbitrary media types.
 """

 def __init__(self, data=None, code=None, msg=None,
     status=None,
     template_name=None, headers=None,
     exception=False, content_type=None):
  """
  Alters the init arguments slightly.
  For example, drop 'template_name', and instead use 'data'.
  Setting 'renderer' and 'media_type' will typically be deferred,
  For example being set automatically by the `APIView`.
  """
  super(Response, self).__init__(None, status=status)

  if isinstance(data, Serializer):
   msg = (
    'You passed a Serializer instance as data, but '
    'probably meant to pass serialized `.data` or '
    '`.error`. representation.'
   )
   raise AssertionError(msg)

  self.data = {"code": code, "message": msg, "data": data}
  self.template_name = template_name
  self.exception = exception
  self.content_type = content_type

  if headers:
   for name, value in six.iteritems(headers):
    self[name] = value

2、重写Base类,将增删改查方法重写并且返回方法为刚刚定义好的新的Response类

#Base类,将增删改查方法重写
#!/usr/bin/env python
# -*- coding:utf-8 -*-

from assets import serializers
from assets import models
from rest_framework.response import Response
from rest_framework import status
from rest_framework import viewsets
from rest_framework.decorators import action
from rest_framework.pagination import PageNumberPagination
from django.shortcuts import get_object_or_404
from common.utils.custom_response import JsonResponse
from rest_framework import filters
from django_filters import rest_framework
from django_filters.rest_framework import DjangoFilterBackend

class CustomViewBase(viewsets.ModelViewSet):
 # pagination_class = LargeResultsSetPagination
 # filter_class = ServerFilter
 queryset = ''
 serializer_class = ''
 permission_classes = ()
 filter_fields = ()
 search_fields = ()
 filter_backends = (rest_framework.DjangoFilterBackend, filters.SearchFilter, filters.OrderingFilter,)

 def create(self, request, *args, **kwargs):
  serializer = self.get_serializer(data=request.data)
  serializer.is_valid(raise_exception=True)
  self.perform_create(serializer)
  headers = self.get_success_headers(serializer.data)
  return JsonResponse(data=serializer.data,msg="success",code=201,status=status.HTTP_201_CREATED,headers=headers)

 def list(self, request, *args, **kwargs):
  queryset = self.filter_queryset(self.get_queryset())
  page = self.paginate_queryset(queryset)
  if page is not None:
   serializer = self.get_serializer(page, many=True)
   return self.get_paginated_response(serializer.data)

  serializer = self.get_serializer(queryset, many=True)
  return JsonResponse(data=serializer.data,code=200,msg="success",status=status.HTTP_200_OK)

 def retrieve(self, request, *args, **kwargs):
  instance = self.get_object()
  serializer = self.get_serializer(instance)
  return JsonResponse(data=serializer.data,code=200,msg="success",status=status.HTTP_200_OK)

 def update(self, request, *args, **kwargs):
  partial = kwargs.pop('partial', False)
  instance = self.get_object()
  serializer = self.get_serializer(instance, data=request.data, partial=partial)
  serializer.is_valid(raise_exception=True)
  self.perform_update(serializer)

  if getattr(instance, '_prefetched_objects_cache', None):
   # If 'prefetch_related' has been applied to a queryset, we need to
   # forcibly invalidate the prefetch cache on the instance.
   instance._prefetched_objects_cache = {}

  return JsonResponse(data=serializer.data,msg="success",code=200,status=status.HTTP_200_OK)

 def destroy(self, request, *args, **kwargs):
  instance = self.get_object()
  self.perform_destroy(instance)
  return JsonResponse(data=[],code=204,msg="delete resource success",status=status.HTTP_204_NO_CONTENT)

3、view视图继承以及测试

class BatchLoadView(CustomViewBase):
 queryset = models.Manufacturer.objects.all()
 serializer_class = serializers.ManufacturerSerializer

 def list(self, request, *args, **kwargs):
  return JsonResponse(code=200, data=[], msg="testings")

这样我们就完成了自定义返回信息,下一节将讲解自定义异常

补充知识:django rest framework 自定义异常返回

上一节给大家介绍了自定义Response返回信息,但那个只用于正确的返回success,但是当我们用到了权限

auth 401、方法不允许method 405,等等,这时候我们就用自己自定义异常返回信息

1、定义settings配置文件

#定义异常返回的路径脚本位置

REST_FRAMEWORK = {
  'EXCEPTION_HANDLER': 'common.utils.custom_execption.custom_exception_handler',
}

2、定义脚本

#注意,脚本路径需要与settings.py 定义的一样

from rest_framework.views import exception_handler

def custom_exception_handler(exc, context):
  # Call REST framework's default exception handler first,
  # to get the standard error response.
  response = exception_handler(exc, context)

  # Now add the HTTP status code to the response.
  if response is not None:
    print(response.data)
    response.data.clear()
    response.data['code'] = response.status_code
    response.data['data'] = []

    if response.status_code == 404:
      try:
        response.data['message'] = response.data.pop('detail')
        response.data['message'] = "Not found"
      except KeyError:
        response.data['message'] = "Not found"

    if response.status_code == 400:
      response.data['message'] = 'Input error'

    elif response.status_code == 401:
      response.data['message'] = "Auth failed"

    elif response.status_code >= 500:
      response.data['message'] = "Internal service errors"

    elif response.status_code == 403:
      response.data['message'] = "Access denied"

    elif response.status_code == 405:
      response.data['message'] = 'Request method error'
  return response

#无需调用,报错的时候他自己会调用!!

以上这篇django rest framework 自定义返回方式就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
从零学python系列之从文件读取和保存数据
May 23 Python
Python实现短网址ShortUrl的Hash运算实例讲解
Aug 10 Python
python 获取list特定元素下标的实例讲解
Apr 09 Python
django中模板的html自动转意方法
May 27 Python
浅谈Python大神都是这样处理XML文件的
May 31 Python
python中将两组数据放在一起按照某一固定顺序shuffle的实例
Jul 15 Python
Python imageio读取视频并进行编解码详解
Dec 10 Python
Python列表切片常用操作实例解析
Dec 16 Python
Python实现计算长方形面积(带参数函数demo)
Jan 18 Python
django 连接数据库出现1045错误的解决方式
May 14 Python
如何用python处理excel表格
Jun 09 Python
python正则表达式的懒惰匹配和贪婪匹配说明
Jul 13 Python
Django+RestFramework API接口及接口文档并返回json数据操作
Jul 12 #Python
Python3交互式shell ipython3安装及使用详解
Jul 11 #Python
Python QTimer实现多线程及QSS应用过程解析
Jul 11 #Python
面向新手解析python Beautiful Soup基本用法
Jul 11 #Python
基于python实现判断字符串是否数字算法
Jul 10 #Python
基于python实现计算两组数据P值
Jul 10 #Python
Python3爬虫中关于Ajax分析方法的总结
Jul 10 #Python
You might like
社区(php&&mysql)一
2006/10/09 PHP
PHP 定界符 使用技巧
2009/06/14 PHP
在PHP中使用反射技术的架构插件使用说明
2010/05/18 PHP
php文件上传简单实现方法
2015/01/24 PHP
PHP、Python和Javascript的装饰器模式对比
2015/02/03 PHP
微信开发之网页授权获取用户信息(二)
2016/01/08 PHP
PHP开发中常用的十个代码样例
2016/02/02 PHP
如何正确配置Nginx + PHP
2016/07/15 PHP
thinkPHP中_initialize方法实例分析
2016/12/05 PHP
15条JavaScript最佳实践小结
2013/08/09 Javascript
微信分享的标题、缩略图、连接及描述设置方法
2014/10/14 Javascript
node.js中的fs.link方法使用说明
2014/12/15 Javascript
jquery实现的table排序功能示例
2017/03/10 Javascript
Express进阶之log4js实用入门指南
2018/02/10 Javascript
详解Vue+Element的动态表单,动态表格(后端发送配置,前端动态生成)
2019/04/20 Javascript
Node.js爬虫如何获取天气和每日问候详解
2019/08/26 Javascript
Vue检测屏幕变化来改变不同的charts样式实例
2020/10/26 Javascript
VUE实现吸底按钮
2021/03/04 Vue.js
用Python写的图片蜘蛛人代码
2012/08/27 Python
Python 操作文件的基本方法总结
2017/08/10 Python
Python中类的初始化特殊方法
2017/12/01 Python
Python 实现使用dict 创建二维数据、DataFrame
2018/04/13 Python
numpy向空的二维数组中添加元素的方法
2018/11/01 Python
Python Matplotlib实现三维数据的散点图绘制
2019/03/19 Python
解决pycharm remote deployment 配置的问题
2019/06/27 Python
Python的logging模块基本用法
2020/12/24 Python
Gweniss格温妮丝女包官网:英国纯手工制造潮流包包品牌
2018/02/07 全球购物
升职自荐书范文
2013/11/28 职场文书
教师自荐信范文
2013/12/09 职场文书
优秀企业获奖感言
2014/02/01 职场文书
中学生自我评价范文
2014/02/08 职场文书
林肯就职演讲稿
2014/05/19 职场文书
企业理念标语
2014/06/09 职场文书
2016学习雷锋精神活动倡议书
2015/04/27 职场文书
2016年社区六一儿童节活动总结
2016/04/06 职场文书
关于Python OS模块常用文件/目录函数详解
2021/07/01 Python