版本控制

随着程序越来越大,可能通过版本不同,做出不同的处理方式。没用rest_framwork之前,我们可能会这样做:

class UserView(APIView):
    def get(self,request,*args,**kwargs):
        version = request.query_params.get('version')
        print(version)
        if version=='v1':
            #如果版本是v1
            ret = {
                'code':111,
                'msg':'版本一的内容'
            }

        elif version=='v2':
            # 如果是v2
            ret = {
                'code': 112,
                'msg': '版本二的内容'
            }
        else:
            ret = {
                'code': 0,
                'msg': '不支持其他版本'
            }
        return Response(ret)

 

通过rest_framework实现:

  先看源码:

    进行认证之前,先获取版本

 

 

 

 

 

控制类实现方式有多种:局部使用时在CBV添加versioning_class 参数,值为版本控制类名。全局使用在settings中设置即可。

 

 使用方法:

  QueryParameterVersioning类:url参数

    # 版本测试
    path('test_version/', views.TestVersionsView.as_view(), name='test_list'),  # 匿名测试
from rest_framework.versioning import QueryParameterVersioning
from rest_framework.response import Response
# from django.urls import reverse

class TestVersionsView(APIView):
    versioning_class = QueryParameterVersioning

    def get(self, request):
        version = request.version
        if version == 'v1':
            return Response('版本一')
        elif version == 'v2':
            versioning_scheme = request.versioning_scheme  # 版本类对象,用于反向生成url
            url = versioning_scheme.reverse(viewname='test_list', request=request) # 接收一个url别名与request
            # print(versioning_scheme, type(versioning_scheme))
            print(url)
            return Response('版本二')
        else:
            return Response("ok")

 

  request.version接收版本号,versioning_scheme接收版本控制类对象用来调用版本控制类下的反向解析url方法。django内置的方法同样可以进行反向解析,但只适用使用版本控制类URLPathVersioning

  URLPathVersioning类:url路由

# 版本测试URLPathVersioning
    re_path("test_version_path/(?P<version>[v1|v2]+)", views.TestVersionsPathView.as_view(), name='test_list2')
from rest_framework.versioning import URLPathVersioning


class TestVersionsPathView(APIView):
    versioning_class = URLPathVersioning

    def get(self, request, *args, **kwargs):
        version = request.version
        versioning_scheme = request.versioning_scheme
        print(request.version)
        if version == 'v1':
            url = reverse(viewname='test_list2', kwargs={"version": "v1"})
            print(url)  # /test_version_path/v1
            return Response('版本一')
        elif version == 'v2':
            url = versioning_scheme.reverse(viewname='test_list2', request=request)
            print(url)  # http://127.0.0.1:8000/test_version_path/v2
            return Response('版本二')
        else:
            return Response('ok')

  

  NamespaceVersioning类:include分发

    # 版本测试NamespaceVersioning
    path('version1/', include('app01.urls', namespace='v1')),
    path('version2/', include('app01.urls', namespace='v2'))
from django.urls import path, re_path, include
from app01 import views

app_name = 'app01'
urlpatterns = [
    path('test_version/', views.TestNamespaceVersionsView.as_view(), name='users-list'),
]
from rest_framework.versioning import NamespaceVersioning


class TestNamespaceVersionsView(APIView):
    versioning_class = NamespaceVersioning

    def get(self, request, *args, **kwargs):
        version = request.version
        versioning_scheme = request.versioning_scheme
        if version == 'v1':
            return Response('版本一')
        elif version == 'v2':
            url = versioning_scheme.reverse(viewname='users-list', request=request)
            print(url)
            return Response('版本二')
        else:
            return Response('ok')

 

  HostNameVersioning:子域名

#分发url
            urlpatterns = [
                #url(r'^admin/', admin.site.urls),
                url(r'^api/', include('api.urls')),
            ]

            urlpatterns = [
                url(r'^users/', views.UsersView.as_view(),name='u'),
            ]
            
            
            class UsersView(APIView):
                
                def get(self,request,*args,**kwargs):
                    self.dispatch
                    print(request.version) # QueryParameterVersioning().detemiin_version()
                    print(request.versioning_scheme) # QueryParameterVersioning()

            
            REST_FRAMEWORK = {
                'VERSION_PARAM':'version',
                'DEFAULT_VERSION':'v1',
                'ALLOWED_VERSIONS':['v1','v2'],
                'DEFAULT_VERSIONING_CLASS':"rest_framework.versioning.HostNameVersioning"
            }
            
            # C:\Windows\System32\drivers\etc
            # vim /etc/hosts
            127.0.0.1    v1.luffy.com
            127.0.0.1    v2.luffy.com
            
            #配置ALLOWED_HOSTS = ['*']

 

  全局设置版本控制:在settings中设置

REST_FRAMEWORK = {
    ...
    # 使用那种版本控制来控制版本号
    'DEFAULT_VERSIONING_CLASS': 'rest_framework.versioning.URLPathVersioning',
    'DEFAULT_VERSION': 'v1',  # 默认的版本
    'ALLOWED_VERSIONS': ['v1', 'v2'],  # 有效的版本
    'VERSION_PARAM': 'version',  # 版本的参数名与URL conf中一致
}

 

posted @ 2020-03-24 00:31  aikell  阅读(168)  评论(0)    收藏  举报