作者:E4b9a6, 创建:2020-01-31, 字数:2226, 已阅:94, 最后更新:2020-01-31
跨域是指在不同的域名、协议或端口之间发送 HTTP 请求的限制,它是一种安全机制,旨在防止恶意网站访问或修改其他网站的数据
当浏览器向另一个域名的网站发送请求时,就会发生跨域,例如,如果网站 example.com 尝试从 otherdomain.com 发起请求时,则会发生跨域,跨域会返回以下常见错误
之所以会造成错误,是因为浏览器具备同源策略
安全机制
如果两个页面的协议,端口(如果有指定)和域名都相同,则称两个页面具有相同的源
同源策略
限制了从同一个源加载的文档或脚本如何与来自另一个源的资源进行交互,用于隔离潜在恶意文件的重要安全机制
如果没有这个机制,将难以应对以下问题
同时,同源策略有助于保护用户隐私,因为它将防止网站跟踪用户在其他网站上的活动
显然,在现代互联网中,多个域名互相访问是常见操作,为了应对这种情况,浏览器同时也具备CORS
(Cross-Origin Resource Sharing)机制
CORS
允许网站在不同域之间安全地共享资,它通过使用HTTP头部来指定哪些域可以访问特定资源,从而实现跨域请求,同时这也是W3C组织推荐的一种跨域访问机制,各大主流浏览器都已经支持这种处理方式
跨域请求在浏览器来看分为2种:
两者的区别是非标准HTTP请求会触发预检查(Options Method
)请求,而标准HTTP请求会直接发起跨域请求
标准请求如下
标准HTTP请求会直接发送跨域请求,并在请求头中携带Origin字段,以表明这是一个跨域的请求,服务器端接到请求后,根据自己的跨域规则设置Access-Control-Allow-Origin
和Access-Control-Allow-Methods
的响应头,来返回验证结果,两者信息一致,浏览器则接收返回的资源内容
大部分情况下,请求都不会是标准HTTP请求,所以需要处理跨域请求
非标准请求,需要先向目标服务器确认是否允许跨域请求,这个过程称之为预检请求
预检请求通常是Options
请求,返回3个值:
这三个值分别指示是否允许请求跨域的源域名、允许跨域的请求方法、允许跨域的请求头,浏览器首先判断发起请求的域名是否在源域名列表中,再判断请求方法和请求头符合目标服务器的要求,最后发起跨域请求
清楚跨域的原理后,设置允许跨域就比较清晰了,例如可以在Nginx中增加对跨域的支持如下
server {
listen 80;
server_name your_domain.com;
location / {
# *号表示允许从任何域名发起的请求,这里为演示方便,通常不这么写
add_header Access-Control-Allow-Origin *;
# 支持哪些跨域方法
add_header Access-Control-Allow-Methods "GET, POST, OPTIONS";
# 支持跨域的headers
add_header Access-Control-Allow-Headers "Authorization, Origin, X-Requested-With, Content-Type, Accept";
# 其他配置
}
}
除了CROS
外,还能看到有前端技术JSONP
支持跨域请求,它利用了这样一个事实:浏览器不会对script标签施加同源策略限制
JSONP不推荐用于新的 Web 应用程序,现代浏览器已经支持跨域资源共享 (CORS),它是一种更安全、更灵活的方法