域名
顶级域名、一级域名、二级域名
.com 顶级域名/一级域名,更准确的说叫顶级域
baidu.com 二级域名,更准确的说叫二级域
tieba.baidu.com 三级域名,更准确的说叫三级域
detail.tieba.baidu.com 四级域名,更准确的说叫四级域
子域名
子域名是在域名系统等级中,属于更高一层域的域。比如,mail.example.com 和 calendar.example.com是example.com的两个子域,而example.com则是顶级域.com的子域
同源策略
浏览器有同源策略,如果两个url的协议、域名、端口完全一致才是同源,有一个不一致就是跨域
同源策略限制
- DOM:禁止操作非源页面的DOM与JS对象
这里主要场景是iframe跨域的情况,非同源的iframe是限制互相访问的
- XmlHttpRequest:禁止使用XHR对象向不同源的服务器发起HTTP请求,即不能发送跨域ajax请求
主要用来防止CSRF攻击
-
本地存储:Cookie、LocalStorage和IndexDB无法跨域读取
跨域(cross-origin)
违反同源策略就是跨域
跨站(cross-site)
只有两个URL的eTLD+1相同即是同站(Same Site),不需要考虑协议和端口
eTLD:有效顶级域名/一级域名,如.com
、.co.uk
、.github.io
、.top
等
eTLD+1:有效顶级域名+二级域名,如 taobao.com
,baidu.com
跨站一定跨域,跨域未必跨站(子域名、三级域名等)
如何检查请求是否为 同站、同源、跨站
Chrome发送请求时会附带一个Sec-Fetch-Site HTTP Header ,Sec-Fetch-Site表示一个请求发起者的来源与目标资源来源之间的关系,这个Header将有以下值之一
- cross-site 跨站/跨域
- same-site 同站
- same-origin 同源
- none
通过检查Sec-Fetch-Site的值,可以确定请求是同站、同源还是跨站
示例
Sec-Fetch-Site: same-origin 示例
https://mysite.example/foo.json
从网页发起的 https://mysite.example
(具有相同的端口)是同源的请求
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: same-origin
Sec-Fetch-Site: cross-site示例
- 例如,从
https://example.com
的页面发起请求到``https://api.example.com
- 例如,从
``https://example.com
的页面点击链接跳转到``https://example.net
Sec-Fetch-Dest: empty
Sec-Fetch-Mode: cors
Sec-Fetch-Site: cross-site
当浏览器检测到请求中的Sec-Fetch-Site: cross-site
,在跨站请求中,浏览器通常会遵循同源策略,该策略要求请求只能访问与其来源相同的资源,即浏览器默认情况下不会将跨站请求的Cookie发送到服务器,但是当设置SameSite为none和Secure时是可以发送的
Cookie访问限制 --- 重点
浏览器的同源策略将会限制不同源间的访问,对于跨站和跨域来说对访问Cookie的影响也是不同的。
-
同源
- 无限制,浏览器均可存储Cookie,请求中均携带Cookie
-
跨域
-
前提前端请求设置withCredentials为true
-
同站请求
- 对于HTTPS,浏览器自动携带相应的Cookie,这是默认行为
- 对于HTTP,浏览器自动携带相应的Cookie,这是默认行为
-
跨站请求
-
对于HTTPS,浏览器默认不会携带Cookie,
- 服务端设置:必须设置
Access-Control-Allow-Credentials
为true
,同时还需要设置Access-Control-Allow-Origin
头部字段来指定允许访问的源 - 客户端设置:withCredentials设置为true,同时
Set-Cookie: name=value; Secure; SameSite=None
- 服务端设置:必须设置
-
对于HTTP,浏览器默认不会携带Cookie
-
-
SameSite属性
- SameSite=None:允许跨站发送Cookie,适用于需要在跨域请求中携带Cookie的情况,需要同时配合Secure属性,即Cookie只能在Https中发送
- SameSite=Strict:禁止跨站发送Cookie,默认值。只有在同站请求中携带Cookie,跨站请求中不会携带Cookie
- SameSite=Lax:限制跨站发送Cookie,仅允许在安全跨站请求中携带Cookie(get请求),在POST请求、iframe或Ajax等情况下,将不会携带Cookie