springboot对于@PathVariable自动解码问题

复制代码
@GetMapping("/getFile/{key}")
public void filePreview(@PathVariable("key") String key, HttpServletResponse response) {

}

测试如下:

复制代码
// 源字符串(urlencode前)A:MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ/k5THwkM+UvaRWWd7PzFVdZoGHx/GEPxm75LJZxKq1fqCdr3PKT/5P7qqoZm9AbN4n4kZ/z9uA==
// urlencode后  B: MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ%2Fk5THwkM%2BUvaRWWd7PzFVdZoGHx%2FGEPxm75LJZxKq1fqCdr3PKT%2F5P7qqoZm9AbN4n4kZ%2Fz9uA%3D%3D  (/变成了%2F,+变为%2B,=变成%3D)
//对传入的B字符串 springboot自动解码后 C:MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ%2Fk5THwkM+UvaRWWd7PzFVdZoGHx%2FGEPxm75LJZxKq1fqCdr3PKT%2F5P7qqoZm9AbN4n4kZ%2Fz9uA==(和原来的不太一样%2F没有解码成/)
// srpingboot自动解码后的C字符串 再 使用urldecode decode后的 D: MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ/k5THwkM UvaRWWd7PzFVdZoGHx/GEPxm75LJZxKq1fqCdr3PKT/5P7qqoZm9AbN4n4kZ/z9uA==   %2B 解码变成了空格了
//没有自动解码直接decode,也就是对 B 直接解码后  E:MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ/k5THwkM+UvaRWWd7PzFVdZoGHx/GEPxm75LJZxKq1fqCdr3PKT/5P7qqoZm9AbN4n4kZ/z9uA==  (这个和源字符串一致)
//将springboot自动解码后的字符串中+替换成%2B再解码:MwbR64EbzUpX5MDnA3qb8yiTXUlbPegQqiNxuT8m7lbJ/k5THwkM+UvaRWWd7PzFVdZoGHx/GEPxm75LJZxKq1fqCdr3PKT/5P7qqoZm9AbN4n4kZ/z9uA==(和源字符串一致)-->最终解决方案

Spring Boot在处理 @RequestParam@PathVariable 等注解时,默认会自动进行一次URL解码。但它的解码方式取决于容器和版本,有时会出现:

  • %2F 没有被解码(出于安全考虑,防止路径遍历攻击)

  • %2B 被解码成了空格(+ 在URL编码的 application/x-www-form-urlencoded 中确实代表空格)

key如果包含特殊字符,必须进行urlencode,但springboot接收时会自动对key进行decode的,但测试发现有些字符串并没有decode,而且代码如果直接decode这个自动解码后的字符串解码出来的字符串可能包含空格!

  • URLDecoder.decode()默认将+转为空格,但保留%20为空格

  • Spring的@PathVariable默认将%20转为空格,但保留+为加号

URL编码规则很明确:

  • 只有空格 会被编码为 %20+

  • 其他字符(如字母、数字、中文等)都会编码为 %XX 形式

  • 解码时,%20+ 才会被转回空格

方案一:获取原始参数值(推荐)

如果你需要自己完全控制解码过程,可以直接获取原始请求参数,避免Spring Boot的自动解码干扰

相关推荐
ly76891 小时前
JavaScript 从入门到进阶:核心语法、异步编程与工程化实践
开发语言·javascript·ecmascript
落魄大学生之流水线上谋生计1 小时前
Java锁全面指南:从基础概念到企业级应用
java·开发语言
why技术1 小时前
eli5,我觉得这个全网在吹的技能,使用体验真的很一般啊。
前端·人工智能·后端
excel1 小时前
记录升级 nuxt3 到 nuxt4 记录
前端
剑胆琴心静水深流2 小时前
全栈之路6---web集成与呈现
前端·vue.js·spring boot·分布式·spring·前端框架·npm
前端snow2 小时前
ai agent -- Memory汇总
前端
爱学习的小白柏2 小时前
【AI问数技术】多Agent协同架构:查询规划/SQL生成/洞察分析/报告生成
java·网络·人工智能·windows·sql·架构·llama
ITresearchGuest2 小时前
AI 焦虑下,前端该何去何从
前端·人工智能
码匠许师傅3 小时前
【C++ 面试真题】30. 聊聊 C++ 的互斥锁与读写锁
java·c++·面试
沙盘客3 小时前
AFSIM 示例解读(03)· 六自由度飞行仿真 six_dof(下):机场运作与弹道导弹投送
java·javascript·经验分享