瀏覽代碼

慧盈系统-oss上传移除过期代码,针对大于1M的图片进行分片上传

ZhangWenQiang 5 年之前
父節點
當前提交
3481225958

+ 134 - 76
happy-common/happy-common-core/src/main/java/org/jeecg/common/oss/OSSClientUtil.java

@@ -1,9 +1,10 @@
 package org.jeecg.common.oss;
 
 import com.aliyun.oss.ClientException;
-import com.aliyun.oss.OSSClient;
+import com.aliyun.oss.OSS;
 import com.aliyun.oss.OSSException;
 import com.aliyun.oss.model.*;
+import lombok.extern.slf4j.Slf4j;
 import org.jeecg.common.util.CommonUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.beans.factory.annotation.Value;
@@ -21,27 +22,38 @@ import java.security.MessageDigest;
 import java.util.*;
 
 /**
- * Created by Meng on 2017/6/8.
+ * Created by zwq on 2020/6/8.
  */
+@Slf4j
 @Component
 public class OSSClientUtil {
 
     @Autowired
-    private OSSClient ossClient;
+    private OSS ossClient;
 
     @Value("${jeecg.oss.bucketName}")
     private String bucketName;
 
     /**
-     * 销毁
+     * 关闭OSSClient。
      */
     public void destroy() {
         ossClient.shutdown();
     }
 
-
-    public String uploadImg2OSS(MultipartFile file, String fileDir) {
-        if (file.getSize() > 100 * 1024 * 1024) {
+    /**
+     * 上传
+     *
+     * @param file
+     * @param fileDir
+     * @return
+     */
+    public String uploadOSS(MultipartFile file, String fileDir) {
+        //文件上传上限 100MB
+        final long fileSize = 100 * 1024 * 1024L;
+        //分片上传 大于1MB
+        final long pageSize = 1 * 1024 * 1024L;
+        if (file.getSize() > fileSize) {
             System.out.println("上传文件大小不能超过100M!");
             return "上传文件大小不能超过100M!";
         }
@@ -52,32 +64,47 @@ public class OSSClientUtil {
         //新文件名
         String fileName = "";
         fileDir = fileDir + System.nanoTime() + "/";
+        //完整路径
+        String objectName = "";
         try {
             //文件输入流
             InputStream inputStream = file.getInputStream();
             originalFilename = CommonUtils.getFileName(originalFilename);
             //新文件名=文件名+时间戳+后缀名
             fileName = originalFilename.substring(0, originalFilename.lastIndexOf(".")) + "_" + System.currentTimeMillis() + substring;
-            this.uploadFile2OSS(inputStream, fileDir, fileName);
+            objectName = fileDir + fileName;
+            if (file.getSize() > pageSize) {
+                log.info("分片上传");
+                //分片上传
+                this.uploadPartOSS(objectName, file);
+            } else {
+                log.info("简单上传");
+                //简单上传
+                this.uploadFileOSS(inputStream, objectName);
+            }
         } catch (IOException e) {
             e.printStackTrace();
         } catch (Exception e1) {
             e1.printStackTrace();
             System.out.println("文件上传失败");
         }
-        String name = "/" + fileDir + fileName;
+        String name = "/" + objectName;
         return name;
     }
 
     /**
+     * 简单上传
      * 上传到OSS服务器  如果同名文件会覆盖服务器上的
      *
-     * @param fileName 文件名称 包括后缀名
+     * @param objectName 上传文件到OSS时需要指定包含文件后缀在内的完整路径,例如abc/efg/123.jpg。
      * @return 出错返回"" ,唯一MD5数字签名
      */
-    public String uploadFile2OSS(InputStream inStream, String fileDir, String fileName) {
-        //上传文件
-        PutObjectResult putResult = ossClient.putObject(bucketName, fileDir + fileName, inStream);
+    public String uploadFileOSS(InputStream inStream, String objectName) {
+        //上传文件流
+        //在初始化分片时设置文件存储类型
+        ObjectMetadata objectMetadata = new ObjectMetadata();
+        objectMetadata.setContentType(getcontentType(objectName.substring(objectName.lastIndexOf("."))));
+        PutObjectResult putResult = ossClient.putObject(bucketName, objectName, inStream, objectMetadata);
         String ret = putResult.getETag();
         try {
             if (inStream != null) {
@@ -91,32 +118,81 @@ public class OSSClientUtil {
     }
 
     /**
+     * 分片上传
+     * 对于同一个UploadId,分片号(PartNumber)标识了该分片在整个文件内的相对位置。如果使用同一个分片号上传了新的数据,那么OSS上这个分片已有的数据将会被覆盖
      *
+     * @param objectName 上传文件到OSS时需要指定包含文件后缀在内的完整路径,例如abc/efg/123.jpg。即fileDir+fileName
+     * @return
      */
-    public void uploadFile2OSSToo(String key, String url) throws Throwable {
-        // 设置断点续传请求
-        UploadFileRequest uploadFileRequest = new UploadFileRequest(bucketName, key);
-        // 指定上传的本地文件
-        uploadFileRequest.setUploadFile(url);
-        // 指定上传并发线程数
-        uploadFileRequest.setTaskNum(5);
-        // 指定上传的分片大小
-        uploadFileRequest.setPartSize(1 * 1024 * 1024);
-        // 开启断点续传
-        uploadFileRequest.setEnableCheckpoint(true);
-        // 断点续传上传
-        UploadFileResult result = ossClient.uploadFile(uploadFileRequest);
-        System.out.println("233--" + result);
-        // 关闭client
-    }
-
-    public String getUploadId(String key) {
-        InitiateMultipartUploadRequest request = new InitiateMultipartUploadRequest(bucketName, key);
+    public String getUploadId(String objectName) {
+        // 创建InitiateMultipartUploadRequest对象。
+        InitiateMultipartUploadRequest request = new InitiateMultipartUploadRequest(bucketName, objectName);
+        // 如果需要在初始化分片时设置文件存储类型,请参考以下代码。
+        ObjectMetadata metadata = new ObjectMetadata();
+        metadata.setContentType(getcontentType(objectName.substring(objectName.lastIndexOf("."))));
+        request.setObjectMetadata(metadata);
+        //初始化分片,返回OSS创建的全局唯一的uploadId
         InitiateMultipartUploadResult result = ossClient.initiateMultipartUpload(request);
         String uploadId = result.getUploadId();
         return uploadId;
     }
 
+    /**
+     * 上传分片
+     *
+     * @param objectName
+     * @param file
+     */
+    public void uploadPartOSS(String objectName, MultipartFile file) {
+        try {
+            //partETags是PartETag的集合。PartETag由分片的ETag和分片号组成。
+            List<PartETag> partETags = new ArrayList<PartETag>();
+            // 计算文件有多少个分片。1MB
+            final long partSize = 1 * 1024 * 1024L;
+            long fileLength = file.getSize();
+            int partCount = (int) (fileLength / partSize);
+            if (fileLength % partSize != 0) {
+                partCount++;
+            }
+            log.info("分片大小===={}", partCount);
+            String uploadId = getUploadId(objectName);
+            // 遍历分片上传。
+            for (int i = 0; i < partCount; i++) {
+                long startPos = i * partSize;
+                long curPartSize = (i + 1 == partCount) ? (fileLength - startPos) : partSize;
+                InputStream instream = file.getInputStream();
+                // 跳过已经上传的分片。
+                instream.skip(startPos);
+                UploadPartRequest uploadPartRequest = new UploadPartRequest();
+                uploadPartRequest.setBucketName(bucketName);
+                uploadPartRequest.setKey(objectName);
+                uploadPartRequest.setUploadId(uploadId);
+                uploadPartRequest.setInputStream(instream);
+                // 设置分片大小。除了最后一个分片没有大小限制,其他的分片最小为100 KB。
+                uploadPartRequest.setPartSize(curPartSize);
+                // 设置分片号。每一个上传的分片都有一个分片号,取值范围是1~10000,如果超出这个范围,OSS将返回InvalidArgument的错误码。
+                uploadPartRequest.setPartNumber(i + 1);
+                // 每个分片不需要按顺序上传,甚至可以在不同客户端上传,OSS会按照分片号排序组成完整的文件。
+                UploadPartResult uploadPartResult = ossClient.uploadPart(uploadPartRequest);
+                // 每次上传分片之后,OSS的返回结果包含PartETag。PartETag将被保存在partETags中。
+                partETags.add(uploadPartResult.getPartETag());
+            }
+            //完成上传
+            completeMultipartUpload(objectName, partETags, uploadId);
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+    }
+
+    /**
+     * 完成分片上传
+     */
+    public void completeMultipartUpload(String fileName, List<PartETag> partETags, String uploadId) {
+        //创建CompleteMultipartUploadRequest对象。
+        CompleteMultipartUploadRequest completeMultipartUploadRequest = new CompleteMultipartUploadRequest(bucketName, fileName, uploadId, partETags);
+        // 完成上传。
+        CompleteMultipartUploadResult completeMultipartUploadResult = ossClient.completeMultipartUpload(completeMultipartUploadRequest);
+    }
 
     /**
      * 获取已上传的分片
@@ -139,48 +215,6 @@ public class OSSClientUtil {
     }
 
     /**
-     * 上传分片
-     */
-    public void uploadSetEnableCheckpoint(String key, String localFile) {
-        List<PartETag> partETags = new ArrayList<PartETag>();
-        InputStream instream = null;
-        try {
-            instream = new FileInputStream(new File(localFile));
-        } catch (FileNotFoundException e) {
-            e.printStackTrace();
-        }
-        UploadPartRequest uploadPartRequest = new UploadPartRequest();
-        uploadPartRequest.setBucketName(bucketName);
-        uploadPartRequest.setKey(key);
-        String uploadId = "7188157413A24508B8E327913AFBFCCE";
-        uploadPartRequest.setUploadId(uploadId);
-        uploadPartRequest.setInputStream(instream);
-        // 设置分片大小,除最后一个分片外,其它分片要大于100KB
-        uploadPartRequest.setPartSize(100 * 1024);
-        // 设置分片号,范围是1~10000,
-        uploadPartRequest.setPartNumber(1);
-        UploadPartResult uploadPartResult = ossClient.uploadPart(uploadPartRequest);
-        partETags.add(uploadPartResult.getPartETag());
-        completeMultipartUpload(key, partETags);
-    }
-
-    /**
-     * 完成分片上传
-     */
-    public void completeMultipartUpload(String key, List<PartETag> partETags) {
-        String uploadId = "490C8D60323F4AE3ACA2C627A785902A";
-        Collections.sort(partETags, new Comparator<PartETag>() {
-            @Override
-            public int compare(PartETag p1, PartETag p2) {
-                return p1.getPartNumber() - p2.getPartNumber();
-            }
-        });
-        CompleteMultipartUploadRequest completeMultipartUploadRequest =
-                new CompleteMultipartUploadRequest(bucketName, key, uploadId, partETags);
-        ossClient.completeMultipartUpload(completeMultipartUploadRequest);
-    }
-
-    /**
      * 取消分片上传事件
      */
     public void abortMultipartUpload(String key) {
@@ -263,6 +297,30 @@ public class OSSClientUtil {
     }
 
     /**
+     * 断点续传
+     *
+     * @param key
+     * @param url
+     * @throws Throwable
+     */
+    public void uploadFile2OSSToo(String key, String url) throws Throwable {
+        // 设置断点续传请求
+        UploadFileRequest uploadFileRequest = new UploadFileRequest(bucketName, key);
+        // 指定上传的本地文件
+        uploadFileRequest.setUploadFile(url);
+        // 指定上传并发线程数
+        uploadFileRequest.setTaskNum(5);
+        // 指定上传的分片大小
+        uploadFileRequest.setPartSize(1 * 1024 * 1024);
+        // 开启断点续传
+        uploadFileRequest.setEnableCheckpoint(true);
+        // 断点续传上传
+        UploadFileResult result = ossClient.uploadFile(uploadFileRequest);
+        System.out.println("233--" + result);
+        // 关闭client
+    }
+
+    /**
      * Description: 判断OSS服务文件上传时文件的contentType
      *
      * @param FilenameExtension 文件后缀
@@ -310,8 +368,8 @@ public class OSSClientUtil {
      * @return
      */
     public String getUrl(String key) {
-        // 设置URL过期时间为10年  3600l* 1000*24*365*10
-        Date expiration = new Date(new Date().getTime() + 3600l * 1000 * 24 * 365 * 10);
+        // 设置URL过期时间为10年  3600L* 1000*24*365*10
+        Date expiration = new Date(System.currentTimeMillis() + 3600L * 1000 * 24 * 365 * 10);
         // 生成URL
         URL url = ossClient.generatePresignedUrl(bucketName, key, expiration);
         if (url != null) {

+ 1 - 1
happy-common/happy-common-core/src/main/java/org/jeecg/common/system/controller/FileController.java

@@ -251,7 +251,7 @@ public class FileController {
             String fileDir = USERFILES_BASE_URL + uploadPath + "/" + sysUser.getUsername() + "/" + year + "/" + month + "/";
             // 判断文件是否为空
             if (!file.isEmpty()) {
-                String filePath = ossClientUtil.uploadImg2OSS(file, fileDir);
+                String filePath = ossClientUtil.uploadOSS(file, fileDir);
                 System.out.println("lu" + filePath);
                 if ("上传文件大小不能超过100M!".equals(filePath) || "文件上传失败".equals(filePath)) {
                     result.setSuccess(false);

+ 4 - 3
happy-common/happy-common-core/src/main/java/org/jeecg/config/oss/OSSConfig.java

@@ -1,6 +1,7 @@
 package org.jeecg.config.oss;
 
-import com.aliyun.oss.OSSClient;
+import com.aliyun.oss.OSS;
+import com.aliyun.oss.OSSClientBuilder;
 import org.springframework.beans.factory.annotation.Value;
 import org.springframework.context.annotation.Bean;
 import org.springframework.context.annotation.Configuration;
@@ -26,8 +27,8 @@ public class OSSConfig {
      * @return
      */
     @Bean
-    public OSSClient ossClient() {
-        OSSClient ossClient = new OSSClient(endpoint, accessKeyId, accessKeySecret);
+    public OSS ossClient() {
+        OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
         return ossClient;
     }