不允许使用access
所以我有一个小的角应用程序连接到我的节点api。我的get请求没有问题,我在加载时从api获取数据。我的帖子请求引发错误;
从'http://localhost:3000/api/heroes'访问'http://localhost:4200'的XMLHttpRequest已被CORS策略阻止:预检响应中的Access-Control-Allow-Headers不允许使用请求头字段内容类型。
和
错误HttpErrorResponse {headers:HttpHeaders,status:0,statusText:“Unknown Error”,url:“http://localhost:3000/api/heroes”,ok:false,...}
这是我的帖子方法@客户端;
addHero(hero: Hero) {
this.http.post<Hero>("http://localhost:3000/api/heroes", hero)
.subscribe((responseData) => {
console.log(responseData);
})
this.heroes.push(hero); //Adds new hero to original array
this.heroesUpdated.next([...this.heroes]); //Adds new array to subject
}
这是我的后端;
app.use((req,res,next) => {
res.setHeader("Access-Control-Allow-Origin", "localhost");
res.setHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
res.setHeader("Access-Control-Allow-Methods","GET, POST, PATCH, DELETE, OPTIONS");
next();
})
app.post("/api/heroes", (req, res,next) => {
const post = req.body;
console.log(post);
res.status(201).json({message:"Succeed"});
});
所以我允许内容类型,但我仍然得到错误。有什么建议如何从这里继续前进?
回答如下:您正确地理解问题在于CORS。
您的错误是:预检响应中的Access-Control-Allow-Headers不允许使用请求标头字段内容类型。
在某些情况下,客户端将向服务器发送“预检请求”。什么时候?
例如,当您的内容类型为“复杂”时。复杂意味着不在application/x-www-form-urlencoded
,multipart/form-data
或text/plain
。
或者当您发送带有正文的POST请求时。
还有其他场合,你可以阅读更多关于这个on MDN。
预检请求只是一个请求,方法“OPTIONS”转到同一个端点。它希望收到一个
- 成功的回应
- 允许所有标题
- 并允许原点。
你的快速中间件app.use((req,res,next) => {...
勾选了要求2和3.(实际上对于3我建议将“Access-Control-Allow-Origin”标题设置为http://localhost:4200
而不仅仅是localhost
)
但是您没有中间件或路由处理程序来处理OPTIONS请求。我们加一个:
如果我们收到OPTIONS请求,则返回200 OK。如果它不是OPTIONS请求,请转到下一个处理程序。
app.use((req, res) => {
if (req.method === 'OPTIONS') {
return res.sendStatus(200);
}
next();
});
由于我们希望OPORS对ALSO的响应设置正确的标题,我们必须在“cors middleware”之后包含它:
app.use((req,res,next) => {
// set cors headers and call next()
});
app.use((req, res, next) => {
// handle preflight requests
});
app.post('api/heroes', ...)
最后,当然有一些现成的解决方案,例如npm上的cors
包,它提供了express的中间件。检查如何在npm page上使用它。
不允许使用access
所以我有一个小的角应用程序连接到我的节点api。我的get请求没有问题,我在加载时从api获取数据。我的帖子请求引发错误;
从'http://localhost:3000/api/heroes'访问'http://localhost:4200'的XMLHttpRequest已被CORS策略阻止:预检响应中的Access-Control-Allow-Headers不允许使用请求头字段内容类型。
和
错误HttpErrorResponse {headers:HttpHeaders,status:0,statusText:“Unknown Error”,url:“http://localhost:3000/api/heroes”,ok:false,...}
这是我的帖子方法@客户端;
addHero(hero: Hero) {
this.http.post<Hero>("http://localhost:3000/api/heroes", hero)
.subscribe((responseData) => {
console.log(responseData);
})
this.heroes.push(hero); //Adds new hero to original array
this.heroesUpdated.next([...this.heroes]); //Adds new array to subject
}
这是我的后端;
app.use((req,res,next) => {
res.setHeader("Access-Control-Allow-Origin", "localhost");
res.setHeader("Access-Control-Allow-Headers", "Origin, X-Requested-With, Content-Type, Accept");
res.setHeader("Access-Control-Allow-Methods","GET, POST, PATCH, DELETE, OPTIONS");
next();
})
app.post("/api/heroes", (req, res,next) => {
const post = req.body;
console.log(post);
res.status(201).json({message:"Succeed"});
});
所以我允许内容类型,但我仍然得到错误。有什么建议如何从这里继续前进?
回答如下:您正确地理解问题在于CORS。
您的错误是:预检响应中的Access-Control-Allow-Headers不允许使用请求标头字段内容类型。
在某些情况下,客户端将向服务器发送“预检请求”。什么时候?
例如,当您的内容类型为“复杂”时。复杂意味着不在application/x-www-form-urlencoded
,multipart/form-data
或text/plain
。
或者当您发送带有正文的POST请求时。
还有其他场合,你可以阅读更多关于这个on MDN。
预检请求只是一个请求,方法“OPTIONS”转到同一个端点。它希望收到一个
- 成功的回应
- 允许所有标题
- 并允许原点。
你的快速中间件app.use((req,res,next) => {...
勾选了要求2和3.(实际上对于3我建议将“Access-Control-Allow-Origin”标题设置为http://localhost:4200
而不仅仅是localhost
)
但是您没有中间件或路由处理程序来处理OPTIONS请求。我们加一个:
如果我们收到OPTIONS请求,则返回200 OK。如果它不是OPTIONS请求,请转到下一个处理程序。
app.use((req, res) => {
if (req.method === 'OPTIONS') {
return res.sendStatus(200);
}
next();
});
由于我们希望OPORS对ALSO的响应设置正确的标题,我们必须在“cors middleware”之后包含它:
app.use((req,res,next) => {
// set cors headers and call next()
});
app.use((req, res, next) => {
// handle preflight requests
});
app.post('api/heroes', ...)
最后,当然有一些现成的解决方案,例如npm上的cors
包,它提供了express的中间件。检查如何在npm page上使用它。