Django @csrf_exempt 装饰器不工作
Django @csrf_exempt decorator not working
我在 linode 服务器上使用 DJango 1.8,并且有以下视图:
import json
from django.http import HttpResponse
from django.shortcuts import render
from django.views.decorators.csrf import csrf_exempt
def home_view(request):
r = { 'response': 'OK', 'data': None }
return HttpResponse(json.dumps(r), content_type = "application/json")
@csrf_exempt
def ping(request):
r = { 'response': 'OK', 'data': 'ping' }
return HttpResponse(json.dumps(r), content_type = "application/json")
我的网址如下所示:
urlpatterns = [
url(r'^django/admin/', include(admin.site.urls)),
url(r'^django/$', home_view),
url(r'^django/ping/$', ping),
url(r'^django/echo/$', echo),
]
如果我访问我的 linode 网站
http://mylinodesite/django/ping/
我得到:
{"data": "ping", "response": "OK"}
太棒了。如果我使用 jquery 并执行
$.get("http://mylinodesite/django/ping/")
我明白了
No 'Access-Control-Allow-Origin' header is present on the requested resource.
根据我的理解,@csrf_exempt 应该摆脱 CSRF header 的东西。给出了什么?
这与 CSRF 没有任何关系,CSRF 仅用于 POST 操作,由 Django 强制执行。
您正在进行跨域 GET 操作。浏览器默认禁止这样做,因为所谓的同源策略:一个 JS 脚本只能向它加载的同一个域发出请求。所以,你被浏览器本身阻止了。
要启用对命名域的请求,您可以使用名为 CORS, which uses a header in the request. See the jQuery Ajax documentation.
的东西
丹尼尔,事实证明你只对了一部分。它是 CORS,但不能固定在 jQuery 端。这是我的 Django 视图代码,可以执行我想要的操作。请注意,它添加了 Access-Control-Allow-Origin
header 以仅允许来自所有 (*
) 的请求 GET
。
这也只是演示如何在一个文件中完成所有这些操作。如果需要,可以创建中间件来为所有请求执行此操作,但这很有效,并且是一个很好的例子,说明如何在一个地方完成所有操作,这样你就可以看到发生了什么,here is the full gist of the entire view file:
def ping(request):
r = { 'response': 'OK', 'data': 'ping' }
response = HttpResponse("['ok']", content_type="application/json")
response['Access-Control-Allow-Origin'] = '*'
response['Access-Control-Allow-Methods'] = 'GET'
return response
我在 linode 服务器上使用 DJango 1.8,并且有以下视图:
import json
from django.http import HttpResponse
from django.shortcuts import render
from django.views.decorators.csrf import csrf_exempt
def home_view(request):
r = { 'response': 'OK', 'data': None }
return HttpResponse(json.dumps(r), content_type = "application/json")
@csrf_exempt
def ping(request):
r = { 'response': 'OK', 'data': 'ping' }
return HttpResponse(json.dumps(r), content_type = "application/json")
我的网址如下所示:
urlpatterns = [
url(r'^django/admin/', include(admin.site.urls)),
url(r'^django/$', home_view),
url(r'^django/ping/$', ping),
url(r'^django/echo/$', echo),
]
如果我访问我的 linode 网站
http://mylinodesite/django/ping/
我得到:
{"data": "ping", "response": "OK"}
太棒了。如果我使用 jquery 并执行
$.get("http://mylinodesite/django/ping/")
我明白了
No 'Access-Control-Allow-Origin' header is present on the requested resource.
根据我的理解,@csrf_exempt 应该摆脱 CSRF header 的东西。给出了什么?
这与 CSRF 没有任何关系,CSRF 仅用于 POST 操作,由 Django 强制执行。
您正在进行跨域 GET 操作。浏览器默认禁止这样做,因为所谓的同源策略:一个 JS 脚本只能向它加载的同一个域发出请求。所以,你被浏览器本身阻止了。
要启用对命名域的请求,您可以使用名为 CORS, which uses a header in the request. See the jQuery Ajax documentation.
的东西丹尼尔,事实证明你只对了一部分。它是 CORS,但不能固定在 jQuery 端。这是我的 Django 视图代码,可以执行我想要的操作。请注意,它添加了 Access-Control-Allow-Origin
header 以仅允许来自所有 (*
) 的请求 GET
。
这也只是演示如何在一个文件中完成所有这些操作。如果需要,可以创建中间件来为所有请求执行此操作,但这很有效,并且是一个很好的例子,说明如何在一个地方完成所有操作,这样你就可以看到发生了什么,here is the full gist of the entire view file:
def ping(request):
r = { 'response': 'OK', 'data': 'ping' }
response = HttpResponse("['ok']", content_type="application/json")
response['Access-Control-Allow-Origin'] = '*'
response['Access-Control-Allow-Methods'] = 'GET'
return response