Browse Source

【代码优化】S3FileClient

puhui999 1 year ago
parent
commit
cf40cce552

+ 64 - 81
yudao-module-infra/yudao-module-infra-biz/src/main/java/cn/iocoder/yudao/module/infra/framework/file/core/client/s3/S3FileClient.java

@@ -9,7 +9,6 @@ import software.amazon.awssdk.auth.credentials.StaticCredentialsProvider;
 import software.amazon.awssdk.core.sync.RequestBody;
 import software.amazon.awssdk.regions.Region;
 import software.amazon.awssdk.services.s3.S3Client;
-import software.amazon.awssdk.services.s3.S3Configuration;
 import software.amazon.awssdk.services.s3.model.DeleteObjectRequest;
 import software.amazon.awssdk.services.s3.model.GetObjectRequest;
 import software.amazon.awssdk.services.s3.model.PutObjectRequest;
@@ -32,38 +31,86 @@ public class S3FileClient extends AbstractFileClient<S3FileClientConfig> {
         super(id, config);
     }
 
+    @Override
+    protected void doInit() {
+        // 补全 domain
+        if (StrUtil.isEmpty(config.getDomain())) {
+            config.setDomain(buildDomain());
+        }
+        // 初始化 S3 客户端
+        client = S3Client.builder()
+                .credentialsProvider(buildCredentials())
+                .region(Region.of("us-east-1")) // 必须填,但填什么都行,常见的值有 "us-east-1",不填会报错
+                .endpointOverride(URI.create(buildEndpoint()))
+                //.serviceConfiguration(S3Configuration.builder().pathStyleAccessEnabled(true).build()) //  Path-style 访问
+                .build();
+    }
+
+    @Override
+    public String upload(byte[] content, String path, String type) {
+        // 构造 PutObjectRequest
+        PutObjectRequest putRequest = PutObjectRequest.builder()
+                .bucket(config.getBucket())
+                .key(path)
+                .contentType(type)
+                .contentLength((long) content.length)
+                .build();
+
+        // 上传文件
+        client.putObject(putRequest, RequestBody.fromBytes(content));
+        // 拼接返回路径
+        return config.getDomain() + "/" + path;
+    }
+
+    @Override
+    public void delete(String path) {
+        DeleteObjectRequest deleteRequest = DeleteObjectRequest.builder()
+                .bucket(config.getBucket())
+                .key(path)
+                .build();
+        client.deleteObject(deleteRequest);
+    }
+
+    @Override
+    public byte[] getContent(String path) {
+        GetObjectRequest getRequest = GetObjectRequest.builder()
+                .bucket(config.getBucket())
+                .key(path)
+                .build();
+
+        return IoUtil.readBytes(client.getObject(getRequest));
+    }
+
+    @Override
+    public FilePresignedUrlRespDTO getPresignedObjectUrl(String path) {
+        return new FilePresignedUrlRespDTO(getPresignedUrl(path, Duration.ofMinutes(10)), config.getDomain() + "/" + path);
+    }
+
     /**
      * 动态创建 S3Presigner
      *
-     * @param endpoint  节点地址
-     * @param accessKey 访问 Key
-     * @param secretKey 访问 Secret
      * @return S3Presigner
      */
-    private static S3Presigner createPresigner(String endpoint, String accessKey, String secretKey) {
+    private S3Presigner createPresigner() {
         return S3Presigner.builder()
-                .credentialsProvider(StaticCredentialsProvider.create(AwsBasicCredentials.create(accessKey, secretKey)))
-                .endpointOverride(URI.create(endpoint))
+                .credentialsProvider(StaticCredentialsProvider.create(AwsBasicCredentials.create(config.getAccessKey(), config.getAccessSecret())))
+                .region(Region.of("us-east-1")) // 必须填,但填什么都行,常见的值有 "us-east-1",不填会报错
+                .endpointOverride(URI.create(buildEndpoint()))
                 .build();
     }
 
     /**
      * 生成动态的预签名上传 URL
      *
-     * @param bucket    存储 Bucket
-     * @param path      相对路径
-     * @param duration  过期时间
-     * @param endpoint  节点地址
-     * @param accessKey 访问 Key
-     * @param secretKey 访问 Secret
+     * @param path     相对路径
+     * @param duration 过期时间
      * @return 生成的上传 URL
      */
-    public static String getPresignedUrl(String bucket, String path, Duration duration,
-                                         String endpoint, String accessKey, String secretKey) {
-        try (S3Presigner presigner = createPresigner(endpoint, accessKey, secretKey)) {
+    public String getPresignedUrl(String path, Duration duration) {
+        try (S3Presigner presigner = createPresigner()) {
             return presigner.presignPutObject(PutObjectPresignRequest.builder()
                     .signatureDuration(duration)
-                    .putObjectRequest(b -> b.bucket(bucket).key(path))
+                    .putObjectRequest(b -> b.bucket(config.getBucket()).key(path))
                     .build()).url().toString();
         }
     }
@@ -82,21 +129,6 @@ public class S3FileClient extends AbstractFileClient<S3FileClientConfig> {
         return StrUtil.format("https://{}.{}", config.getBucket(), config.getEndpoint());
     }
 
-    @Override
-    protected void doInit() {
-        // 补全 domain
-        if (StrUtil.isEmpty(config.getDomain())) {
-            config.setDomain(buildDomain());
-        }
-        // 初始化 S3 客户端
-        client = S3Client.builder()
-                .credentialsProvider(buildCredentials())
-                .region(Region.of(config.getEndpoint())) // 这里随便填,SDK 需要
-                .endpointOverride(URI.create(buildEndpoint()))
-                .serviceConfiguration(S3Configuration.builder().pathStyleAccessEnabled(true).build()) //  Path-style 访问
-                .build();
-    }
-
     /**
      * 基于 config 秘钥,构建 S3 客户端的认证信息
      *
@@ -120,53 +152,4 @@ public class S3FileClient extends AbstractFileClient<S3FileClientConfig> {
         return StrUtil.format("https://{}", config.getEndpoint());
     }
 
-    @Override
-    public String upload(byte[] content, String path, String type) {
-        // 构造 PutObjectRequest
-        PutObjectRequest putRequest = PutObjectRequest.builder()
-                .bucket(config.getBucket())
-                .key(path)
-                .contentType(type)
-                .contentLength((long) content.length)
-                .build();
-
-        // 上传文件
-        client.putObject(putRequest, RequestBody.fromBytes(content));
-        // 拼接返回路径
-        return config.getDomain() + "/" + path;
-    }
-
-    @Override
-    public void delete(String path) {
-        DeleteObjectRequest deleteRequest = DeleteObjectRequest.builder()
-                .bucket(config.getBucket())
-                .key(path)
-                .build();
-        client.deleteObject(deleteRequest);
-    }
-
-    @Override
-    public byte[] getContent(String path) {
-        GetObjectRequest getRequest = GetObjectRequest.builder()
-                .bucket(config.getBucket())
-                .key(path)
-                .build();
-
-        return IoUtil.readBytes(client.getObject(getRequest));
-    }
-
-    @Override
-    public FilePresignedUrlRespDTO getPresignedObjectUrl(String path) {
-        String presignedUrl = getPresignedUrl(
-                config.getBucket(),
-                path,
-                Duration.ofMinutes(10),
-                config.getEndpoint(),
-                config.getAccessKey(),
-                config.getAccessSecret()
-        );
-
-        return new FilePresignedUrlRespDTO(presignedUrl, config.getDomain() + "/" + path);
-    }
-
 }