Django DRF接口开发

网站Api开发

    网站API也称接口,其实与网站的URL地址是同一个原理。当用户使用GET或者POST方式访问接口时,接口以JSON或者字符串的数据内容返回给用户,这是最主要的区别。网站的URL地址主要是返回HTML网页需要的变量信息。

    实际快速开发API,可以使用Django Rest Framework(简称DRF)框架实现。首先需要安装,建议使用pip进行:

pip install djangorestframework

    框架安装完成后,在项目app的index中创建 serializers.py 文件,用于定义DRF的 Serializer 类。构建项目目录后,接着在settings.py 分别设置数据连接信息和DRF框架的功能设置,配置代码如下:

# 数据库连接方式

DATABASES = {

    'default':

        { 'ENGINE': 'django.db.backends.mysql',

        'NAME': 'MyDjango_db',

        'USER': 'root',

        'PASSWORD': '123456',

        'HOST': '127.0.0.1',

        'PORT': '3306' }

}

# Django Rest Framework 框架的配置信息

INSTALLED_APPS = [   

'django.contrib.admin',    

'django.contrib.auth',    

'django.contrib.contenttypes',   

 'django.contrib.sessions',    

'django.contrib.messages',    

'django.contrib.staticfiles',    

'index',    

'rest_framework',   

 'index.apps.IndexConfig',

]

# 分页设置 自定义设置分页的数

REST_FRAMEWORK = {    

    'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.PageNumberPagination',    

    'PAGE_SIZE': 10

}

上述代码中:   

    1. 在INSTALLED_APPS 中添加功能配置,这样能使Django在运行过程中自动加载DRF的功能。

    2. 配置RF属性,属性值以字典的形式表示,用于设置DRF的分页功能。


    完成 settings.py 的配置后,下一步是定义项目的数据模型。在index的models.py中别分定义模型Type和Product,代码如下:

from django.db import models

# Create your models here.

class Type(models.Model):

    id = models.AutoField('id', primary_key=True)

    typeName = models.CharField('产品类型', max_length=25)

    def __str__(self):

        return self.typeName

class Product(models.Model):

    id = models.AutoField('id', primary_key=True)

    name = models.CharField('名称', max_length=50)

    weight = models.CharField('重量', max_length=20)

    size = models.CharField('尺寸', max_length=20)

    type = models.ForeignKey(Type, on_delete=models.CASCADE, verbose_name='产品类型')

    def __str__(self):

        return self.name  # 设置返回值

定义好的模型执行数据迁移,在项目的数据库中生成对应的数据表。


    上述基本配置完成后,接下来使用DRF 快速开发PI。首先在项目应用 index 的 serializers.py 中分别定义Serializer 类和 ModelSerializer 类,代码如下:

from abc import ABC

from rest_framework import serializers

from .models import Product, Type


type_name = Type.objects.values('type_name').all()

TYPE_CHOICES = [item['id'] for item in type_name]  # 定义下拉内容

class MySerializer(serializers.Serializer, ABC):

    id = serializers.IntegerField(read_only=True)

    name = serializers.CharField(required=True, allow_blank=False, max_length=100)

    weight = serializers.CharField(required=True, allow_blank=False, max_length=100)

    size = serializers.CharField(required=True, allow_blank=False, max_length=100)

    type = serializers.ChoiceField(choices=TYPE_CHOICES, default=1)

    def create(self, validated_data):  # 重写create函数,将API数据保存在数据表中

        return Product.objects.create(**validated_data)

    def update(self, instance, validated_data):  # 重写 update 函数,将API数据保存在数据表中

        instance.name = validated_data.get('name', instance.name)

        instance.weight = validated_data.get('weight', instance.weight)

        instance.size = validated_data.get('size', instance.size)

        instance.type = validated_data.get('type', instance.type)

        instance.save()

        return instance

class ProductSerializer(serializers.ModelSerializer):

    class Meta:

        model = Product

        fields = '__all__'

        # fields = ('id', 'name', 'weight', 'size', 'type')

    从上述代码可以看到,Serializer 类 和ModelSerializer类与Django的表单From 类和 ModelForom 类非常相似,若想进一步了解,在Python的安装目录中查看相应的源文件(\Lib\site-packages\rest_framework)


    最后在 urls.py 和 views.py 中实现API开发。以定义好的ProductSerializer 类为列子,API功能实现代码如下:

