使用 angular 向 django-rest 发送 DELETE 请求被解释为 OPTIONS



我尝试使用带有 angularjs 的 django-rest 构建的 rest API,但我遇到了一个问题。当我发送一个删除请求时,django-rest 会看到选项。

这就是我所做的:

我的姜戈 views.py

@api_view(['GET', 'PUT', 'DELETE'])
def node_detail(request, pk):
    """
    Retrieve, update or delete a node. 
    """
    try:
        node = Node.objects.get(pk=pk)
    except Node.DoesNotExist:
        return Response(status=status.HTTP_404_NOT_FOUND)
    if request.method == 'GET':
        serializer = NodeSerializer(node)
        return Response(serializer.data)
    elif request.method == 'PUT':
        data = JSONParser().parse(request)
        serializer = NodeSerializer(node, data=data)
        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data)
        else:
            return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST)
    elif request.method == 'DELETE':
        node.delete()
        return Response(status=status.HTTP_204_NO_CONTENT)

我已经添加了带有django-cors-headers的CORS,并且所有Origins都被接受(CORS_ORIGIN_ALLOW_ALL = True)

我有一个角度服务来管理它$resource

angular.module('akilio.nodes.services', ['ngResource'])
.factory('NodeServices', function($resource){
    return $resource('http://127.0.0.1:8000/nodes/:nodeId/', {nodeId: '@nodeId'});
});

现在,使用ng-click="deleteNode()"的按钮,我调用此控制器

controller('DetailCtrl', ['$scope', '$routeParams', 'NodeServices', function($scope, $routeParams, NodeServices) {
        $scope.node = NodeServices.get({nodeId: $routeParams.pk});
        $scope.deleteNode = function(){
            $scope.node.$delete(function(){
                console.log('ok');
            }, function(){
                console.log('nok');
            });
        };
    }]);

console.log() 每次都返回我"nok",在我的 Django 控制台中,我看到

[08/Nov/2013 09:39:10] "OPTIONS /nodes HTTP/1.1" 301 0

仅供参考,我的角度版本是v1.2.0-rc.3,然后我已经添加到我的应用程序中

config(['$sceDelegateProvider', function($sceDelegateProvider) {
     $sceDelegateProvider.resourceUrlWhitelist(['self', 'http://127.0.0.1']);
 }])

但没有任何改变:(

一个想法 ?

编辑

我认为问题来自$resource,也许我在实现中错了。我试图删除一个带有$http而不是$resource的节点

$http.delete('http://127.0.0.1:8000/nodes/4/');

一切都很好。

你可能需要相应地调整你的 django 设置:

CORS_ALLOW_CREDENTIALS = True
CORS_ORIGIN_WHITELIST = ('127.0.0.1:8000', )
SESSION_COOKIE_DOMAIN = '127.0.0.1'
CSRF_COOKIE_DOMAIN = '127.0.0.1'

另外,如果您使用 CSRF 令牌,请不要忘记这一点:

app.run(function($http) {
    $http.defaults.headers.post['X-CSRFToken'] = $.cookie('csrftoken');
});

实际上问题来自Django,它增加了一个试用空间。然后当 angular 试图获得http://test/url但 django 将其重定向到http://test/url/此重定向意味着数据丢失。

我的解决方案是将此修改为资源.js文件。

其他解决方案是可能的,Django与APPEND_SLASH为假

最新更新