CSRF攻击原理与SameSite防御详解
解释CSRF(跨站请求伪造)攻击的原理、攻击流程,以及Cookie的SameSite属性(Strict/Lax/None)如何防御CSRF。前端开发者还应该采取哪些额外措施?
回答
孤独的心
CSRF攻击原理
攻击者诱导用户访问恶意网站,利用用户已登录目标网站的Cookie,伪造请求到目标网站执行非预期操作。
攻击流程:
- 用户登录bank.com,浏览器存储会话Cookie
- 用户访问恶意网站evil.com(未退出bank.com)
- evil.com页面发送请求(img/form/XMLHttpRequest)到bank.com/transfer
- 浏览器自动附带bank.com的Cookie(同源策略不阻止请求发送)
- bank.com验证Cookie通过,执行转账操作
Cookie SameSite属性防御
Set-Cookie: sessionId=xxx; SameSite=Lax
| SameSite值 | 描述 |
|---|---|
| Strict | 完全禁止跨站携带Cookie。链接点击也不会发送Cookie。最安全但用户体验差 |
| Lax(默认) | 允许Top-level导航的GET请求携带Cookie(a标签、地址栏、window.open)。防御CSRF的主流选择 |
| None | 不限制跨站Cookie携带。必须配合Secure(仅HTTPS)使用,不安全 |
Chrome 80+默认SameSite=Lax,显著降低了CSRF风险。
额外防御措施
1. CSRF Token(最常用)
- 服务端生成随机token,嵌入表单/Header
- 请求时验证token一致性
- 攻击者无法获取token(跨域读取不到页面内容)
2. Origin/Referer验证
- 服务端检查请求头中的Origin/Referer
- 拒绝非预期来源的请求
3. 自定义Header
- 要求请求携带
X-Requested-With: XMLHttpRequest - 简单请求(form/img)无法添加自定义Header
- 使用
fetch/XMLHttpRequest即可
4. 双重Cookie验证
- 在Cookie和请求参数中放置同一随机值
- 服务端比对两者是否匹配
5. 关键操作二次验证
- 转账/改密需要输入密码或短信验证码
- 即使CSRF成功也无法完成操作
前端开发注意事项:
- fetch/axios默认带
credentials: 'same-origin' - 跨域请求配置
credentials: 'include'时需服务端配合CORS - 不同source CRSF token或使用
SameSite=Strict - 敏感接口结合验证码或二次确认