gpt4 book ai didi

node.js - AngularJS $resource 为 $save 方法发出 HTTP OPTIONS 请求而不是 HTTP POST

转载 作者:IT老高 更新时间:2023-10-28 22:03:39 24 4
gpt4 key购买 nike

我正在编写一个简单的库应用程序,以便为使用 AngularJS 的更大项目做好准备。在网上阅读了很多关于使用 $resource 与 RESTful API 交互的内容后,我认为它可能会提供一些节省时间和扩展的好处来实现它,而不是使用 $http 。问题是由于某种原因(我不是 CORS 方面的专家,并且请求是跨域发送的)当使用 $save 方法时,我的 Node.js 控制台显示:

OPTIONS /books 200 1ms - 161b 

使用 query() 方法可以正常工作 - Node 控制台显示:

GET /books 200 1ms - 228b

此时我已经被困了几个小时,尝试了下面的变体,但它总是最终成为 的 OPTIONS 请求而不是 POST(根据 Angular 文档应该是这样) $save 方法。

AngularJS 网络应用

app.js

var libraryApp = angular.module('libraryApp', ['ngResource', 'ngRoute', 'libraryControllers']);

libraryApp.factory('$book', ['$resource', function ($resource) {

return $resource('http://mywebserver\\:1337/books/:bookId', { bookId: '@bookId' });
}]);

controllers.js

var libraryControllers = angular.module('libraryControllers', []);

libraryControllers.controller('BookCtrl', ['$scope', '$book', function($scope, $book) {

...

$scope.addBook = function () {
var b = new $book;
b.isbn = "TEST";
b.description = "TEST";
b.price = 9.99;
b.$save();
};
}]);

带有 Express REST API 的 Node.js

app.js

var express = require('express'),
books = require('./routes/books'),
http = require('http'),
path = require('path');

var app = express();

...

// enable cross-domain scripting
app.all('*', function(req, res, next) {
res.header("Access-Control-Allow-Origin", req.headers.origin);
res.header("Access-Control-Allow-Headers", "X-Requested-With");
next();
});

// routing
app.get('/books', books.getAll);
app.get('/books/:isbn', books.get);
// This is what I want to fire with the $save method
app.post('/books', books.add);

http.createServer(app).listen(app.get('port'), function(){
console.log('Express server listening on port ' + app.get('port'));
});

./routes/books.js

...

exports.add = function(req, res) {

console.log("POST request received...");
console.log(req.body.isbn);
};

尝试将这一行放在我的配置函数中 delete $httpProvider.defaults.headers.common["X-Requested-With"]; 但没有改变。

我不是 Angular/Node 专业人士,但现在我认为这与它是跨域有关,就像我说的,我不是 CORS 专家。

提前致谢。

最佳答案

我知道回答我自己的问题可能不太好,但我在发布此问题几天后发现了问题。

这一切都取决于浏览器如何管理 CORS。当在 JavaScript 中发出非“简单”的跨域请求时(即 GET 请求 - 这解释了 query() 函数为何起作用),浏览器将自动向指定的 URL/URI,称为“飞行前”请求或“ promise ”。只要远程源返回 200 的 HTTP 状态代码以及有关它将在响应 header 中接受的内容的相关详细信息,浏览器就会继续执行原始 JavaScript 调用。

这是一个简短的 jQuery 示例:

function makeRequest() {
// browser makes HTTP OPTIONS request to www.myotherwebsite.com/api/test
// and if it receives a HTTP status code of 200 and relevant details about
// what it will accept in HTTP headers, then it will make this POST request...
$.post( "www.myotherwebsite.com/api/test", function(data) {
alert(data);
});
// ...if not then it won't - it's that simple.
}

我所要做的就是在响应 header 中添加服务器将接受的详细信息:

// 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();
});

然后在 Express 路由之前插入这几行,以简单地为每个 OPTIONS 请求返回一个 HTTP 200 状态代码:

// fulfils pre-flight/promise request
app.options('*', function(req, res) {
res.send(200);
});

希望这将帮助任何在此页面上遇到同样问题的人。

关于node.js - AngularJS $resource 为 $save 方法发出 HTTP OPTIONS 请求而不是 HTTP POST,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21221688/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com