angular.js post 和 django rest 框架的 403 错误
403 error with angular.js post and django rest framework
我正在尝试制作一个非常简单的登录表单,在前端使用 angular.js,在后端使用 api。这是 html 一侧的表格:
<form action="" method="post">
{% csrf_token %}
<div class="modal-body">
<div class="form-group">
<label for="login-username" class="control-label">Email:</label>
<input type="text" class="form-control" name="username" id="login-username" ng-model="loginData.email" required>
</div>
<div class="form-group">
<label for="login-password" class="control-label">Password:</label>
<input type="text" class="form-control" name="password" id="login-password" ng-model="loginData.password" required>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
<button type="button" class="btn btn-primary" ng-click="login()">Login as {$ loginData.email $}</button>
</div>
</form>
这是我的 angular 控制器(注意:我知道这里没有问题,因为我有一个非常相似的寄存器功能,工作正常):
mainApp.controller("mainCtrl", function($scope, $http) {
$scope.loginData = {"email":"bernard@mail.com","password":"pass"};
$scope.login = function() {
return $http.post('/api/v1/auth/login/',
$scope.loginData
).success(function(data, status){
alert("success : "+status);
console.log(data);
}).error(function(data, status){
alert("error : "+status);
});
}
});
这是我的 angular 应用程序,其中包含 csrf headers :
var mainApp = angular.module("mainApp", []).config(function($interpolateProvider) {
$interpolateProvider.startSymbol('{$');
$interpolateProvider.endSymbol('$}');
}).run(run);
function run($http) {
$http.defaults.xsrfHeaderName = 'X-CSRFToken';
$http.defaults.xsrfCookieName = 'csrftoken';
}
在 django 方面,我有一个登录视图,它非常适合 get 而不是 post 方法。这就是我迷路的地方。
class LoginView(views.APIView):
"""
View for login user
"""
queryset = BaseUser.objects.all()
def get(self, request, format=None):
print("get_login098765") # THIS IS PRINTED PERFECTLY
return Response()
def post(self, request, format=None): #THIS THROWS 403 ERROR
print("post_login098765") #THIS IS NOT PRINTED
return Response()
我错过了什么?谢谢!
编辑:
我收到一个名为 login 的文件,其中包含:{"detail":"Authentication credentials were not provided."}
据我了解,需要在配置函数中应用 CRSF 参数:
var mainApp = angular.module("mainApp", []).config(function($interpolateProvider, $httpProvider) {
$interpolateProvider.startSymbol('{$');
$interpolateProvider.endSymbol('$}');
$httpProvider.defaults.xsrfHeaderName = 'X-CSRFToken';
$httpProvider.defaults.xsrfCookieName = 'csrftoken';
}).run(run);
为回应您的编辑,消息:
{"detail":"Authentication credentials were not provided."}
由 Django REST Framework 抛出并且与您对该 ViewSet 的权限有关。我建议看看 http://www.django-rest-framework.org/api-guide/authentication/
这可能包括将默认身份验证 类 添加到您的设置文件,如下所示:
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework.authentication.BasicAuthentication',
'rest_framework.authentication.SessionAuthentication',
)
}
或者基于视图,像这样:
from rest_framework.authentication import SessionAuthentication, BasicAuthentication
from rest_framework.permissions import IsAuthenticated
class LoginView(api.APIView):
authentication_classes = (SessionAuthentication, BasicAuthentication)
permission_classes = (IsAuthenticated,)
[...]
更新:由于使用 AllowAny
作为权限有效,您可以执行以下操作将这些权限限制为 post 路由。这是一个例子:
class LoginView(api.APIView):
queryset = BaseUser.objects.all()
def get_permissions(self):
if self.request.method == 'POST':
return (permissions.AllowAny(),)
return (permissions.IsAuthenticated(),)
这将覆盖此端点上 POST 请求的权限,并默认为其他路由的 IsAuthenticated。
我正在尝试制作一个非常简单的登录表单,在前端使用 angular.js,在后端使用 api。这是 html 一侧的表格:
<form action="" method="post">
{% csrf_token %}
<div class="modal-body">
<div class="form-group">
<label for="login-username" class="control-label">Email:</label>
<input type="text" class="form-control" name="username" id="login-username" ng-model="loginData.email" required>
</div>
<div class="form-group">
<label for="login-password" class="control-label">Password:</label>
<input type="text" class="form-control" name="password" id="login-password" ng-model="loginData.password" required>
</div>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
<button type="button" class="btn btn-primary" ng-click="login()">Login as {$ loginData.email $}</button>
</div>
</form>
这是我的 angular 控制器(注意:我知道这里没有问题,因为我有一个非常相似的寄存器功能,工作正常):
mainApp.controller("mainCtrl", function($scope, $http) {
$scope.loginData = {"email":"bernard@mail.com","password":"pass"};
$scope.login = function() {
return $http.post('/api/v1/auth/login/',
$scope.loginData
).success(function(data, status){
alert("success : "+status);
console.log(data);
}).error(function(data, status){
alert("error : "+status);
});
}
});
这是我的 angular 应用程序,其中包含 csrf headers :
var mainApp = angular.module("mainApp", []).config(function($interpolateProvider) {
$interpolateProvider.startSymbol('{$');
$interpolateProvider.endSymbol('$}');
}).run(run);
function run($http) {
$http.defaults.xsrfHeaderName = 'X-CSRFToken';
$http.defaults.xsrfCookieName = 'csrftoken';
}
在 django 方面,我有一个登录视图,它非常适合 get 而不是 post 方法。这就是我迷路的地方。
class LoginView(views.APIView):
"""
View for login user
"""
queryset = BaseUser.objects.all()
def get(self, request, format=None):
print("get_login098765") # THIS IS PRINTED PERFECTLY
return Response()
def post(self, request, format=None): #THIS THROWS 403 ERROR
print("post_login098765") #THIS IS NOT PRINTED
return Response()
我错过了什么?谢谢!
编辑:
我收到一个名为 login 的文件,其中包含:{"detail":"Authentication credentials were not provided."}
据我了解,需要在配置函数中应用 CRSF 参数:
var mainApp = angular.module("mainApp", []).config(function($interpolateProvider, $httpProvider) {
$interpolateProvider.startSymbol('{$');
$interpolateProvider.endSymbol('$}');
$httpProvider.defaults.xsrfHeaderName = 'X-CSRFToken';
$httpProvider.defaults.xsrfCookieName = 'csrftoken';
}).run(run);
为回应您的编辑,消息:
{"detail":"Authentication credentials were not provided."}
由 Django REST Framework 抛出并且与您对该 ViewSet 的权限有关。我建议看看 http://www.django-rest-framework.org/api-guide/authentication/
这可能包括将默认身份验证 类 添加到您的设置文件,如下所示:
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework.authentication.BasicAuthentication',
'rest_framework.authentication.SessionAuthentication',
)
}
或者基于视图,像这样:
from rest_framework.authentication import SessionAuthentication, BasicAuthentication
from rest_framework.permissions import IsAuthenticated
class LoginView(api.APIView):
authentication_classes = (SessionAuthentication, BasicAuthentication)
permission_classes = (IsAuthenticated,)
[...]
更新:由于使用 AllowAny
作为权限有效,您可以执行以下操作将这些权限限制为 post 路由。这是一个例子:
class LoginView(api.APIView):
queryset = BaseUser.objects.all()
def get_permissions(self):
if self.request.method == 'POST':
return (permissions.AllowAny(),)
return (permissions.IsAuthenticated(),)
这将覆盖此端点上 POST 请求的权限,并默认为其他路由的 IsAuthenticated。