📅  最后修改于: 2023-12-03 15:39:22.968000             🧑  作者: Mango
当我们在使用 AJAX 或 Fetch API 向不同源的服务器发送请求时,如果服务器设置了 CORS 策略,就会导致请求被阻止。一种常见的错误信息就是:
已被 CORS 策略阻止:预检响应中的 Access-Control-Allow-Headers 不允许请求标头字段内容类型。
这个错误信息有点拗口,下面我们来解析一下:
CORS 是跨源资源共享 (Cross-Origin Resource Sharing) 的缩写,它是一种在客户端实现跨域请求的机制。在默认情况下,浏览器只允许同源的访问,即协议、域名、端口号都相同的网站之间可以相互访问。CORS 机制可以解决这个限制,使得不同源的网站之间可以进行跨域访问。
在 CORS 策略生效的情况下,浏览器会发送一个 OPTIONS 请求到服务器,询问服务器是否允许这个跨域请求。这个 OPTIONS 请求的响应被称为预检响应。预检响应中包含了一些头部信息,用来告诉浏览器服务器是否允许这个跨域请求。
Access-Control-Allow-Headers 是服务器在预检响应中设置的一个头部字段,用来告诉浏览器哪些请求标头字段是允许的。
这个错误信息意味着请求中包含了一个不被允许的请求标头字段,即“Content-Type”。Content-Type 是用来指定请求或响应的实体的类型的。有时候,我们需要向服务器提交一些数据,比如 JSON 格式的数据,就需要设置 Content-Type 为 application/json。然而,如果服务器在预检响应中设置 Access-Control-Allow-Headers 不包含 Content-Type,浏览器就会报错,提示这个请求被阻止。
要解决这个问题,服务器需要在预检响应中设置 Access-Control-Allow-Headers,包含 Content-Type 这个请求标头字段。如果你是服务器开发者,可以根据自己的语言和框架,寻找相应的设置 Access-Control-Allow-Headers 的方法。如果你是前端开发者,可以尝试修改请求的 Content-Type 头部,或者向服务器提交 FormData。FormData 可以不设 Content-Type,因为浏览器会自动设置。此外,也可以使用第三方库,比如 Axios,来避免这种错误发生。
// 修改请求的 Content-Type
fetch(url, {
method: 'POST',
body: JSON.stringify(data),
headers: {
'Content-Type': 'application/json' // 修改 Content-Type
}
});
// 使用 FormData
let formData = new FormData();
formData.append('name', 'Tom');
formData.append('age', 18);
fetch(url, {
method: 'POST',
body: formData // 不设 Content-Type,因为浏览器会自动设置
});
// 使用 Axios
axios.post(url, data, {
headers: {
'Content-Type': 'application/json' // 自动设置 Content-Type
}
});
以上是一些解决方法,具体情况需具体分析。希望这篇文章能够给大家带来一些帮助。