尧图网站建设 尧图网络
  • 首页
  • 关于我们
  • 服务项目
  • 案例展示
  • 建站流程
  • 资讯中心
  • 联系我们
首页/资讯中心/详情

Spring Boot应用CSRF防护实战与Spring Security解决方案

Spring Boot应用CSRF防护实战与Spring Security解决方案
📅 发布时间:2026/7/4 6:36:58

1. CSRF漏洞的本质与危害

CSRF(Cross-Site Request Forgery)是一种利用用户已登录状态发起的恶意请求攻击。想象这样一个场景:你在咖啡厅用笔记本登录了银行网站,此时浏览器保存了登录凭证。如果这时你点开了黑客发来的钓鱼邮件里的链接,这个页面可能偷偷向银行发送转账请求——因为浏览器会自动带上你的登录凭证,银行系统会认为这是你本人操作。

这种攻击之所以危险,是因为:

  • 攻击者无需获取用户凭证
  • 用户完全无感知
  • 可执行任意权限范围内的操作
  • 攻击成本极低

典型攻击流程:

  1. 用户登录受信任网站A
  2. 网站A在用户浏览器设置认证Cookie
  3. 用户未登出A的情况下访问恶意网站B
  4. B的页面包含自动向A发送请求的代码
  5. 浏览器自动携带A的Cookie发送请求
  6. A服务器无法区分该请求是否来自用户真实意愿

2. Spring Boot应用为何容易"裸奔"

很多Spring Boot开发者存在以下误区:

误区一:GET请求不需要防护

