AngularJS和ExpressJS:如何读取$http.put()发送的内容

AngularJS和ExpressJS:如何读取$http.put()发送的内容,angularjs,node.js,express,Angularjs,Node.js,Express,我对angularJS应用程序有问题,它向nodejs服务器发送回调。当我使用POST或GET方法时,所有方法都可以正常工作,但当我发送PUT请求时,会出现错误 如果我从curl调用服务器,它工作正常;当我使用PUT方法从angularJS调用某个远程服务器时,它也可以正常工作。所以问题在于本地主机上angularJS和nodejs之间的合作,但我还没有弄清楚 我的angular方法,调用本地nodejs服务器: $http({ method :'PUT', url:'htt

我对angularJS应用程序有问题,它向nodejs服务器发送回调。当我使用POST或GET方法时,所有方法都可以正常工作,但当我发送PUT请求时,会出现错误

如果我从
curl
调用服务器,它工作正常;当我使用PUT方法从angularJS调用某个远程服务器时,它也可以正常工作。所以问题在于本地主机上angularJS和nodejs之间的合作,但我还没有弄清楚

我的angular方法,调用本地nodejs服务器:

 $http({
   method  :'PUT',
     url:'http://127.0.0.1:3000/s',
     data: $.param({"test":true, _method: 'PUT'}),
     headers :{'Content-Type':'application/x-www-form-urlencoded'}
        }).success(function(data, status, headers, config) {
            alert('OK');
        }).error(function(data, status, headers, config) {
            alert('error');
        }).catch(function(error){
            alert('catch' + JSON.stringify(error));
        });
我的nodejs文件:

var express        =    require("express");
var mysql          =    require('mysql');
var bodyParser     =    require('body-parser')
var methodOverride =    require('method-override');
var app            =    express();

//use body parser to get json
app.use(bodyParser.json())
// for parsing application/x-www-form-urlencoded
app.use(bodyParser.urlencoded({ extended: true }));
// allow PUT from browser
app.use(methodOverride('_method'));

app.put('/s', function(req, res){
  console.log('OK');
  //handle_database_put(req, res);
  res.set('Access-Control-Allow-Origin', '*');
  res.set('Access-Control-Allow-Methods', 'PUT, GET, POST, DELETE, OPTIONS');
  res.send('PUT OK');
});

app.listen(3000);
编辑以下是Angular应用程序中的错误消息。服务器从未按应有的方式打印
OK

{"data":null,"status":0,"config":{"method":"PUT","transformRequest":[null],"transformResponse":[null],"url":"http://127.0.0.1:3000/s","data":"test=true&_method=PUT","headers":{"Content-Type":"application/x-www-form-urlencoded","Accept":"application/json, text/plain, */*"}},"statusText":""}
编辑2:我刚刚注意到,请求未被识别为
放置
,而是被识别为
选项

试试这个

$http({
   method  :'PUT',
     url:'http://127.0.0.1:3000/s',
     params: {"test":true, _method: 'PUT'},
     headers :{'Content-Type':'application/json'}
        }).success(function(data, status, headers, config) {
            alert('OK');
        }).error(function(data, status, headers, config) {
            alert('error');
        }).catch(function(error){
            alert('catch' + JSON.stringify(error));
        });
您的服务器
“Accept”:“application/json
,您正在发送
“Content Type”:“application/x-www-form-urlencoded”
,因此您必须使用
“Content-Type”:“application/json”
并将数据转换为json,如下所示:

function youMethod(){
            var myUrl = 'http://127.0.0.1:3000/s';

            var data = {
                test: true,
                _method: "PUT"
            };

            return $http({
                url: myUrl,
                method: 'PUT',
                data: JSON.stringify(data), 
                headers: {
                    'Content-Type': 'application/json'
                }
              }).then(youMethodComplete)
                .catch(youMethodFailed);

            function youMethodComplete(response) {
                alert('OK');
                console.log(response);
            }

            function uyouMethodFailed(response) {
                alert('ERROR');
                console.log(response);     
            }
        }
pd:我也推荐->

额外:如果您想使用
“内容类型”:“application/x-www-form-urlencoded”
,并为此目的配置服务器,您需要遵循以下语法:

function youMethod(){
                var myUrl = 'http://127.0.0.1:3000/s';

                var data = {
                    test: true,
                    _method: "PUT"
                };

                return $http({
                    url: myUrl,
                    method: 'PUT',
                    data: $httpParamSerializer(data), //remember to inject $httpParamSerializer
                    headers: {
                        'Content-Type': 'application/x-www-form-urlencoded'
                    }
                  }).then(youMethodComplete)
                    .catch(youMethodFailed);

                function youMethodComplete(response) {
                    alert('OK');
                    console.log(response);
                }

                function uyouMethodFailed(response) {
                    alert('ERROR');
                    console.log(response);     
                }
            }

我终于发现了问题:

发生的情况是,浏览器发出飞行前
OPTIONS
HTTP请求,如果它从服务器接收到状态200,则会继续执行原始PUT调用

在ExpressJS服务器上,进行了以下配置,来自AngularJS的PUT请求现在使用PUT请求正确地发送和接收数据:

// apply this rule to all requests accessing any URL/URI
app.all('*', function(req, res, next) {
    // add details of what is allowed in HTTP request headers to the response headers
    res.header('Access-Control-Allow-Origin', req.headers.origin);
    res.header('Access-Control-Allow-Methods', 'POST, GET, PUT, DELETE, OPTIONS');
    res.header('Access-Control-Allow-Credentials', false);
    res.header('Access-Control-Max-Age', '86400');
    res.header('Access-Control-Allow-Headers', 'X-Requested-With, X-HTTP-Method-Override, Content-Type, Accept');
    // the next() function continues execution and will move onto the requested URL/URI
    next();
});

对我来说,这仍然是一个谜,为什么
POST
请求被正确处理,而
PUT
请求没有被正确处理

我没有使用Node.js,我也遇到了同样的问题。我已经被POST所取代。我想知道为什么会发生这种情况。你正在定义URL参数以与PUT请求一起发送,但试图从req.query中检索数据。你知道吗尝试只发送{test:true}而不将其包装在$param()中?
req.query
?检查
req.body
中交付的内容。这无关紧要,服务器从不“确认”它收到angular的请求,也不打印任何内容(我可以将其更改为
console.log('OK')
,但它不打印任何内容)。错误返回到angular应用程序,但服务器似乎甚至没有收到请求。我认为json数据必须是url编码的,我的代码与POST方法完美配合。当我更改方法时,问题出现了,但其他一切都保持不变。为什么要使用
内容类型
应用程序/x-www-form-urEncoded
而不是
application/json
请看这篇文章:您的代码(发送应用程序/json)导致错误:{“数据”:null,“状态”:0,“配置”:{“方法”:“PUT”,“transformRequest”:[null],“transformResponse”:“{”test\”:true,\“\u method\”:“PUT\”,“headers”:“{”内容类型”:“应用程序/json”,“Accept”:“application/json,text/plain,/“}}”,statusText:“}”,这就是为什么我使用application/x-www-form-urlencoded,而且使用x-www-form-urlencoded的方法返回错误:{“data”:null,“status”:0,“config”:{“method”:“PUT”,“transformRequest”:[null],“transformResponse”:[null],“url”:{“Content Type”:“application/x-www-form-urlencoded”,“Accept”:”application/json,text/plain,/“}”,statusText:“}”