能夠在配置文件中配置全局默認的認證方案css
REST_FRAMEWORK = { 'DEFAULT_AUTHENTICATION_CLASSES': ( 'rest_framework.authentication.SessionAuthentication', # session認證 'rest_framework.authentication.BasicAuthentication', # 基本認證 ) }
也能夠在每一個視圖中經過設置authentication_classess屬性來設置html
from rest_framework.authentication import SessionAuthentication, BasicAuthentication from rest_framework.views import APIView class ExampleView(APIView): # 類屬性 authentication_classes = [SessionAuthentication, BasicAuthentication] ...
認證失敗會有兩種可能的返回值:前端
401 Unauthorized 未認證python
403 Permission Denied 權限被禁止git
權限控制能夠限制用戶對於視圖的訪問和對於具體數據對象的訪問。github
在執行視圖的dispatch()方法前,會先進行視圖訪問權限的判斷數據庫
在經過get_object()獲取具體對象時,會進行模型對象訪問權限的判斷django
能夠在配置文件中全局設置默認的權限管理類,如json
REST_FRAMEWORK = { .... 'DEFAULT_PERMISSION_CLASSES': ( 'rest_framework.permissions.IsAuthenticated', ) }
若是未指明,則採用以下默認配置bootstrap
'DEFAULT_PERMISSION_CLASSES': ( 'rest_framework.permissions.AllowAny', )
也能夠在具體的視圖中經過permission_classes屬性來設置,如
from rest_framework.permissions import IsAuthenticated from rest_framework.views import APIView class ExampleView(APIView): permission_classes = (IsAuthenticated,) ...
AllowAny 容許全部用戶
IsAuthenticated 僅經過認證的用戶
IsAdminUser 僅管理員用戶
IsAuthenticatedOrReadOnly 已經登錄認證的用戶能夠對數據進行增刪改操做,沒有登錄認證的只能查看數據。
from rest_framework.authentication import SessionAuthentication from rest_framework.permissions import IsAuthenticated from rest_framework.generics import RetrieveAPIView class StudentAPIView(RetrieveAPIView): queryset = Student.objects.all() serializer_class = StudentSerializer authentication_classes = [SessionAuthentication] permission_classes = [IsAuthenticated]
如需自定義權限,需繼承rest_framework.permissions.BasePermission父類,並實現如下兩個任何一個方法或所有
.has_permission(self, request, view)
是否能夠訪問視圖, view表示當前視圖對象
.has_object_permission(self, request, view, obj)
是否能夠訪問數據對象, view表示當前視圖, obj爲數據對象
例如:
在當前子應用下,建立一個權限文件permissions.py中聲明自定義權限類:
from rest_framework.permissions import BasePermission class IsXiaoMingPermission(BasePermission): def has_permission(self, request, view): if( request.user.username == "xiaoming" ): return True
from rest_framework.permissions import BasePermission class IsXiaoMingPermission(BasePermission): def has_permission(self, request, view): if( request.user.username == "xiaoming" ): return True
能夠對接口訪問的頻次進行限制,以減輕服務器壓力。
通常用於付費購買次數,投票等場景使用.
能夠在配置文件中,使用DEFAULT_THROTTLE_CLASSES
和 DEFAULT_THROTTLE_RATES
進行全局配置,
REST_FRAMEWORK = { 'DEFAULT_THROTTLE_CLASSES': ( 'rest_framework.throttling.AnonRateThrottle', 'rest_framework.throttling.UserRateThrottle' ), 'DEFAULT_THROTTLE_RATES': { 'anon': '100/day', 'user': '1000/day' } }
DEFAULT_THROTTLE_RATES
可使用 second
, minute
, hour
或day
來指明週期。
也能夠在具體視圖中經過throttle_classess屬性來配置,如
from rest_framework.throttling import UserRateThrottle from rest_framework.views import APIView class ExampleView(APIView): throttle_classes = (UserRateThrottle,) ...
1) AnonRateThrottle
限制全部匿名未認證用戶,使用IP區分用戶。
使用DEFAULT_THROTTLE_RATES['anon']
來設置頻次
2)UserRateThrottle
限制認證用戶,使用User id 來區分。
使用DEFAULT_THROTTLE_RATES['user']
來設置頻次
3)ScopedRateThrottle
限制用戶對於每一個視圖的訪問頻次,使用ip或user id。
例如:
class ContactListView(APIView): throttle_scope = 'contacts' ... class ContactDetailView(APIView): throttle_scope = 'contacts' ... class UploadView(APIView): throttle_scope = 'uploads' ... REST_FRAMEWORK = { 'DEFAULT_THROTTLE_CLASSES': ( 'rest_framework.throttling.ScopedRateThrottle', ), 'DEFAULT_THROTTLE_RATES': { 'contacts': '1000/day', 'uploads': '20/day' } }
全局配置中設置訪問頻率
'DEFAULT_THROTTLE_RATES': { 'anon': '3/minute', 'user': '10/minute' }
from rest_framework.authentication import SessionAuthentication from rest_framework.permissions import IsAuthenticated from rest_framework.generics import RetrieveAPIView from rest_framework.throttling import UserRateThrottle class StudentAPIView(RetrieveAPIView): queryset = Student.objects.all() serializer_class = StudentSerializer authentication_classes = [SessionAuthentication] permission_classes = [IsAuthenticated] throttle_classes = (UserRateThrottle,)
******用的不少
對於列表數據可能須要根據字段進行過濾,咱們能夠經過添加django-fitlter擴展來加強支持。
pip install django-filter
在配置文件中增長過濾後端的設置:
INSTALLED_APPS = [ ... 'django_filters', # 須要註冊應用, ] REST_FRAMEWORK = { ... 'DEFAULT_FILTER_BACKENDS': ('django_filters.rest_framework.DjangoFilterBackend',)
在視圖中添加filter_fields屬性,指定能夠過濾的字段
class StudentListView(ListAPIView): queryset = Student.objects.all() serializer_class = StudentSerializer filter_fields = ('age', 'sex') # 127.0.0.1:8000/four/students/?sex=1
對於列表數據,REST framework提供了OrderingFilter過濾器來幫助咱們快速指明數據按照指定字段進行排序。
使用方法:
在類視圖中設置filter_backends,使用rest_framework.filters.OrderingFilter
過濾器,REST framework會在請求的查詢字符串參數中檢查是否包含了ordering參數,若是包含了ordering參數,則按照ordering參數指明的排序字段對數據集進行排序。
前端能夠傳遞的ordering參數的可選字段值須要在ordering_fields中指明。
示例:
class StudentListView(ListAPIView): queryset = Student.objects.all() serializer_class = StudentModelSerializer filter_backends = [OrderingFilter] ordering_fields = ('id', 'age') # 127.0.0.1:8000/books/?ordering=-age # -id 表示針對id字段進行倒序排序 # id 表示針對id字段進行升序排序
若是須要在過濾之後再次進行排序,則須要二者結合!
from rest_framework.generics import ListAPIView from students.models import Student from .serializers import StudentModelSerializer from django_filters.rest_framework import DjangoFilterBackend class Student3ListView(ListAPIView): queryset = Student.objects.all() serializer_class = StudentModelSerializer filter_fields = ('age', 'sex') # 由於局部配置會覆蓋全局配置,因此須要從新把過濾組件核心類再次聲明, # 不然過濾功能會失效 filter_backends = [OrderingFilter,DjangoFilterBackend] ordering_fields = ('id', 'age')
REST framework提供了分頁的支持。
咱們能夠在配置文件中設置全局的分頁方式,如:
REST_FRAMEWORK = { 'DEFAULT_PAGINATION_CLASS': 'rest_framework.pagination.PageNumberPagination', 'PAGE_SIZE': 100 # 每頁數目 }
也可經過自定義Pagination類,來爲視圖添加不一樣分頁行爲。在視圖中經過pagination_clas
屬性來指明。
class LargeResultsSetPagination(PageNumberPagination): page_size = 1000 page_size_query_param = 'page_size' max_page_size = 10000 class BookDetailView(RetrieveAPIView): queryset = BookInfo.objects.all() serializer_class = BookInfoSerializer pagination_class = LargeResultsSetPagination
注意:若是在視圖內關閉分頁功能,只需在視圖內設置
pagination_class = None
1) PageNumberPagination
前端訪問網址形式:
GET http://127.0.0.1:8000/students/?page=4
能夠在子類中定義的屬性:
page_size 每頁數目
page_query_param 前端發送的頁數關鍵字名,默認爲"page"
page_size_query_param 前端發送的每頁數目關鍵字名,默認爲None
max_page_size 前端最多能設置的每頁數量
# 聲明分頁的配置類 from rest_framework.pagination import PageNumberPagination class StandardPageNumberPagination(PageNumberPagination): # 默認每一頁顯示的數據量 page_size = 2 # 容許客戶端經過get參數來控制每一頁的數據量 page_size_query_param = "size" max_page_size = 10 # 自定義頁碼的參數名 page_query_param = "p" class StudentAPIView(ListAPIView): queryset = Student.objects.all() serializer_class = StudentModelSerializer pagination_class = StandardPageNumberPagination # 127.0.0.1/four/students/?p=1&size=5
2)LimitOffsetPagination
前端訪問網址形式:
GET http://127.0.0.1/four/students/?limit=100&offset=400
能夠在子類中定義的屬性:
default_limit 默認限制,默認值與PAGE_SIZE
設置一直
limit_query_param limit參數名,默認'limit'
offset_query_param offset參數名,默認'offset'
max_limit 最大limit限制,默認None
from rest_framework.pagination import LimitOffsetPagination class StandardLimitOffsetPagination(LimitOffsetPagination): # 默認每一頁查詢的數據量,相似上面的page_size default_limit = 2 limit_query_param = "size" offset_query_param = "start" class StudentAPIView(ListAPIView): queryset = Student.objects.all() serializer_class = StudentModelSerializer # 調用頁碼分頁類 # pagination_class = StandardPageNumberPagination # 調用查詢偏移分頁類 pagination_class = StandardLimitOffsetPagination
REST framework提供了異常處理,咱們能夠自定義異常處理函數。
from rest_framework.views import exception_handler def custom_exception_handler(exc, context): # 先調用REST framework默認的異常處理方法得到標準錯誤響應對象 response = exception_handler(exc, context) # 在此處補充自定義的異常處理 if response is None: response.data['status_code'] = response.status_code return response
在配置文件中聲明自定義的異常處理
REST_FRAMEWORK = { 'EXCEPTION_HANDLER': 'my_project.my_app.utils.custom_exception_handler' }
若是未聲明,會採用默認的方式,以下
rest_frame/settings.py REST_FRAMEWORK = { 'EXCEPTION_HANDLER': 'rest_framework.views.exception_handler' }
例如:
補充上處理關於數據庫的異常
from rest_framework.views import exception_handler as drf_exception_handler from rest_framework import status from django.db import DatabaseError def exception_handler(exc, context): response = drf_exception_handler(exc, context) if response is None: view = context['view'] if isinstance(exc, DatabaseError): print('[%s]: %s' % (view, exc)) response = Response({'detail': '服務器內部錯誤'}, status=status.HTTP_507_INSUFFICIENT_STORAGE) return response
APIException 全部異常的父類
ParseError 解析錯誤
AuthenticationFailed 認證失敗
NotAuthenticated 還沒有認證
PermissionDenied 權限決絕
NotFound 未找到
MethodNotAllowed 請求方式不支持
NotAcceptable 要獲取的數據格式不支持
Throttled 超過限流次數
ValidationError 校驗失敗
也就是說,不少的沒有在上面列出來的異常,就須要咱們在自定義異常中本身處理了。
REST framework能夠自動幫助咱們生成接口文檔。
接口文檔以網頁的方式呈現。
自動接口文檔能生成的是繼承自APIView
及其子類的視圖。
REST framewrok生成接口文檔須要coreapi
庫的支持。
pip install coreapi
在總路由中添加接口文檔路徑。
文檔路由對應的視圖配置爲rest_framework.documentation.include_docs_urls
,
參數title
爲接口文檔網站的標題。
from rest_framework.documentation import include_docs_urls urlpatterns = [ ... path('docs/', include_docs_urls(title='站點頁面標題')) ]
1) 單一方法的視圖,可直接使用類視圖的文檔字符串,如
class BookListView(generics.ListAPIView): """ 返回全部圖書信息. """
2)包含多個方法的視圖,在類視圖的文檔字符串中,分開方法定義,如
class BookListCreateView(generics.ListCreateAPIView): """ get: 返回全部圖書信息. post: 新建圖書. """
3)對於視圖集ViewSet,仍在類視圖的文檔字符串中封開定義,可是應使用action名稱區分,如
class BookInfoViewSet(mixins.ListModelMixin, mixins.RetrieveModelMixin, GenericViewSet): """ list: 返回圖書列表數據 retrieve: 返回圖書詳情數據 latest: 返回最新的圖書數據 read: 修改圖書的閱讀量 """
瀏覽器訪問 127.0.0.1:8000/docs/,便可看到自動生成的接口文檔。
1) 視圖集ViewSet中的retrieve名稱,在接口文檔網站中叫作read
2)參數的Description須要在模型類或序列化器類的字段中以help_text選項定義,如:
class Student(models.Model): ... age = models.IntegerField(default=0, verbose_name='年齡', help_text='年齡') ...
或
class StudentSerializer(serializers.ModelSerializer): class Meta: model = Student fields = "__all__" extra_kwargs = { 'age': { 'required': True, 'help_text': '年齡' } }
xadmin是Django的第三方擴展,比使用Django的admin站點更強大也更方便。
文檔:https://xadmin.readthedocs.io/en/latest/index.html
經過以下命令安裝xadmin的最新版
pip install https://codeload.github.com/sshwsfc/xadmin/zip/django2
在配置文件中註冊以下應用
INSTALLED_APPS = [ ... 'xadmin', 'crispy_forms', 'reversion', ... ] # 修改使用中文界面 LANGUAGE_CODE = 'zh-Hans' # 修改時區 TIME_ZONE = 'Asia/Shanghai'
xadmin有創建本身的數據庫模型類,須要進行數據庫遷移
python manage.py makemigrations
python manage.py migrate
在總路由中添加xadmin的路由信息
import xadmin xadmin.autodiscover() # version模塊自動註冊須要版本控制的 Model from xadmin.plugins import xversion xversion.register_models() urlpatterns = [ path(r'xadmin/', xadmin.site.urls), ]
若是以前沒有建立超級用戶,須要建立,若是有了,則能夠直接使用以前的。
python manage.py createsuperuser
xadmin再也不使用Django的admin.py,而是須要編寫代碼在adminx.py文件中。
xadmin的站點管理類不用繼承admin.ModelAdmin
,而是直接繼承object
便可。
例如:在子應用中建立adminx.py文件。
import xadmin from xadmin import views class BaseSetting(object): """xadmin的基本配置""" enable_themes = True # 開啓主題切換功能 use_bootswatch = True xadmin.site.register(views.BaseAdminView, BaseSetting) class GlobalSettings(object): """xadmin的全局配置""" site_title = "路飛學城" # 設置站點標題 site_footer = "路飛學城有限公司" # 設置站點的頁腳 menu_style = "accordion" # 設置菜單摺疊 xadmin.site.register(views.CommAdminView, GlobalSettings)
xadmin可使用的頁面樣式控制基本與Django原生的admin一直。
list_display 控制列表展現的字段
list_display = ['id', 'btitle', 'bread', 'bcomment']
search_fields 控制能夠經過搜索框搜索的字段名稱,xadmin使用的是模糊查詢
search_fields = ['id','btitle']
list_filter 能夠進行過濾操做的列,對於分類、性別、狀態
list_filter = ['is_delete']
ordering 默認排序的字段
show_detail_fields 在列表頁提供快速顯示詳情信息
list_editable 在列表頁能夠快速直接編輯的字段
refresh_times 指定列表頁的定時刷新
refresh_times = [5, 10,30,60] # 設置容許後端管理人員按多長時間(秒)刷新頁面
list_export 控制列表頁導出數據的可選格式
list_export = ('xls', 'xml', 'json') list_export設置爲None來禁用數據導出功能 list_export_fields = ('id', 'btitle', 'bpub_date')
show_bookmarks 控制是否顯示書籤功能
show_bookmarks = True
data_charts 控制顯示圖表的樣式
data_charts = { "order_amount": { 'title': '圖書發佈日期表', "x-field": "bpub_date", "y-field": ('btitle',), "order": ('id',) }, # 支持生成多個不一樣的圖表 # "order_amount": { # 'title': '圖書發佈日期表', # "x-field": "bpub_date", # "y-field": ('btitle',), # "order": ('id',) # }, }
title 控制圖標名稱
x-field 控制x軸字段
y-field 控制y軸字段,能夠是多個值
order 控制默認排序
model_icon 控制菜單的圖標【圖標的設置能夠參考bootstrap的圖標css名稱】
class BookInfoAdmin(object): model_icon = 'fa fa-gift' xadmin.site.register(models.BookInfo, BookInfodmin)
readonly_fields 在編輯頁面的只讀字段
exclude 在編輯頁面隱藏的字段
ok