From 9c3c085032bddf6bb5e8b730067292e7f1520328 Mon Sep 17 00:00:00 2001
From: zhaowenyu <35589726@qq.com>
Date: Wed, 04 Feb 2026 14:54:56 +0800
Subject: [PATCH] 2026-02-04 优化minio上传

---
 ard-admin/src/main/java/com/ard/web/controller/sample/media/MinioProxyUploadController.java |   38 +++++++++++++++++++++++++++-----------
 1 files changed, 27 insertions(+), 11 deletions(-)

diff --git a/ard-admin/src/main/java/com/ard/web/controller/sample/media/MinioProxyUploadController.java b/ard-admin/src/main/java/com/ard/web/controller/sample/media/MinioProxyUploadController.java
index 649e862..97a59b7 100644
--- a/ard-admin/src/main/java/com/ard/web/controller/sample/media/MinioProxyUploadController.java
+++ b/ard-admin/src/main/java/com/ard/web/controller/sample/media/MinioProxyUploadController.java
@@ -75,22 +75,38 @@
             HttpServletRequest request
     ) {
         log.info("接收参数bucketName:{}",bucketName);
-        // ===================== 1. 解析原始路径:保留所有斜杠/末尾分隔符,完全对齐原生MinIO =====================
-        String rawUri = request.getRequestURI();
-        String requestUri = URLDecoder.decode(rawUri, StandardCharsets.UTF_8);
+        // ===================== 核心修复:安全路径解析,替换替代截取,杜绝索引错误 =====================
+        // String contextPath = request.getContextPath();
+        String rawUri = URLDecoder.decode(request.getRequestURI(), StandardCharsets.UTF_8);
+        // 剔除上下文路径,得到纯业务路径
+        String purePath = rawUri.substring("/minioTransfer".length());
         String bucketPrefix = "/" + bucketName;
-        // 提取原始ObjectKey,无任何修改
-        String objectKey = requestUri.substring(bucketPrefix.length());
 
-        log.info("中转MinIO PUT请求 | 桶名:{} | 原始对象路径:{} | 请求体大小:{}byte",
-                bucketName, objectKey, rawRequestBody == null ? 0 : rawRequestBody.length);
+        log.info("中转MinIO 路径解析开始 | 原始URI:{} | 纯业务路径:{} | 桶前缀:{}", rawUri, purePath, bucketPrefix);
+
+        // 校验路径是否以桶前缀开头
+        if (!purePath.startsWith(bucketPrefix)) {
+            return buildNativeS3Error("InvalidRequest", "请求路径格式不匹配", rawUri, HttpStatus.BAD_REQUEST);
+        }
+
+        // 修复点:replace替换前缀,替代 substring 长度截取,彻底解决索引错位问题
+        String objectKey = purePath.replaceFirst("^" + bucketPrefix, "");
+        // 兜底处理空路径
+        if (objectKey.isEmpty()) {
+            objectKey = "/";
+        }
+
+        log.info("中转MinIO 路径解析成功 | 纯业务路径:{} | 桶名:{} | 最终对象路径:{}",
+                purePath, bucketName, objectKey);
+
+        // byte[] requestData = rawRequestBody == null ? new byte[0] : rawRequestBody;
 
         try {
             // ===================== 2. 复用原有逻辑:获取临时凭证 =====================
             var credentials = ossService.getCredentials();
             if (credentials == null || credentials.getAccessKeyId() == null || credentials.getSecurityToken() == null) {
                 log.error("临时凭证获取失败");
-                return buildNativeS3Error("InvalidCredentials", "临时凭证无效", requestUri, HttpStatus.FORBIDDEN);
+                return buildNativeS3Error("InvalidCredentials", "临时凭证无效", rawUri, HttpStatus.FORBIDDEN);
             }
 
             // ===================== 3. 复用原有逻辑:构建MinIO客户端 =====================
@@ -106,7 +122,7 @@
             // 校验桶存在性(兼容原生接口行为,桶不存在返回404)
             boolean bucketExists = minioClient.bucketExists(BucketExistsArgs.builder().bucket(bucketName).build());
             if (!bucketExists) {
-                return buildNativeS3Error("NoSuchBucket", "指定存储桶不存在", requestUri, HttpStatus.NOT_FOUND);
+                return buildNativeS3Error("NoSuchBucket", "指定存储桶不存在", bucketName, HttpStatus.NOT_FOUND);
             }
 
             // ===================== 4. 透传请求:原样转发大疆原始数据到MinIO,无业务篡改 =====================
@@ -145,10 +161,10 @@
                     .body(nativeError);
         } catch (MinioException e) {
             log.error("MinIO客户端异常:{}", e.getMessage());
-            return buildNativeS3Error("ClientError", e.getMessage(), requestUri, HttpStatus.INTERNAL_SERVER_ERROR);
+            return buildNativeS3Error("ClientError", e.getMessage(), rawUri, HttpStatus.INTERNAL_SERVER_ERROR);
         } catch (Exception e) {
             log.error("代理中转通用异常:{}", e.getMessage(), e);
-            return buildNativeS3Error("InternalError", "服务器代理异常", requestUri, HttpStatus.INTERNAL_SERVER_ERROR);
+            return buildNativeS3Error("InternalError", "服务器代理异常", rawUri, HttpStatus.INTERNAL_SERVER_ERROR);
         }
     }
 

--
Gitblit v1.9.3