在尝试使用Angular 2发布到我的Django服务器时,我正在努力解决403 / CSRF问题。
我的服务器代码和我的Angular代码都在同一个127.0.0.1服务器上运行。
运行Angular代码时,服务器返回403 4612错误
我的Django View代码看起来像这样(我正在使用Django REST框架):
rom django.utils import timezone
from django.shortcuts import render, get_object_or_404, redirect
from django.contrib.auth.models import User
from .models import Item, Seen, Keyword, Flag
from django.utils.decorators import classonlymethod
from django.views.decorators.csrf import csrf_exempt
from rest_framework import viewsets
from items.serializers import ItemSerializer, UserSerializer
from rest_framework.authentication import SessionAuthentication
class CsrfExemptSessionAuthentication(SessionAuthentication):
def enforce_csrf(self, request):
return # To not perform the csrf check previously happening
class ItemViewSet(viewsets.ModelViewSet):
queryset = Item.objects.all().order_by('-date_added')
serializer_class = ItemSerializer
authentication_classes = (CsrfExemptSessionAuthentication, )
#permission_classes = [IsAccountAdminOrReadOnly]
"""
Use the API call query params to determing what to return
API params can be:
?user=<users_id>&num=<num_of_items_to_return>&from=<user_id_of_items_to_show>
"""
def get_queryset(self):
this_user = self.request.query_params.get('user', None)
restrict_to_items_from_user_id = self.request.query_params.get('from', None)
quantity = self.request.query_params.get('num', 20)
if restrict_to_items_from_user_id is not None:
queryset = Item.objects.filter(owner=restrict_to_items_from_user_id, active=True).order_by('-date_added')[0:int(quantity)]
elif this_user is not None:
queryset = Item.objects.filter(active=True, credits_left__gt=0).exclude(pk__in=Seen.objects.filter(user_id=this_user).values_list('item_id', flat=True))[0:int(quantity)]
else:
queryset = Item.objects.filter(active=True, credits_left__gt=0)[0:int(quantity)]
return queryset
执行POST的我的Angular 2代码如下所示:
import {Injectable, Inject} from 'angular2/core';
import {Http, Headers, HTTP_PROVIDERS} from 'angular2/http';
import {UserData} from './user-data';
import 'rxjs/add/operator/map';
@Injectable()
export class ConferenceData {
static get parameters(){
return [[Http], [UserData]];
}
constructor(http, user) {
// inject the Http provider and set to this instance
this.http = http;
this.user = user;
}
load() {
// Example of a PUT item
let body = JSON.stringify({ url: 'fred', item_type: 'P', owner_id: 2 });
let headers = new Headers();
headers.append('Content-Type', 'application/json');
this.http.post('http://127.0.0.1:8000/api/items/', body, {
headers: headers
})
.subscribe(
data => {
alert(JSON.stringify(data));
},
err => this.logError(err.json().message),
() => console.log('Authentication Complete')
);
}
}
我发现CSRF问题真的难以掌握!
编辑:添加了CORS设置
我的CORS设置如下所示:
CORS_ORIGIN_ALLOW_ALL = True
CORS_ORIGIN_WHITELIST = (
'veeu.co',
'127.0.0.1'
)
CORS_ORIGIN_REGEX_WHITELIST = ()
CORS_URLS_REGEX = '^.*$'
CORS_ALLOW_METHODS = (
'GET',
'POST',
'PUT',
'PATCH',
'DELETE',
'UPDATE',
'OPTIONS'
)
CORS_ALLOW_HEADERS = (
'x-requested-with',
'content-type',
'accept',
'origin',
'authorization',
'x-csrftoken'
)
CORS_EXPOSE_HEADERS = ()
CORS_ALLOW_CREDENTIALS = False
答案 0 :(得分:1)
您可以将令牌作为标头添加到您的ajax请求中,而不是禁用CSRF保护。请参阅the docs,特别是AngularJS的最后一节。
您可能必须使用csrf_ensure
作为初始Django视图,以确保Django设置csrf cookie。