|
|
@@ -614,35 +614,28 @@ public class WbsTreeContractController extends BladeController {
|
|
|
String originalFileName = excelName + ".xlsx";
|
|
|
|
|
|
try {
|
|
|
- // 1. 先将/替换为其他可接受字符
|
|
|
- String sanitizedFileName = originalFileName.replace("/", "∕"); // 使用除号符号(U+2215)
|
|
|
- // 或者使用其他替代字符:
|
|
|
- // .replace("/", "/") // 全角斜杠
|
|
|
- // .replace("/", "-") // 连字符
|
|
|
- // .replace("/", " or ") // 文字描述
|
|
|
+ // 1. 先编码所有字符
|
|
|
+ String fullyEncoded = URLEncoder.encode(originalFileName, StandardCharsets.UTF_8.name());
|
|
|
|
|
|
- // 2. 编码其他字符
|
|
|
- String fullyEncoded = URLEncoder.encode(sanitizedFileName, StandardCharsets.UTF_8.name());
|
|
|
-
|
|
|
- // 3. 解码我们想要保留的其他特殊字符
|
|
|
+ // 2. 解码我们想要保留的特殊字符
|
|
|
String partiallyDecoded = fullyEncoded
|
|
|
.replaceAll("\\+", "%20") // 空格保持编码为%20
|
|
|
.replaceAll("%2B", "+") // 解码+号
|
|
|
+ .replaceAll("%2F", "/") // 解码/号
|
|
|
.replaceAll("%23", "#") // 解码#号
|
|
|
.replaceAll("%7E", "~") // 解码~号
|
|
|
- // / 已经被替换,不需要处理
|
|
|
+ // - 号不需要处理,URL编码不会编码-
|
|
|
;
|
|
|
|
|
|
- // 4. 设置响应头
|
|
|
+ // 3. 设置响应头
|
|
|
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
|
|
|
response.setHeader("Content-Disposition",
|
|
|
- "attachment; filename=\"" + partiallyDecoded + "\"; " +
|
|
|
- "filename*=UTF-8''" + partiallyDecoded);
|
|
|
+ "attachment; filename=\"" + partiallyDecoded + "\"; ");
|
|
|
|
|
|
} catch (Exception e) {
|
|
|
- // 备用方案
|
|
|
+ // 备用方案:简单清理
|
|
|
String safeFileName = originalFileName
|
|
|
- .replaceAll("[\\\\/:*?\"<>|]", "_")
|
|
|
+ .replaceAll("[\\\\:*?\"<>|]", "_")
|
|
|
.trim();
|
|
|
response.setContentType("application/vnd.openxmlformats-officedocument.spreadsheetml.sheet");
|
|
|
response.setHeader("Content-Disposition",
|