@GetMapping("/transfer") public String transferMoney(@RequestParam String toAccount, @RequestParam BigDecimal amount) { // 转账逻辑 }

攻击者只需构造一个图片链接:

<img src="http://bank.com/transfer?toAccount=hacker&amount=10000">

误区二:POST请求天然安全

<form action="http://bank.com/transfer" method="POST"> <input type="hidden" name="toAccount" value="hacker"> <input type="hidden" name="amount" value="10000"> </form> <script>document.forms[0].submit();</script>

误区三:前后端分离无需考虑即使使用AJAX,浏览器仍会自动携带Cookie:

fetch('/api/transfer', { method: 'POST', body: JSON.stringify({toAccount: 'hacker', amount: 10000}), headers: {'Content-Type': 'application/json'} })

3. Spring Security防御方案全解析

3.1 基础防护配置

@Configuration @EnableWebSecurity public class SecurityConfig extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { http .csrf() .csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse()) .and() // 其他配置... } }

3.2 深度防御策略

策略一:Cookie+Header双重验证

.csrfTokenRepository(new CookieCsrfTokenRepository() {{ setCookieHttpOnly(false); // 允许JS读取 setCookieName("XSRF-TOKEN"); setHeaderName("X-XSRF-TOKEN"); }})

策略二:自定义防护路径

.requireCsrfProtectionMatcher(request -> { // 只保护/api开头的POST/PUT/DELETE请求 return request.getMethod().matches("POST|PUT|DELETE") && request.getRequestURI().startsWith("/api"); })

策略三:动态Token刷新

.csrfTokenRepository(new CsrfTokenRepository() { @Override public CsrfToken generateToken(HttpServletRequest request) { return new DefaultCsrfToken( "X-CSRF-TOKEN", "_csrf", UUID.randomUUID().toString() ); } // 其他实现方法... })

4. 实战中的坑与解决方案

坑一:文件上传失效

// 错误配置 http.csrf().disable(); // 正确方案 http.csrf().ignoringAntMatchers("/upload");

坑二:前后端分离场景前端需要:

  1. 从Cookie读取XSRF-TOKEN
  2. 在每次请求Header中添加X-XSRF-TOKEN
// Axios拦截器示例 axios.interceptors.request.use(config => { const token = document.cookie .split('; ') .find(row => row.startsWith('XSRF-TOKEN=')) ?.split('=')[1]; config.headers['X-XSRF-TOKEN'] = token; return config; });

坑三:多Tab操作冲突解决方案:每个表单生成独立Token

<form> <input type="hidden" name="_csrf" th:value="${csrfToken}"> <!-- 表单内容 --> </form>

5. 高级防护技巧

技巧一:二次验证

@PostMapping("/transfer") public ResponseEntity<?> transfer( @RequestParam String toAccount, @RequestParam BigDecimal amount, @CookieValue(value = "XSRF-TOKEN") String csrfToken, @RequestHeader("X-XSRF-TOKEN") String headerToken) { if(!csrfToken.equals(headerToken)) { throw new InvalidCsrfTokenException(); } // 业务逻辑... }

技巧二:操作指纹绑定

String userFingerprint = request.getHeader("User-Agent") + request.getHeader("Accept-Language"); String storedToken = redis.get(userFingerprint); if(!storedToken.equals(request.getHeader("X-CSRF-TOKEN"))) { throw new InvalidCsrfTokenException(); }

技巧三:敏感操作限流

@RateLimiter(value = 1, timeUnit = TimeUnit.MINUTES) @PostMapping("/transfer") public ResponseEntity<?> transferMoney() { // 业务逻辑 }

6. 渗透测试常见问题

问题一:CSRF Token泄露

通过子域名或XSS漏洞可能窃取Token

解决方案:

.setCookieDomain("maindomain.com") // 限制Cookie域 .setSecure(true) // 仅HTTPS传输

问题二:Token未绑定会话

// 错误做法:所有用户使用相同Token String staticToken = "fixed_token_value"; // 正确做法:会话级Token String sessionToken = UUID.randomUUID().toString(); request.getSession().setAttribute("CSRF_TOKEN", sessionToken);

问题三:防护覆盖不全检查清单:

  • [ ] 所有状态修改操作(POST/PUT/DELETE/PATCH)
  • [ ] 文件上传接口
  • [ ] GraphQL端点
  • [ ] SOAP WebService
  • [ ] 第三方回调接口

7. Spring Security 6.x新特性

特性一:CSRF Token自动旋转

.csrfTokenRepository(new RotatingCsrfTokenRepository())

特性二:同站点Cookie属性

@Bean public CookieSerializer cookieSerializer() { DefaultCookieSerializer serializer = new DefaultCookieSerializer(); serializer.setSameSite("Strict"); return serializer; }

特性三:安全头增强

http.headers() .contentSecurityPolicy("script-src 'self'") .xssProtection() .and() .referrerPolicy(ReferrerPolicy.SAME_ORIGIN);

在实际项目中,我建议采用分层防御策略:基础CSRF防护+敏感操作二次验证+关键接口限流。曾经有个电商项目因为忽略CSRF防护,导致攻击者利用图片外链批量修改用户收货地址,这个教训让我在后续所有项目中都严格执行CSRF防护规范。

相关新闻

  • 如何快速配置PotPlayer百度翻译插件:新手完全指南
  • Android安全分析实战:3分钟快速上手工具链与自动化响应
  • AI效率工具产品化:用户访谈驱动的PMF验证方法

最新新闻

  • Python三维数学建模
  • Autopilot-Notes:高精地图与SLAM技术的融合应用深度解析
  • BlueHound与Neo4j深度集成:如何利用图数据库技术可视化攻击路径
  • 从零到一:使用MeshApiExamples创建自定义程序化网格编辑器
  • Xous代码贡献指南:从代码审查到发布流程的完整手册
  • CircularProgressView终极配置指南:15个XML属性详解与实战应用

日新闻

  • STM32F745VG与MC6470 IMU的高性能姿态控制系统设计
  • 机器不消费,人何以生存
  • AI项目操作手册编写规范与最佳实践

周新闻

  • Windows字体自定义终极方案:No!! MeiryoUI完全指南
  • Deepin Boot Maker:告别命令行,3分钟制作Linux启动盘的智能解决方案
  • Plain Craft Launcher 2:重新定义你的Minecraft游戏体验

月新闻

  • 2026年6月公司网站搭建最新热门渠道测评:四大低成本/零代码平台对比+避坑
  • 【Linux】Linux arm 编译QT程序,出现expected “}“报错
  • 【MATLAB例程】四基站二维AOA定位与距离辅助增强对比仿真。基于角度观测和测距修正的固定目标平面定位精度分析

关于尧图

  • 公司简介
  • 团队介绍
  • 企业文化
  • 荣誉资质

服务项目

  • 定制开发
  • 电商建站
  • UI 设计
  • 运维服务

快速链接

  • 案例展示
  • 建站流程
  • 常见问题
  • 资讯中心

联系方式

  • 📍北京市朝阳区互联网产业园 A 座 10 层
  • 📞400-888-8888
  • ✉️contact@rkmt.cn
  • 🕐周一至周日 9:00-21:00

© 2024 北京尧图网络科技有限公司 版权所有 | 京 ICP 备 XXXXXXXX 号