# index 的urls.py

from django.urls import path

from . import views

urlpatterns = [

    # 基于类的视图

    path('', views.ProductClass.as_view()),

    # 基于函数的视图

    path('', views.product_def)

]

# index 的 views.py

from .models import Product

from .serializers import ProductSerializer

# APIView 方式生成视图

from rest_framework.views import APIView

from rest_framework.response import Response

from rest_framework import status

from rest_framework.pagination import PageNumberPagination

# Create your views here.


class ProductClass(APIView):

    def get(self, request):

        queryset = Product.objects.all()

        pg = PageNumberPagination()  # 分页查询,需要在setting.py中设置REST_FRAMEWORK 属性

        page_roles = pg.paginate_queryset(queryset=queryset, request=request, view=self)

        serializer = ProductSerializer(instance=page_roles, many=True)

        # serializer = ProductSerializer(instance=queryset, many=True)  # 全表查询

        return Response(serializer.data)

    @staticmethod def post(request):

        serializer = ProductSerializer(data=request.data) # 获取请求数据

        if serializer.is_valid(): # 数据验证

            serializer.save() # 数据保存

            return Response(serializer.data, status=status.HTTP_200_OK)

        return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

    @staticmethod def delete(request):

        serializer = ProductSerializer(data=request.data['id']) # 获取请求数据

        Product.objects.filter(id=serializer).delete()

def product_def(request, pk):

    if request.method == 'GET':

        queryset = Product.objects.filter(id=pk).all()

        serializer = ProductSerializer(instance=queryset, many=True)

        return Response(serializer.data)

    elif request.method == 'POST':

        serializer = ProductSerializer(data=request.data)

        if serializer.is_valid():

            serializer.save()

            return Response(serializer.data, status=status.HTTP_200_OK)

        return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)

    elif request.method == 'DELETE':

        queryset = Product.objects.filter(id=pk).all()

        queryset.delete()

        return Response(data='删除成功', status=status.HTTP_204_NO_CONTENT)

def product_del(request, pk):

    try:

        Product.objects.filter(id=pk).all().delete()

    except Exception as e:

        raise e

    else:

        return Response(data='删除成功', status=status.HTTP_204_NO_CONTENT)

    在分析上述代码之前,首先了解一下DRF实现API开发的三种方式:

    1.基于类的视图

    2.基于函数的视图

    3. 重构 ViewSets 类

    其中,重构ViewSets 类实现过程过于复杂,一般不建议采用这种实现方式。在views.py 定义的 ProductClass  类分别居于类的视图和基于函数的视图,两种使用的说明如下:   

    1.基于类的视图:主要通过自定义类来实现视图,自定义类可以选择基础父类APIView、mixins 或 generics类只适用于ModelSerializer 类。上述代码朱啊哟继承APIView类,并且定义GET请求和POST请求的处理函数。GET函数主要讲模型Product的数据进行分页显示,POST函数讲用户发送的数据进行验证并入库处理。 

    2. 基于函数的视图:使用函数的方式实现API开发是三者中最为简单的方式,从函数product_def 的定义来看,该函数与Django定于的视图函数并没有什么区别。唯一的区别在与函数需要使用装饰器 api_view 并且数据是由DRF定义的对象进行返回的。

    上述代码中,若用户发送GET请求,函数参数pk作为模型Prodect的查询条件,查询结果交给ProductSerializer 类实例化对象serializer进行数据格式转换,最后由DRF的Response 对象返回给用户。若用户发送POST请求,函数讲用户发送的数据进行验证并入库处理。


    Django Rest Framework 框架的使用方式总结如下:

    1. 在settings.py 中添加 DRF 功能,并对工嗯呢该进行分页配置。

    2. 在APP中新建 serializers.py 文件并定义 Serializer 类或 ModelSerializer 类。

    3. 在 urls.py 中定义路由地址。

    4. 在 views.py 中定义视图函数, 三种定义方式分别为:基于类的视图、基于函数的视图和重构 ViewSets 类。

你可能感兴趣的:(Django DRF接口开发)