django框架进阶-CSRF认证

###############################################

"""
django中csrf的实现机制

#第一步:django第一次响应来自某个客户端的请求时,后端随机产生一个token值,把这个token保存在SESSION状态中;同时,后端把这个token放到cookie中交给前端页面;
#第二步:下次前端需要发起请求(比如发帖)的时候把这个token值加入到请求数据或者头信息中,一起传给后端;Cookies:{csrftoken:xxxxx}
#第三步:后端校验前端请求带过来的token和SESSION里的token是否一致;


Django中的CSRF中间件源码的逻辑:

从Django项目配置文件夹中读取CSRF_USE_SESSIONS的值,
如果获取成功,则从session中读取CSRF_SESSION_KEY的值,默认为'_csrftoken',
如果没有获取到CSRF_USE_SESSIONS的值,则从发送过来的请求中获取CSRF_COOKIE_NAME的值,如果没有定义则返回None。

再来看process_view方法
在process_view方法中,先检查视图函数是否被csrf_exempt装饰器装饰,
如果视图函数没有被csrf_exempt装饰器装饰,则程序继续执行,否则返回None。
接着从request请求头中或者cookie中获取携带的token并进行验证,验证通过才会继续执行与URL匹配的视图函数,否则就返回403 Forbidden错误。

实际项目中,会在发送POST,PUT,DELETE,PATCH请求时,在提交的form表单中添加
{% csrf_token %}
即可,否则会出现403的错误

""" 
 

###############################################

5.1 基于Django FBV
在一个项目中,如果注册起用了CsrfViewMiddleware中间件,则项目中所有的视图函数和视图类在执行过程中都要进行CSRF验证。

此时想使某个视图函数或视图类不进行CSRF验证,则可以使用csrf_exempt装饰器装饰不想进行CSRF验证的视图函数

from django.views.decorators.csrf import csrf_exempt
@csrf_exempt  
def index(request):  
    pass

也可以把csrf_exempt装饰器直接加在URL路由映射中,使某个视图函数不经过CSRF验证
from django.views.decorators.csrf import csrf_exempt  
from users import views  
 urlpatterns = [  
    url(r'^admin/', admin.site.urls),  
    url(r'^index/',csrf_exempt(views.index)),  
]


同样的,如果在一个Django项目中,没有注册起用CsrfViewMiddleware中间件,但是想让某个视图函数进行CSRF验证,则可以使用csrf_protect装饰器
csrf_protect装饰器的用法跟csrf_exempt装饰器用法相同,都可以加上视图函数上方装饰视图函数或者在URL路由映射中直接装饰视图函数

from django.views.decorators.csrf import csrf_exempt  
@csrf_protect  
def index(request):  
    pass

或者
from django.views.decorators.csrf import csrf_protect  
from users import views  
urlpatterns = [  
    url(r'^admin/', admin.site.urls),  
    url(r'^index/',csrf_protect(views.index)),  
]

###############################################

5.1 基于Django CBV
上面的情况是基于Django FBV的,如果是基于Django CBV,则不可以直接加在视图类的视图函数中了
此时有三种方式来对Django CBV进行CSRF验证或者不进行CSRF验证

方法一,在视图类中定义dispatch方法,为dispatch方法加csrf_exempt装饰器
from django.views.decorators.csrf import csrf_exempt
from django.utils.decorators import method_decorator
class UserAuthView(View):
    @method_decorator(csrf_exempt)
    def dispatch(self, request, *args, **kwargs):
        return super(UserAuthView,self).dispatch(request,*args,**kwargs)

    def get(self,request,*args,**kwargs):
        pass

    def post(self,request,*args,**kwargs):
        pass

    def put(self,request,*args,**kwargs):
        pass

    def delete(self,request,*args,**kwargs):
        pass

方法二:为视图类上方添加装饰器

@method_decorator(csrf_exempt,name='dispatch')
class UserAuthView(View):
    def get(self,request,*args,**kwargs):
        pass

    def post(self,request,*args,**kwargs):
        pass

    def put(self,request,*args,**kwargs):
        pass

    def delete(self,request,*args,**kwargs):
        pass

方式三:在url.py中为类添加装饰器

from django.views.decorators.csrf import csrf_exempt

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    url(r'^auth/', csrf_exempt(views.UserAuthView.as_view())),
]

###############################################

 ###############################################

 ###############################################

原文地址:https://www.cnblogs.com/andy0816/p/12363032.html