commit
697f243a19
20
README.md
20
README.md
@ -3,7 +3,7 @@
|
||||
<a href="http://fileos.qiwenshare.com/"><img width="30%" src="https://images.gitee.com/uploads/images/2020/0810/131432_e00bbf82_947714.png" ></a>
|
||||
</p>
|
||||
<p align="center">
|
||||
<strong>基于springboot + vue 框架开发的Web文件系统,旨在为用户提供一个简单、方便的文件存储方案,能够以完善的目录结构体系,对文件进行管理 。</strong>
|
||||
<strong>基于Spring Boot + VUE CLI@3 框架开发的分布式文件系统,旨在为用户和企业提供一个简单、方便的文件存储方案,能够以完善的目录结构体系,对文件进行管理 。</strong>
|
||||
</p>
|
||||
<p align="center">
|
||||
<a target="_blank" href="https://baike.baidu.com/item/MIT%E8%AE%B8%E5%8F%AF%E8%AF%81/6671281?fr=aladdin">
|
||||
@ -15,7 +15,6 @@
|
||||
<a target="_blank" href="https://gitee.com/mingSoft/MCMS/stargazers">
|
||||
<img src="https://gitee.com/qiwen-cloud/qiwen-file/badge/star.svg?theme=dark" alt='gitee star'/>
|
||||
</a>
|
||||
|
||||
</p>
|
||||
<p align="center">
|
||||
<a href="http://pan.qiwenshare.com/" target="_blank">在线演示环境</a> |
|
||||
@ -42,13 +41,24 @@
|
||||
3. 支持对zip文件和rar文件的在线解压缩
|
||||
4. 支持文件和目录的移动和复制
|
||||
5. 多文件格式分类查看
|
||||
6. 支持阿里云OSS对象存储
|
||||
7. 增加分片上传,该功能同时支持本地存储和阿里云OSS
|
||||
6. 支持阿里云OSS对象存储,FastDFS存储
|
||||
7. 增加分片上传,该功能同时支持本地存储和阿里云OSS,FastDFS
|
||||
8. 支持极速秒传功能,提高上传效率
|
||||
9. 上传文件前台实时显示上传文件进度,上传速率,百分比等信息
|
||||
10. 支持文件重命名
|
||||
11. 可实时显示文件存储占用情况及总占用容量
|
||||
12. ...
|
||||
12. 支持ElasticSearch文件搜索
|
||||
13. ...
|
||||
|
||||
## 项目代码地址
|
||||
|系统|地址|
|
||||
|-|-|
|
||||
|奇文网盘前台|[https://gitee.com/qiwen-cloud/qiwen-file-web](https://gitee.com/qiwen-cloud/qiwen-file-web)|
|
||||
|奇文网盘后台|[https://gitee.com/qiwen-cloud/qiwen-file](https://gitee.com/qiwen-cloud/qiwen-file)|
|
||||
|
||||
## 网络拓扑图
|
||||
|
||||

|
||||
|
||||
## 软件架构
|
||||
该项目采用前后端分离的方式进行开发和部署,主要用到以下关键技术
|
||||
|
@ -43,18 +43,20 @@
|
||||
<artifactId>jjwt</artifactId>
|
||||
<version>0.9.1</version>
|
||||
</dependency>
|
||||
<!-- <dependency>-->
|
||||
<!-- <groupId>org.csource</groupId>-->
|
||||
<!-- <artifactId>fastdfs-client-java</artifactId>-->
|
||||
<!-- <version>1.27-SNAPSHOT</version>-->
|
||||
<!-- </dependency>-->
|
||||
<!-- https://mvnrepository.com/artifact/net.oschina.zcx7878/fastdfs-client-java -->
|
||||
|
||||
<dependency>
|
||||
<groupId>net.oschina.zcx7878</groupId>
|
||||
<artifactId>fastdfs-client-java</artifactId>
|
||||
<version>1.27.0.0</version>
|
||||
<groupId>com.github.tobato</groupId>
|
||||
<artifactId>fastdfs-client</artifactId>
|
||||
<version>1.26.2</version>
|
||||
</dependency>
|
||||
|
||||
<!--redis-->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-data-redis</artifactId>
|
||||
</dependency>
|
||||
|
||||
|
||||
</dependencies>
|
||||
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.config;
|
||||
package com.qiwenshare.common.config;
|
||||
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import lombok.Data;
|
@ -0,0 +1,14 @@
|
||||
package com.qiwenshare.common.config;
|
||||
|
||||
import com.github.tobato.fastdfs.FdfsClientConfig;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.EnableMBeanExport;
|
||||
import org.springframework.context.annotation.Import;
|
||||
import org.springframework.jmx.support.RegistrationPolicy;
|
||||
|
||||
@Configuration
|
||||
@Import(FdfsClientConfig.class)
|
||||
@EnableMBeanExport(registration = RegistrationPolicy.IGNORE_EXISTING)
|
||||
public class FdfsConfig {
|
||||
|
||||
}
|
@ -1,8 +1,7 @@
|
||||
package com.qiwenshare.file.config;
|
||||
package com.qiwenshare.common.config;
|
||||
|
||||
import lombok.Data;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.boot.context.properties.NestedConfigurationProperty;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Data
|
||||
@ -12,6 +11,9 @@ public class QiwenFileConfig {
|
||||
|
||||
private boolean shareMode;
|
||||
|
||||
private String storageType;
|
||||
private String cacheMode;
|
||||
|
||||
private AliyunConfig aliyun = new AliyunConfig();
|
||||
|
||||
}
|
@ -0,0 +1,37 @@
|
||||
package com.qiwenshare.common.config;
|
||||
|
||||
|
||||
import org.springframework.cache.annotation.CachingConfigurerSupport;
|
||||
import org.springframework.cache.annotation.EnableCaching;
|
||||
import org.springframework.cache.interceptor.KeyGenerator;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@Configuration
|
||||
@EnableCaching
|
||||
public class RedisAutoConfiguration extends CachingConfigurerSupport {
|
||||
|
||||
@Bean
|
||||
public KeyGenerator keyGenerator() {
|
||||
return (target, method, params) -> {
|
||||
StringBuilder sb = new StringBuilder();
|
||||
sb.append(target.getClass().getName());
|
||||
sb.append(method.getName());
|
||||
for (Object obj : params) {
|
||||
sb.append(obj.toString());
|
||||
}
|
||||
return sb.toString();
|
||||
};
|
||||
}
|
||||
|
||||
// @Bean
|
||||
// public CacheManager cacheManager(RedisConnectionFactory redisConnectionFactory) {
|
||||
// RedisCacheConfiguration redisCacheConfiguration = RedisCacheConfiguration.defaultCacheConfig()
|
||||
// .entryTtl(Duration.ofHours(1)); // 设置缓存有效期一小时
|
||||
// return RedisCacheManager
|
||||
// .builder(RedisCacheWriter.nonLockingRedisCacheWriter(redisConnectionFactory))
|
||||
// .cacheDefaults(redisCacheConfiguration).build();
|
||||
// }
|
||||
|
||||
}
|
||||
|
@ -0,0 +1,9 @@
|
||||
package com.qiwenshare.common.domain;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class DeleteFile {
|
||||
private String fileUrl;
|
||||
private String timeStampName;
|
||||
}
|
@ -0,0 +1,9 @@
|
||||
package com.qiwenshare.common.domain;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class DownloadFile {
|
||||
private String fileUrl;
|
||||
private String timeStampName;
|
||||
}
|
@ -11,7 +11,9 @@ public class UploadFile {
|
||||
private int success;
|
||||
private String message;
|
||||
private String url;
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
private Integer storageType;
|
||||
//切片上传相关参数
|
||||
private String taskId;
|
||||
private int chunkNumber;
|
||||
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.common.cbb;
|
||||
package com.qiwenshare.common.exception;
|
||||
|
||||
public class NotSameFileExpection extends Exception {
|
||||
public NotSameFileExpection() {
|
@ -0,0 +1,12 @@
|
||||
package com.qiwenshare.common.exception;
|
||||
|
||||
public abstract class UploadException extends RuntimeException{
|
||||
|
||||
protected UploadException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
protected UploadException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
}
|
@ -0,0 +1,16 @@
|
||||
package com.qiwenshare.common.exception;
|
||||
|
||||
public class UploadGeneralException extends UploadException{
|
||||
|
||||
public UploadGeneralException(Throwable cause) {
|
||||
super("上传出现了异常", cause);
|
||||
}
|
||||
|
||||
public UploadGeneralException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
public UploadGeneralException(String message, Throwable cause) {
|
||||
super(message, cause);
|
||||
}
|
||||
}
|
@ -0,0 +1,39 @@
|
||||
package com.qiwenshare.common.factory;
|
||||
|
||||
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.operation.delete.product.AliyunOSSDeleter;
|
||||
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.operation.download.product.AliyunOSSDownloader;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import com.qiwenshare.common.operation.upload.product.AliyunOSSUploader;
|
||||
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
@Component
|
||||
public class AliyunOSSOperationFactory implements FileOperationFactory {
|
||||
@Resource
|
||||
AliyunOSSUploader aliyunOSSUploader;
|
||||
@Resource
|
||||
AliyunOSSDownloader aliyunOSSDownloader;
|
||||
@Resource
|
||||
AliyunOSSDeleter aliyunOSSDeleter;
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return aliyunOSSUploader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Downloader getDownloader() {
|
||||
return aliyunOSSDownloader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Deleter getDeleter() {
|
||||
return aliyunOSSDeleter;
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,38 @@
|
||||
package com.qiwenshare.common.factory;
|
||||
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.operation.delete.product.FastDFSDeleter;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.operation.download.product.FastDFSDownloader;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import com.qiwenshare.common.operation.upload.product.FastDFSUploader;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
@Component
|
||||
public class FastDFSOperationFactory implements FileOperationFactory {
|
||||
|
||||
@Resource
|
||||
FastDFSUploader fastDFSUploader;
|
||||
@Resource
|
||||
FastDFSDownloader fastDFSDownloader;
|
||||
@Resource
|
||||
FastDFSDeleter fastDFSDeleter;
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return fastDFSUploader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Downloader getDownloader() {
|
||||
return fastDFSDownloader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Deleter getDeleter() {
|
||||
return fastDFSDeleter;
|
||||
}
|
||||
|
||||
|
||||
}
|
@ -0,0 +1,11 @@
|
||||
package com.qiwenshare.common.factory;
|
||||
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
|
||||
public interface FileOperationFactory {
|
||||
Uploader getUploader();
|
||||
Downloader getDownloader();
|
||||
Deleter getDeleter();
|
||||
}
|
@ -0,0 +1,38 @@
|
||||
package com.qiwenshare.common.factory;
|
||||
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.operation.delete.product.LocalStorageDeleter;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.operation.download.product.LocalStorageDownloader;
|
||||
import com.qiwenshare.common.operation.upload.product.LocalStorageUploader;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
@Component
|
||||
public class LocalStorageOperationFactory implements FileOperationFactory{
|
||||
|
||||
@Resource
|
||||
LocalStorageUploader localStorageUploader;
|
||||
@Resource
|
||||
LocalStorageDownloader localStorageDownloader;
|
||||
@Resource
|
||||
LocalStorageDeleter localStorageDeleter;
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return localStorageUploader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Downloader getDownloader() {
|
||||
return localStorageDownloader;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Deleter getDeleter() {
|
||||
return localStorageDeleter;
|
||||
}
|
||||
|
||||
|
||||
}
|
@ -278,9 +278,9 @@ public class FileOperation {
|
||||
}
|
||||
}
|
||||
for (String zipPath : fileEntryNameList) {
|
||||
if (FileUtil.isImageFile(FileUtil.getFileType(zipPath))) {
|
||||
if (FileUtil.isImageFile(FileUtil.getFileExtendName(zipPath))) {
|
||||
File file = new File(destDirPath + zipPath);
|
||||
File minFile = new File(destDirPath + FileUtil.getFileNameNotExtend(zipPath) + "_min." + FileUtil.getFileType(zipPath));
|
||||
File minFile = new File(destDirPath + FileUtil.getFileNameNotExtend(zipPath) + "_min." + FileUtil.getFileExtendName(zipPath));
|
||||
try {
|
||||
ImageOperation.thumbnailsImage(file, minFile, 300);
|
||||
} catch (IOException e) {
|
||||
@ -361,7 +361,7 @@ public class FileOperation {
|
||||
|
||||
public static long deleteFileFromDisk(String fileurl) {
|
||||
String fileUrl = PathUtil.getStaticPath() + fileurl;
|
||||
String extendName = FileUtil.getFileType(fileUrl);
|
||||
String extendName = FileUtil.getFileExtendName(fileUrl);
|
||||
String minFileUrl = fileUrl.replace("." + extendName, "_min." + extendName);
|
||||
long filesize = getFileSize(fileUrl);
|
||||
|
||||
|
@ -0,0 +1,7 @@
|
||||
package com.qiwenshare.common.operation.delete;
|
||||
|
||||
import com.qiwenshare.common.domain.DeleteFile;
|
||||
|
||||
public abstract class Deleter {
|
||||
public abstract void delete(DeleteFile deleteFile);
|
||||
}
|
@ -0,0 +1,32 @@
|
||||
package com.qiwenshare.common.operation.delete.product;
|
||||
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.domain.DeleteFile;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
||||
@Component
|
||||
public class AliyunOSSDeleter extends Deleter {
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
@Override
|
||||
public void delete(DeleteFile deleteFile) {
|
||||
// AliyunOSSDelete.deleteObject(qiwenFileConfig.getAliyun().getOss(), deleteFile.getFileUrl().substring(1));
|
||||
String endpoint = qiwenFileConfig.getAliyun().getOss().getEndpoint();
|
||||
String accessKeyId = qiwenFileConfig.getAliyun().getOss().getAccessKeyId();
|
||||
String accessKeySecret = qiwenFileConfig.getAliyun().getOss().getAccessKeySecret();
|
||||
String bucketName = qiwenFileConfig.getAliyun().getOss().getBucketName();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
|
||||
ossClient.deleteObject(bucketName, deleteFile.getFileUrl().substring(1));
|
||||
|
||||
|
||||
|
||||
// 关闭OSSClient。
|
||||
ossClient.shutdown();
|
||||
}
|
||||
}
|
@ -0,0 +1,17 @@
|
||||
package com.qiwenshare.common.operation.delete.product;
|
||||
|
||||
import com.github.tobato.fastdfs.service.FastFileStorageClient;
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.domain.DeleteFile;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public class FastDFSDeleter extends Deleter {
|
||||
@Autowired
|
||||
private FastFileStorageClient fastFileStorageClient;
|
||||
@Override
|
||||
public void delete(DeleteFile deleteFile) {
|
||||
fastFileStorageClient.deleteFile(deleteFile.getFileUrl());
|
||||
}
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
package com.qiwenshare.common.operation.delete.product;
|
||||
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.domain.DeleteFile;
|
||||
import com.qiwenshare.common.operation.FileOperation;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public class LocalStorageDeleter extends Deleter {
|
||||
@Override
|
||||
public void delete(DeleteFile deleteFile) {
|
||||
FileOperation.deleteFile(PathUtil.getStaticPath() + deleteFile.getFileUrl());
|
||||
if (FileUtil.isImageFile(FileUtil.getFileExtendName(deleteFile.getFileUrl()))) {
|
||||
FileOperation.deleteFile(PathUtil.getStaticPath() + deleteFile.getFileUrl().replace(deleteFile.getTimeStampName(), deleteFile.getTimeStampName() + "_min"));
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,9 @@
|
||||
package com.qiwenshare.common.operation.download;
|
||||
|
||||
import com.qiwenshare.common.domain.DownloadFile;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
public abstract class Downloader {
|
||||
public abstract void download(HttpServletResponse httpServletResponse, DownloadFile uploadFile);
|
||||
}
|
@ -0,0 +1,62 @@
|
||||
package com.qiwenshare.common.operation.download.product;
|
||||
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.OSSObject;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.common.domain.DownloadFile;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.BufferedInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
|
||||
@Component
|
||||
public class AliyunOSSDownloader extends Downloader {
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
@Override
|
||||
public void download(HttpServletResponse httpServletResponse, DownloadFile downloadFile) {
|
||||
|
||||
BufferedInputStream bis = null;
|
||||
byte[] buffer = new byte[1024];
|
||||
|
||||
OSS ossClient = createOSSClient(qiwenFileConfig.getAliyun().getOss());
|
||||
OSSObject ossObject = ossClient.getObject(qiwenFileConfig.getAliyun().getOss().getBucketName(), downloadFile.getTimeStampName());
|
||||
InputStream inputStream = ossObject.getObjectContent();
|
||||
try {
|
||||
bis = new BufferedInputStream(inputStream);
|
||||
OutputStream os = httpServletResponse.getOutputStream();
|
||||
int i = bis.read(buffer);
|
||||
while (i != -1) {
|
||||
os.write(buffer, 0, i);
|
||||
i = bis.read(buffer);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (bis != null) {
|
||||
try {
|
||||
bis.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
ossClient.shutdown();
|
||||
}
|
||||
|
||||
public OSS createOSSClient(AliyunOSS aliyunOSS) {
|
||||
String endpoint = aliyunOSS.getEndpoint();
|
||||
String accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
String accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
return ossClient;
|
||||
}
|
||||
}
|
@ -0,0 +1,43 @@
|
||||
package com.qiwenshare.common.operation.download.product;
|
||||
|
||||
import com.github.tobato.fastdfs.proto.storage.DownloadByteArray;
|
||||
import com.github.tobato.fastdfs.service.FastFileStorageClient;
|
||||
import com.qiwenshare.common.domain.DownloadFile;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.servlet.ServletOutputStream;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.IOException;
|
||||
|
||||
@Component
|
||||
public class FastDFSDownloader extends Downloader {
|
||||
@Autowired
|
||||
private FastFileStorageClient fastFileStorageClient;
|
||||
@Override
|
||||
public void download(HttpServletResponse httpServletResponse, DownloadFile downloadFile) {
|
||||
String group = downloadFile.getFileUrl().substring(0, downloadFile.getFileUrl().indexOf("/"));
|
||||
String path = downloadFile.getFileUrl().substring(downloadFile.getFileUrl().indexOf("/") + 1);
|
||||
DownloadByteArray downloadByteArray = new DownloadByteArray();
|
||||
byte[] bytes = fastFileStorageClient.downloadFile(group, path, downloadByteArray);
|
||||
|
||||
// // 这里只是为了整合fastdfs,所以写死了文件格式。需要在上传的时候保存文件名。下载的时候使用对应的格式
|
||||
// response.setHeader("Content-disposition", "attachment;filename=" + URLEncoder.encode("sb.xlsx", "UTF-8"));
|
||||
// response.setCharacterEncoding("UTF-8");
|
||||
ServletOutputStream outputStream = null;
|
||||
try {
|
||||
outputStream = httpServletResponse.getOutputStream();
|
||||
outputStream.write(bytes);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
try {
|
||||
outputStream.flush();
|
||||
outputStream.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,48 @@
|
||||
package com.qiwenshare.common.operation.download.product;
|
||||
|
||||
import com.qiwenshare.common.domain.DownloadFile;
|
||||
import com.qiwenshare.common.operation.FileOperation;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.*;
|
||||
|
||||
@Component
|
||||
public class LocalStorageDownloader extends Downloader {
|
||||
@Override
|
||||
public void download(HttpServletResponse httpServletResponse, DownloadFile downloadFile) {
|
||||
BufferedInputStream bis = null;
|
||||
byte[] buffer = new byte[1024];
|
||||
//设置文件路径
|
||||
File file = FileOperation.newFile(PathUtil.getStaticPath() + downloadFile.getFileUrl());
|
||||
if (file.exists()) {
|
||||
|
||||
|
||||
FileInputStream fis = null;
|
||||
|
||||
try {
|
||||
fis = new FileInputStream(file);
|
||||
bis = new BufferedInputStream(fis);
|
||||
OutputStream os = httpServletResponse.getOutputStream();
|
||||
int i = bis.read(buffer);
|
||||
while (i != -1) {
|
||||
os.write(buffer, 0, i);
|
||||
i = bis.read(buffer);
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (bis != null) {
|
||||
try {
|
||||
bis.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -1,12 +1,9 @@
|
||||
package com.qiwenshare.common.upload;
|
||||
package com.qiwenshare.common.operation.upload;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.io.FileUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.io.File;
|
||||
@ -26,14 +23,11 @@ public abstract class Uploader {
|
||||
// 文件大小限制,单位KB
|
||||
public final int maxSize = 10000000;
|
||||
|
||||
protected StandardMultipartHttpServletRequest request = null;
|
||||
|
||||
public abstract List<UploadFile> upload(HttpServletRequest request);
|
||||
public abstract List<UploadFile> upload(HttpServletRequest request, UploadFile uploadFile);
|
||||
|
||||
/**
|
||||
* 根据字符串创建本地目录 并按照日期建立子目录返回
|
||||
*
|
||||
* @param path
|
||||
* @return
|
||||
*/
|
||||
protected String getSaveFilePath() {
|
||||
@ -75,7 +69,6 @@ public abstract class Uploader {
|
||||
}
|
||||
|
||||
public synchronized boolean checkUploadStatus(UploadFile param, File confFile) throws IOException {
|
||||
//File confFile = new File(savePath, timeStampName + ".conf");
|
||||
RandomAccessFile confAccessFile = new RandomAccessFile(confFile, "rw");
|
||||
//设置文件长度
|
||||
confAccessFile.setLength(param.getTotalChunks());
|
@ -1,41 +1,36 @@
|
||||
package com.qiwenshare.common.upload.product;
|
||||
package com.qiwenshare.common.operation.upload.product;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.*;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
import com.qiwenshare.common.exception.UploadGeneralException;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import lombok.Data;
|
||||
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
|
||||
import org.apache.commons.fileupload.servlet.ServletFileUpload;
|
||||
import org.apache.commons.io.FileUtils;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.RandomAccessFile;
|
||||
import java.util.*;
|
||||
import java.util.concurrent.ExecutorService;
|
||||
import java.util.concurrent.Executors;
|
||||
|
||||
@Component
|
||||
public class AliyunOSSUploader extends Uploader {
|
||||
private static final Logger logger = LoggerFactory.getLogger(AliyunOSSUploader.class);
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
|
||||
private UploadFile uploadFile;
|
||||
private String endpoint;
|
||||
private String accessKeyId;
|
||||
private String accessKeySecret;
|
||||
private String bucketName;
|
||||
|
||||
// partETags是PartETag的集合。PartETag由分片的ETag和分片号组成。
|
||||
public static Map<String, List<PartETag>> partETagsMap = new HashMap<String, List<PartETag>>();
|
||||
@ -45,73 +40,49 @@ public class AliyunOSSUploader extends Uploader {
|
||||
|
||||
public static Map<String, String> timeStampNameMap = new HashMap<>();
|
||||
|
||||
public AliyunOSSUploader() {
|
||||
|
||||
}
|
||||
|
||||
public AliyunOSSUploader(UploadFile uploadFile) {
|
||||
this.uploadFile = uploadFile;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<UploadFile> upload(HttpServletRequest httpServletRequest) {
|
||||
public List<UploadFile> upload(HttpServletRequest httpServletRequest, UploadFile uploadFile) {
|
||||
logger.info("开始上传upload");
|
||||
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<>();
|
||||
this.request = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
AliyunOSS aliyunOSS = (AliyunOSS) request.getAttribute("oss");
|
||||
StandardMultipartHttpServletRequest request = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
|
||||
endpoint = aliyunOSS.getEndpoint();
|
||||
accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
bucketName = aliyunOSS.getBucketName();
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(this.request);
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(request);
|
||||
if (!isMultipart) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(0);
|
||||
uploadFile.setMessage("未包含文件上传域");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
return saveUploadFileList;
|
||||
throw new UploadGeneralException("未包含文件上传域");
|
||||
}
|
||||
DiskFileItemFactory dff = new DiskFileItemFactory();//1、创建工厂
|
||||
String savePath = getSaveFilePath();
|
||||
dff.setRepository(new File(savePath));
|
||||
|
||||
try {
|
||||
ServletFileUpload sfu = new ServletFileUpload(dff);//2、创建文件上传解析器
|
||||
sfu.setSizeMax(this.maxSize * 1024L);
|
||||
sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
Iterator<String> iter = this.request.getFileNames();
|
||||
while (iter.hasNext()) {
|
||||
ServletFileUpload sfu = new ServletFileUpload(dff);
|
||||
sfu.setSizeMax(this.maxSize * 1024L);
|
||||
sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
Iterator<String> iter = request.getFileNames();
|
||||
while (iter.hasNext()) {
|
||||
|
||||
saveUploadFileList = doUpload(savePath, iter);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(1);
|
||||
uploadFile.setMessage("未知错误");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
e.printStackTrace();
|
||||
saveUploadFileList = doUpload(request, savePath, iter, uploadFile);
|
||||
}
|
||||
|
||||
|
||||
logger.info("结束上传");
|
||||
return saveUploadFileList;
|
||||
}
|
||||
|
||||
private List<UploadFile> doUpload(String savePath, Iterator<String> iter) throws IOException {
|
||||
OSS ossClient = getClient();
|
||||
private List<UploadFile> doUpload(StandardMultipartHttpServletRequest standardMultipartHttpServletRequest, String savePath, Iterator<String> iter, UploadFile uploadFile) {
|
||||
OSS ossClient = getClient(uploadFile);
|
||||
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<>();
|
||||
|
||||
try {
|
||||
MultipartFile multipartfile = this.request.getFile(iter.next());
|
||||
MultipartFile multipartfile = standardMultipartHttpServletRequest.getFile(iter.next());
|
||||
|
||||
String timeStampName = getTimeStampName();
|
||||
String originalName = multipartfile.getOriginalFilename();
|
||||
|
||||
String fileName = getFileName(originalName);
|
||||
|
||||
String fileType = FileUtil.getFileType(originalName);
|
||||
String fileType = FileUtil.getFileExtendName(originalName);
|
||||
uploadFile.setFileName(fileName);
|
||||
uploadFile.setFileType(fileType);
|
||||
uploadFile.setTimeStampName(timeStampName);
|
||||
@ -122,12 +93,12 @@ public class AliyunOSSUploader extends Uploader {
|
||||
|
||||
synchronized (AliyunOSSUploader.class) {
|
||||
if (uploadPartRequestMap.get(uploadFile.getIdentifier()) == null) {
|
||||
InitiateMultipartUploadRequest request = new InitiateMultipartUploadRequest(bucketName, ossFilePath.substring(1));
|
||||
InitiateMultipartUploadRequest request = new InitiateMultipartUploadRequest(qiwenFileConfig.getAliyun().getOss().getBucketName(), ossFilePath.substring(1));
|
||||
InitiateMultipartUploadResult upresult = ossClient.initiateMultipartUpload(request);
|
||||
String uploadId = upresult.getUploadId();
|
||||
|
||||
UploadFileInfo uploadPartRequest = new UploadFileInfo();
|
||||
uploadPartRequest.setBucketName(bucketName);
|
||||
uploadPartRequest.setBucketName(qiwenFileConfig.getAliyun().getOss().getBucketName());
|
||||
uploadPartRequest.setKey(ossFilePath.substring(1));
|
||||
uploadPartRequest.setUploadId(uploadId);
|
||||
uploadPartRequestMap.put(uploadFile.getIdentifier(), uploadPartRequest);
|
||||
@ -166,7 +137,7 @@ public class AliyunOSSUploader extends Uploader {
|
||||
boolean isComplete = checkUploadStatus(uploadFile, confFile);
|
||||
if (isComplete) {
|
||||
logger.info("分片上传完成");
|
||||
completeMultipartUpload();
|
||||
completeMultipartUpload(uploadFile);
|
||||
|
||||
uploadFile.setUrl(ossFilePath);
|
||||
uploadFile.setSuccess(1);
|
||||
@ -178,9 +149,11 @@ public class AliyunOSSUploader extends Uploader {
|
||||
|
||||
} catch (Exception e) {
|
||||
logger.error("上传出错:" + e);
|
||||
throw new UploadGeneralException(e);
|
||||
}
|
||||
|
||||
uploadFile.setIsOSS(1);
|
||||
uploadFile.setStorageType(1);
|
||||
|
||||
uploadFile.setFileSize(uploadFile.getTotalSize());
|
||||
saveUploadFileList.add(uploadFile);
|
||||
@ -190,37 +163,37 @@ public class AliyunOSSUploader extends Uploader {
|
||||
/**
|
||||
* 将文件分块进行升序排序并执行文件上传。
|
||||
*/
|
||||
protected void completeMultipartUpload() {
|
||||
protected void completeMultipartUpload(UploadFile uploadFile) {
|
||||
|
||||
List<PartETag> partETags = partETagsMap.get(uploadFile.getIdentifier());
|
||||
Collections.sort(partETags, Comparator.comparingInt(PartETag::getPartNumber));
|
||||
UploadFileInfo uploadFileInfo = uploadPartRequestMap.get(uploadFile.getIdentifier());
|
||||
CompleteMultipartUploadRequest completeMultipartUploadRequest =
|
||||
new CompleteMultipartUploadRequest(bucketName,
|
||||
new CompleteMultipartUploadRequest(qiwenFileConfig.getAliyun().getOss().getBucketName(),
|
||||
uploadFileInfo.getKey(),
|
||||
uploadFileInfo.getUploadId(),
|
||||
partETags);
|
||||
logger.info("----:" + JSON.toJSONString(partETags));
|
||||
// 完成上传。
|
||||
CompleteMultipartUploadResult completeMultipartUploadResult = getClient().completeMultipartUpload(completeMultipartUploadRequest);
|
||||
CompleteMultipartUploadResult completeMultipartUploadResult = getClient(uploadFile).completeMultipartUpload(completeMultipartUploadRequest);
|
||||
logger.info("----:" + JSON.toJSONString(completeMultipartUploadRequest));
|
||||
getClient().shutdown();
|
||||
getClient(uploadFile).shutdown();
|
||||
partETagsMap.remove(uploadFile.getIdentifier());
|
||||
uploadPartRequestMap.remove(uploadFile.getIdentifier());
|
||||
ossMap.remove(uploadFile.getIdentifier());
|
||||
//
|
||||
}
|
||||
|
||||
private void listFile() {
|
||||
private void listFile(UploadFile uploadFile) {
|
||||
// 列举已上传的分片,其中uploadId来自于InitiateMultipartUpload返回的结果。
|
||||
ListPartsRequest listPartsRequest = new ListPartsRequest(bucketName, uploadPartRequestMap.get(uploadFile.getIdentifier()).getKey(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getUploadId());
|
||||
ListPartsRequest listPartsRequest = new ListPartsRequest(qiwenFileConfig.getAliyun().getOss().getBucketName(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getKey(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getUploadId());
|
||||
// 设置uploadId。
|
||||
//listPartsRequest.setUploadId(uploadId);
|
||||
// 设置分页时每一页中分片数量为100个。默认列举1000个分片。
|
||||
listPartsRequest.setMaxParts(100);
|
||||
// 指定List的起始位置。只有分片号大于此参数值的分片会被列举。
|
||||
// listPartsRequest.setPartNumberMarker(1);
|
||||
PartListing partListing = getClient().listParts(listPartsRequest);
|
||||
PartListing partListing = getClient(uploadFile).listParts(listPartsRequest);
|
||||
|
||||
for (PartSummary part : partListing.getParts()) {
|
||||
logger.info("分片号:"+part.getPartNumber() + ", 分片数据大小: "+
|
||||
@ -241,13 +214,14 @@ public class AliyunOSSUploader extends Uploader {
|
||||
/**
|
||||
* 取消上传
|
||||
*/
|
||||
private void cancelUpload() {
|
||||
private void cancelUpload(UploadFile uploadFile) {
|
||||
AbortMultipartUploadRequest abortMultipartUploadRequest =
|
||||
new AbortMultipartUploadRequest(bucketName, uploadPartRequestMap.get(uploadFile.getIdentifier()).getKey(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getUploadId());
|
||||
getClient().abortMultipartUpload(abortMultipartUploadRequest);
|
||||
new AbortMultipartUploadRequest(qiwenFileConfig.getAliyun().getOss().getBucketName(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getKey(), uploadPartRequestMap.get(uploadFile.getIdentifier()).getUploadId());
|
||||
getClient(uploadFile).abortMultipartUpload(abortMultipartUploadRequest);
|
||||
}
|
||||
|
||||
protected synchronized String getTimeStampName(){
|
||||
|
||||
protected synchronized String getTimeStampName(UploadFile uploadFile){
|
||||
String timeStampName;
|
||||
|
||||
if (StringUtils.isEmpty(timeStampNameMap.get(uploadFile.getIdentifier()))) {
|
||||
@ -259,10 +233,10 @@ public class AliyunOSSUploader extends Uploader {
|
||||
return timeStampName;
|
||||
}
|
||||
|
||||
private synchronized OSS getClient() {
|
||||
private synchronized OSS getClient(UploadFile uploadFile) {
|
||||
OSS ossClient = null;
|
||||
if (ossMap.get(uploadFile.getIdentifier()) == null) {
|
||||
ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
ossClient = new OSSClientBuilder().build(qiwenFileConfig.getAliyun().getOss().getEndpoint(), qiwenFileConfig.getAliyun().getOss().getAccessKeyId(), qiwenFileConfig.getAliyun().getOss().getAccessKeySecret());
|
||||
ossMap.put(uploadFile.getIdentifier(), ossClient);
|
||||
} else {
|
||||
ossClient = ossMap.get(uploadFile.getIdentifier());
|
@ -0,0 +1,197 @@
|
||||
package com.qiwenshare.common.operation.upload.product;
|
||||
|
||||
import com.github.tobato.fastdfs.domain.StorePath;
|
||||
import com.github.tobato.fastdfs.service.AppendFileStorageClient;
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.exception.UploadGeneralException;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
|
||||
import org.apache.commons.fileupload.servlet.ServletFileUpload;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.io.File;
|
||||
import java.util.*;
|
||||
@Component
|
||||
@Slf4j
|
||||
public class FastDFSUploader extends Uploader {
|
||||
public static Object lock = new Object();
|
||||
@Resource
|
||||
AppendFileStorageClient defaultAppendFileStorageClient;
|
||||
|
||||
private static Map<String, Integer> CURRENT_UPLOAD_CHUNK_NUMBER = new HashMap<>();
|
||||
private static Map<String, Long> UPLOADED_SIZE = new HashMap<>();
|
||||
private static Map<String, String> STORE_PATH = new HashMap<>();
|
||||
private static Map<String, Object> LOCK_MAP = new HashMap<>();
|
||||
|
||||
@Override
|
||||
public List<UploadFile> upload(HttpServletRequest request, UploadFile uploadFile) {
|
||||
log.info("开始上传upload");
|
||||
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<>();
|
||||
StandardMultipartHttpServletRequest standardMultipartHttpServletRequest = (StandardMultipartHttpServletRequest) request;
|
||||
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(standardMultipartHttpServletRequest);
|
||||
if (!isMultipart) {
|
||||
throw new UploadGeneralException("未包含文件上传域");
|
||||
}
|
||||
DiskFileItemFactory dff = new DiskFileItemFactory();//1、创建工厂
|
||||
String savePath = getSaveFilePath();
|
||||
dff.setRepository(new File(savePath));
|
||||
|
||||
try {
|
||||
ServletFileUpload sfu = new ServletFileUpload(dff);//2、创建文件上传解析器
|
||||
sfu.setSizeMax(this.maxSize * 1024L);
|
||||
sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
Iterator<String> iter = standardMultipartHttpServletRequest.getFileNames();
|
||||
while (iter.hasNext()) {
|
||||
saveUploadFileList = doUpload(standardMultipartHttpServletRequest, savePath, iter, uploadFile);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
throw new UploadGeneralException(e);
|
||||
}
|
||||
|
||||
log.info("结束上传");
|
||||
return saveUploadFileList;
|
||||
}
|
||||
|
||||
|
||||
private List<UploadFile> doUpload(StandardMultipartHttpServletRequest standardMultipartHttpServletRequest, String savePath, Iterator<String> iter, UploadFile uploadFile) {
|
||||
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<>();
|
||||
|
||||
try {
|
||||
MultipartFile multipartfile = standardMultipartHttpServletRequest.getFile(iter.next());
|
||||
synchronized (lock) {
|
||||
if (LOCK_MAP.get(uploadFile.getIdentifier()) == null) {
|
||||
LOCK_MAP.put(uploadFile.getIdentifier(), new Object());
|
||||
}
|
||||
}
|
||||
uploadFileChunk(multipartfile, uploadFile);
|
||||
|
||||
String timeStampName = getTimeStampName();
|
||||
String originalName = multipartfile.getOriginalFilename();
|
||||
|
||||
String fileName = getFileName(originalName);
|
||||
|
||||
String fileType = FileUtil.getFileExtendName(originalName);
|
||||
uploadFile.setFileName(fileName);
|
||||
uploadFile.setFileType(fileType);
|
||||
uploadFile.setTimeStampName(timeStampName);
|
||||
|
||||
|
||||
String confFilePath = savePath + FILE_SEPARATOR + uploadFile.getIdentifier() + "." + "conf";
|
||||
File confFile = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + confFilePath);
|
||||
|
||||
|
||||
boolean isComplete = checkUploadStatus(uploadFile, confFile);
|
||||
if (isComplete) {
|
||||
log.info("分片上传完成");
|
||||
LOCK_MAP.remove(uploadFile.getIdentifier());
|
||||
uploadFile.setUrl(STORE_PATH.get(uploadFile.getIdentifier()));
|
||||
uploadFile.setSuccess(1);
|
||||
uploadFile.setMessage("上传成功");
|
||||
} else {
|
||||
uploadFile.setSuccess(0);
|
||||
uploadFile.setMessage("未完成");
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
throw new UploadGeneralException(e);
|
||||
}
|
||||
|
||||
uploadFile.setIsOSS(0);
|
||||
uploadFile.setStorageType(2);
|
||||
uploadFile.setFileSize(uploadFile.getTotalSize());
|
||||
saveUploadFileList.add(uploadFile);
|
||||
return saveUploadFileList;
|
||||
}
|
||||
|
||||
public void uploadFileChunk(MultipartFile multipartFile, UploadFile uploadFile) {
|
||||
|
||||
synchronized (LOCK_MAP.get(uploadFile.getIdentifier())) {
|
||||
// 存储在fastdfs不带组的路径
|
||||
|
||||
log.info("当前文件的Md5:{}", uploadFile.getIdentifier());
|
||||
|
||||
log.info("当前块的大小:{}", uploadFile.getCurrentChunkSize());
|
||||
if (CURRENT_UPLOAD_CHUNK_NUMBER.get(uploadFile.getIdentifier()) == null) {
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), 1);
|
||||
}
|
||||
|
||||
while (uploadFile.getChunkNumber() != CURRENT_UPLOAD_CHUNK_NUMBER.get(uploadFile.getIdentifier())) {
|
||||
try {
|
||||
LOCK_MAP.get(uploadFile.getIdentifier()).wait();
|
||||
} catch (InterruptedException e) {
|
||||
log.error("--------InterruptedException-------");
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
log.info("***********开始上传第{}块**********", uploadFile.getChunkNumber());
|
||||
StorePath storePath = null;
|
||||
|
||||
try {
|
||||
|
||||
if (uploadFile.getChunkNumber() <= 1) {
|
||||
log.info("上传第一块");
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber() + 1);
|
||||
try {
|
||||
storePath = defaultAppendFileStorageClient.uploadAppenderFile("group1", multipartFile.getInputStream(),
|
||||
multipartFile.getSize(), FileUtil.getFileExtendName(multipartFile.getOriginalFilename()));
|
||||
// 记录第一个分片上传的大小
|
||||
UPLOADED_SIZE.put(uploadFile.getIdentifier(), uploadFile.getCurrentChunkSize());
|
||||
log.info("第一块上传完成");
|
||||
if (storePath == null) {
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber());
|
||||
log.info("获取远程文件路径出错");
|
||||
throw new UploadGeneralException("获取远程文件路径出错");
|
||||
}
|
||||
} catch (Exception e) {
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber());
|
||||
log.error("初次上传远程文件出错", e);
|
||||
throw new UploadGeneralException("初次上传远程文件出错", e);
|
||||
}
|
||||
|
||||
STORE_PATH.put(uploadFile.getIdentifier(), storePath.getPath());
|
||||
log.info("上传文件 result = {}", storePath.getPath());
|
||||
} else {
|
||||
log.info("上传第{}块:" + uploadFile.getChunkNumber());
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber() + 1);
|
||||
String path = STORE_PATH.get(uploadFile.getIdentifier());
|
||||
if (path == null) {
|
||||
log.error("无法获取已上传服务器文件地址");
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber());
|
||||
throw new UploadGeneralException("无法获取已上传服务器文件地址");
|
||||
}
|
||||
try {
|
||||
Long alreadySize = UPLOADED_SIZE.get(uploadFile.getIdentifier());
|
||||
// 追加方式实际实用如果中途出错多次,可能会出现重复追加情况,这里改成修改模式,即时多次传来重复文件块,依然可以保证文件拼接正确
|
||||
defaultAppendFileStorageClient.modifyFile("group1", path, multipartFile.getInputStream(),
|
||||
multipartFile.getSize(), alreadySize);
|
||||
// 记录分片上传的大小
|
||||
UPLOADED_SIZE.put(uploadFile.getIdentifier(), alreadySize + multipartFile.getSize());
|
||||
log.info("第{}块更新完成", uploadFile.getChunkNumber());
|
||||
} catch (Exception e) {
|
||||
CURRENT_UPLOAD_CHUNK_NUMBER.put(uploadFile.getIdentifier(), uploadFile.getChunkNumber());
|
||||
log.error("更新远程文件出错", e);
|
||||
throw new UploadGeneralException("更新远程文件出错", e);
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
log.error("上传文件错误", e);
|
||||
throw new UploadGeneralException("上传文件错误", e);
|
||||
}
|
||||
|
||||
log.info("***********第{}块上传成功**********", uploadFile.getChunkNumber());
|
||||
|
||||
LOCK_MAP.get(uploadFile.getIdentifier()).notifyAll();
|
||||
}
|
||||
}
|
||||
}
|
@ -1,18 +1,19 @@
|
||||
package com.qiwenshare.common.upload.product;
|
||||
package com.qiwenshare.common.operation.upload.product;
|
||||
|
||||
import com.qiwenshare.common.cbb.NotSameFileExpection;
|
||||
import com.qiwenshare.common.exception.NotSameFileExpection;
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.exception.UploadGeneralException;
|
||||
import com.qiwenshare.common.operation.ImageOperation;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import org.apache.commons.codec.digest.DigestUtils;
|
||||
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
|
||||
import org.apache.commons.fileupload.servlet.ServletFileUpload;
|
||||
import org.apache.commons.io.FileUtils;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
|
||||
@ -24,30 +25,26 @@ import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.UUID;
|
||||
@Component
|
||||
public class LocalStorageUploader extends Uploader {
|
||||
private static final Logger logger = LoggerFactory.getLogger(LocalStorageUploader.class);
|
||||
// private UploadFile uploadFile;
|
||||
|
||||
public class ChunkUploader extends Uploader {
|
||||
private static final Logger logger = LoggerFactory.getLogger(ChunkUploader.class);
|
||||
private UploadFile uploadFile;
|
||||
|
||||
public ChunkUploader() {
|
||||
public LocalStorageUploader() {
|
||||
|
||||
}
|
||||
|
||||
public ChunkUploader(UploadFile uploadFile) {
|
||||
this.uploadFile = uploadFile;
|
||||
}
|
||||
//
|
||||
// public ChunkUploader(UploadFile uploadFile) {
|
||||
// this.uploadFile = uploadFile;
|
||||
// }
|
||||
|
||||
@Override
|
||||
public List<UploadFile> upload(HttpServletRequest httpServletRequest) {
|
||||
public List<UploadFile> upload(HttpServletRequest httpServletRequest,UploadFile uploadFile) {
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
this.request = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(this.request);
|
||||
StandardMultipartHttpServletRequest standardMultipartHttpServletRequest = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(standardMultipartHttpServletRequest);
|
||||
if (!isMultipart) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(0);
|
||||
uploadFile.setMessage("未包含文件上传域");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
return saveUploadFileList;
|
||||
throw new UploadGeneralException("未包含文件上传域");
|
||||
}
|
||||
DiskFileItemFactory dff = new DiskFileItemFactory();//1、创建工厂
|
||||
String savePath = getSaveFilePath();
|
||||
@ -57,43 +54,28 @@ public class ChunkUploader extends Uploader {
|
||||
ServletFileUpload sfu = new ServletFileUpload(dff);//2、创建文件上传解析器
|
||||
sfu.setSizeMax(this.maxSize * 1024L);
|
||||
sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
Iterator<String> iter = this.request.getFileNames();
|
||||
Iterator<String> iter = standardMultipartHttpServletRequest.getFileNames();
|
||||
while (iter.hasNext()) {
|
||||
saveUploadFileList = doUpload(savePath, iter);
|
||||
saveUploadFileList = doUpload(standardMultipartHttpServletRequest, savePath, iter, uploadFile);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(1);
|
||||
uploadFile.setMessage("未知错误");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
e.printStackTrace();
|
||||
throw new UploadGeneralException("未包含文件上传域");
|
||||
} catch (NotSameFileExpection notSameFileExpection) {
|
||||
notSameFileExpection.printStackTrace();
|
||||
}
|
||||
|
||||
|
||||
return saveUploadFileList;
|
||||
|
||||
|
||||
}
|
||||
|
||||
private List<UploadFile> doUpload(String savePath, Iterator<String> iter) throws IOException, NotSameFileExpection {
|
||||
private List<UploadFile> doUpload(StandardMultipartHttpServletRequest standardMultipartHttpServletRequest, String savePath, Iterator<String> iter, UploadFile uploadFile) throws IOException, NotSameFileExpection {
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
//UploadFile uploadFile = new UploadFile();
|
||||
MultipartFile multipartfile = this.request.getFile(iter.next());
|
||||
MultipartFile multipartfile = standardMultipartHttpServletRequest.getFile(iter.next());
|
||||
|
||||
//InputStream inputStream = multipartfile.getInputStream();
|
||||
String timeStampName = uploadFile.getIdentifier();
|
||||
// .getTimeStampName();
|
||||
// if (StringUtils.isEmpty(uploadFile.getTimeStampName())) {
|
||||
// timeStampName = getTimeStampName();
|
||||
// }
|
||||
|
||||
|
||||
String originalName = multipartfile.getOriginalFilename();
|
||||
|
||||
String fileName = getFileName(originalName);
|
||||
String fileType = FileUtil.getFileType(originalName);
|
||||
String fileType = FileUtil.getFileExtendName(originalName);
|
||||
uploadFile.setFileName(fileName);
|
||||
uploadFile.setFileType(fileType);
|
||||
uploadFile.setTimeStampName(timeStampName);
|
||||
@ -107,6 +89,7 @@ public class ChunkUploader extends Uploader {
|
||||
File minFile = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + minFilePath);
|
||||
File confFile = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + confFilePath);
|
||||
uploadFile.setIsOSS(0);
|
||||
uploadFile.setStorageType(0);
|
||||
uploadFile.setUrl(saveFilePath);
|
||||
|
||||
if (StringUtils.isEmpty(uploadFile.getTaskId())) {// == null || "".equals(uploadFile.getTaskId())) {
|
@ -0,0 +1,136 @@
|
||||
//package com.qiwenshare.common.upload.product;
|
||||
//
|
||||
//import com.qiwenshare.common.domain.UploadFile;
|
||||
//import com.qiwenshare.common.operation.ImageOperation;
|
||||
//import com.qiwenshare.common.upload.Uploader;
|
||||
//import com.qiwenshare.common.util.FileUtil;
|
||||
//import com.qiwenshare.common.util.PathUtil;
|
||||
//import org.apache.commons.fileupload.disk.DiskFileItemFactory;
|
||||
//import org.apache.commons.fileupload.servlet.ServletFileUpload;
|
||||
//import org.apache.commons.fileupload.util.Streams;
|
||||
//import org.apache.commons.lang3.StringUtils;
|
||||
//import org.slf4j.Logger;
|
||||
//import org.slf4j.LoggerFactory;
|
||||
//import org.springframework.web.multipart.MultipartFile;
|
||||
//import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
//
|
||||
//import javax.servlet.http.HttpServletRequest;
|
||||
//import java.io.*;
|
||||
//import java.util.ArrayList;
|
||||
//import java.util.Iterator;
|
||||
//import java.util.List;
|
||||
//
|
||||
//public class NormalUploader extends Uploader {
|
||||
// private static final Logger logger = LoggerFactory.getLogger(NormalUploader.class);
|
||||
//
|
||||
// @Override
|
||||
// public List<UploadFile> upload(HttpServletRequest httpServletRequest) {
|
||||
// List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
// this.request = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
// boolean isMultipart = ServletFileUpload.isMultipartContent(this.request);
|
||||
// if (!isMultipart) {
|
||||
// UploadFile uploadFile = new UploadFile();
|
||||
// uploadFile.setSuccess(0);
|
||||
// uploadFile.setMessage("未包含文件上传域");
|
||||
// saveUploadFileList.add(uploadFile);
|
||||
// return saveUploadFileList;
|
||||
// }
|
||||
// DiskFileItemFactory dff = new DiskFileItemFactory();//1、创建工厂
|
||||
// String savePath = getSaveFilePath();
|
||||
// dff.setRepository(new File(savePath));
|
||||
//
|
||||
// try {
|
||||
// ServletFileUpload sfu = new ServletFileUpload(dff);//2、创建文件上传解析器
|
||||
// sfu.setSizeMax(this.maxSize * 1024L);
|
||||
// sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
// Iterator<String> iter = this.request.getFileNames();
|
||||
// while (iter.hasNext()) {
|
||||
// saveUploadFileList = doUpload(savePath, iter);
|
||||
// }
|
||||
// } catch (IOException e) {
|
||||
// UploadFile uploadFile = new UploadFile();
|
||||
// uploadFile.setSuccess(1);
|
||||
// uploadFile.setMessage("未知错误");
|
||||
// saveUploadFileList.add(uploadFile);
|
||||
// e.printStackTrace();
|
||||
// }
|
||||
//
|
||||
// return saveUploadFileList;
|
||||
// }
|
||||
//
|
||||
// private List<UploadFile> doUpload(String savePath, Iterator<String> iter) throws IOException {
|
||||
// List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
// UploadFile uploadFile = new UploadFile();
|
||||
// MultipartFile multipartfile = this.request.getFile(iter.next());
|
||||
//
|
||||
// InputStream inputStream = multipartfile.getInputStream();
|
||||
// String timeStampName = getTimeStampName();
|
||||
//
|
||||
//
|
||||
// String originalName = multipartfile.getOriginalFilename();
|
||||
//
|
||||
// String fileName = getFileName(originalName);
|
||||
//
|
||||
// String fileType = FileUtil.getFileExtendName(originalName);
|
||||
// uploadFile.setFileName(fileName);
|
||||
// uploadFile.setFileType(fileType);
|
||||
// uploadFile.setTimeStampName(timeStampName);
|
||||
//
|
||||
// String saveFilePath = savePath + FILE_SEPARATOR + timeStampName;
|
||||
// String minFilePath = savePath + FILE_SEPARATOR + timeStampName;
|
||||
// if (StringUtils.isNotEmpty(fileType)) {
|
||||
// saveFilePath += "." + fileType;
|
||||
// minFilePath += "_min" + "." + fileType;
|
||||
// }
|
||||
//
|
||||
// File file = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + saveFilePath);
|
||||
// File minFile = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + minFilePath);
|
||||
//
|
||||
// uploadFile.setIsOSS(0);
|
||||
// uploadFile.setStorageType(0);
|
||||
// uploadFile.setUrl(saveFilePath);
|
||||
// BufferedInputStream in = null;
|
||||
// FileOutputStream out = null;
|
||||
// BufferedOutputStream output = null;
|
||||
//
|
||||
// try {
|
||||
// in = new BufferedInputStream(inputStream);
|
||||
// out = new FileOutputStream(file);
|
||||
// output = new BufferedOutputStream(out);
|
||||
// Streams.copy(in, output, true);
|
||||
// if (FileUtil.isImageFile(uploadFile.getFileType())){
|
||||
// ImageOperation.thumbnailsImage(file, minFile, 300);
|
||||
// }
|
||||
//
|
||||
// } catch (FileNotFoundException e) {
|
||||
// logger.error("文件没有发现" + e);
|
||||
// } catch (IOException e) {
|
||||
// logger.error("文件读取失败" + e);
|
||||
// } finally {
|
||||
//
|
||||
// closeStream(in, out, output);
|
||||
// }
|
||||
//
|
||||
//
|
||||
//
|
||||
// uploadFile.setSuccess(1);
|
||||
// uploadFile.setMessage("上传成功");
|
||||
// uploadFile.setFileSize(request.getContentLengthLong());
|
||||
// saveUploadFileList.add(uploadFile);
|
||||
// return saveUploadFileList;
|
||||
// }
|
||||
//
|
||||
//
|
||||
// private void closeStream(BufferedInputStream in, FileOutputStream out,
|
||||
// BufferedOutputStream output) throws IOException {
|
||||
// if (in != null) {
|
||||
// in.close();
|
||||
// }
|
||||
// if (out != null) {
|
||||
// out.close();
|
||||
// }
|
||||
// if (output != null) {
|
||||
// output.close();
|
||||
// }
|
||||
// }
|
||||
//}
|
@ -1,55 +0,0 @@
|
||||
/**
|
||||
* 示例说明
|
||||
*
|
||||
* HelloOSS是OSS Java SDK的示例程序,您可以修改endpoint、accessKeyId、accessKeySecret、bucketName后直接运行。
|
||||
* 运行方法请参考README。
|
||||
*
|
||||
* 本示例中的并不包括OSS Java SDK的所有功能,详细功能及使用方法,请参看“SDK手册 > Java-SDK”,
|
||||
* 链接地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/preface.html?spm=5176.docoss/sdk/java-sdk/。
|
||||
*
|
||||
* 调用OSS Java SDK的方法时,抛出异常表示有错误发生;没有抛出异常表示成功执行。
|
||||
* 当错误发生时,OSS Java SDK的方法会抛出异常,异常中包括错误码、错误信息,详细请参看“SDK手册 > Java-SDK > 异常处理”,
|
||||
* 链接地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/exception.html?spm=5176.docoss/api-reference/error-response。
|
||||
*
|
||||
* OSS控制台可以直观的看到您调用OSS Java SDK的结果,OSS控制台地址是:https://oss.console.aliyun.com/index#/。
|
||||
* OSS控制台使用方法请参看文档中心的“控制台用户指南”, 指南的来链接地址是:https://help.aliyun.com/document_detail/oss/getting-started/get-started.html?spm=5176.docoss/user_guide。
|
||||
*
|
||||
* OSS的文档中心地址是:https://help.aliyun.com/document_detail/oss/user_guide/overview.html。
|
||||
* OSS Java SDK的文档地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/install.html?spm=5176.docoss/sdk/java-sdk。
|
||||
*
|
||||
*/
|
||||
|
||||
package com.qiwenshare.common.oss;
|
||||
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.ObjectMetadata;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
|
||||
import java.io.InputStream;
|
||||
|
||||
|
||||
public class AliyunOSSDelete {
|
||||
|
||||
|
||||
/**
|
||||
* 流式上传
|
||||
*/
|
||||
public static void deleteObject(AliyunOSS aliyunOSS, String objectName) {
|
||||
String endpoint = aliyunOSS.getEndpoint();
|
||||
String accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
String accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
String bucketName = aliyunOSS.getBucketName();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
|
||||
ossClient.deleteObject(bucketName, objectName);
|
||||
|
||||
|
||||
|
||||
// 关闭OSSClient。
|
||||
ossClient.shutdown();
|
||||
}
|
||||
|
||||
|
||||
}
|
@ -1,38 +0,0 @@
|
||||
package com.qiwenshare.common.oss;
|
||||
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.OSSObject;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
|
||||
import java.io.InputStream;
|
||||
|
||||
public class AliyunOSSDownload {
|
||||
private String endpoint = "";
|
||||
private String accessKeyId = "";
|
||||
private String accessKeySecret = "";
|
||||
private String bucketName = "";
|
||||
public OSS createOSSClient(AliyunOSS aliyunOSS) {
|
||||
String endpoint = aliyunOSS.getEndpoint();
|
||||
String accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
String accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
this.bucketName = aliyunOSS.getBucketName();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
return ossClient;
|
||||
}
|
||||
|
||||
/**
|
||||
* 流式下载
|
||||
*/
|
||||
public InputStream streamDownload(String objectName) {
|
||||
|
||||
// 创建OSSClient实例。
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
|
||||
// ossObject包含文件所在的存储空间名称、文件名称、文件元信息以及一个输入流。
|
||||
OSSObject ossObject = ossClient.getObject(bucketName, objectName);
|
||||
return ossObject.getObjectContent();
|
||||
|
||||
}
|
||||
|
||||
}
|
@ -1,59 +0,0 @@
|
||||
/**
|
||||
* 示例说明
|
||||
*
|
||||
* HelloOSS是OSS Java SDK的示例程序,您可以修改endpoint、accessKeyId、accessKeySecret、bucketName后直接运行。
|
||||
* 运行方法请参考README。
|
||||
*
|
||||
* 本示例中的并不包括OSS Java SDK的所有功能,详细功能及使用方法,请参看“SDK手册 > Java-SDK”,
|
||||
* 链接地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/preface.html?spm=5176.docoss/sdk/java-sdk/。
|
||||
*
|
||||
* 调用OSS Java SDK的方法时,抛出异常表示有错误发生;没有抛出异常表示成功执行。
|
||||
* 当错误发生时,OSS Java SDK的方法会抛出异常,异常中包括错误码、错误信息,详细请参看“SDK手册 > Java-SDK > 异常处理”,
|
||||
* 链接地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/exception.html?spm=5176.docoss/api-reference/error-response。
|
||||
*
|
||||
* OSS控制台可以直观的看到您调用OSS Java SDK的结果,OSS控制台地址是:https://oss.console.aliyun.com/index#/。
|
||||
* OSS控制台使用方法请参看文档中心的“控制台用户指南”, 指南的来链接地址是:https://help.aliyun.com/document_detail/oss/getting-started/get-started.html?spm=5176.docoss/user_guide。
|
||||
*
|
||||
* OSS的文档中心地址是:https://help.aliyun.com/document_detail/oss/user_guide/overview.html。
|
||||
* OSS Java SDK的文档地址是:https://help.aliyun.com/document_detail/oss/sdk/java-sdk/install.html?spm=5176.docoss/sdk/java-sdk。
|
||||
*
|
||||
*/
|
||||
|
||||
package com.qiwenshare.common.oss;
|
||||
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.CopyObjectResult;
|
||||
import com.aliyun.oss.model.ObjectMetadata;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
|
||||
import java.io.InputStream;
|
||||
|
||||
|
||||
public class AliyunOSSRename {
|
||||
|
||||
/**
|
||||
* 流式上传
|
||||
*/
|
||||
public static void rename(AliyunOSS aliyunOSS, String sourceObjectName, String destinationObjectName) {
|
||||
String endpoint = aliyunOSS.getEndpoint();
|
||||
String accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
String accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
String bucketName = aliyunOSS.getBucketName();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
CopyObjectResult result = ossClient.copyObject(bucketName, sourceObjectName, bucketName, destinationObjectName);
|
||||
|
||||
ossClient.deleteObject(bucketName, sourceObjectName);
|
||||
ObjectMetadata metadata = new ObjectMetadata();
|
||||
// if ("pdf".equals(FileUtil.getFileType(objectName))) {
|
||||
// metadata.setContentDisposition("attachment");
|
||||
// }
|
||||
|
||||
// ossClient.putObject(bucketName, objectName, inputStream, metadata);
|
||||
|
||||
|
||||
// 关闭OSSClient。
|
||||
ossClient.shutdown();
|
||||
}
|
||||
|
||||
}
|
@ -1,10 +1,8 @@
|
||||
package com.qiwenshare.common.cbb;
|
||||
package com.qiwenshare.common.result;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
* 统一结果返回
|
||||
* @param <T>
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.common.cbb;
|
||||
package com.qiwenshare.common.result;
|
||||
|
||||
import lombok.Getter;
|
||||
|
||||
@ -12,6 +12,7 @@ public enum ResultCodeEnum {
|
||||
PARAM_ERROR(false,20002,"参数错误"),
|
||||
NULL_POINT(false, 20003, "空指针异常"),
|
||||
INDEX_OUT_OF_BOUNDS(false, 20004, "下标越界异常"),
|
||||
REQUEST_TIMEOUT(false, 20005, "请求超时"),
|
||||
;
|
||||
|
||||
// 响应是否成功
|
@ -1,18 +0,0 @@
|
||||
package com.qiwenshare.common.upload.factory;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.product.AliyunOSSUploader;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
|
||||
|
||||
public class AliyunOSSUploaderFactory implements UploaderFactory {
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return new AliyunOSSUploader();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Uploader getUploader(UploadFile uploadFile) {
|
||||
return new AliyunOSSUploader(uploadFile);
|
||||
}
|
||||
}
|
@ -1,20 +0,0 @@
|
||||
package com.qiwenshare.common.upload.factory;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.product.ChunkUploader;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
|
||||
public class ChunkUploaderFactory implements UploaderFactory {
|
||||
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return new ChunkUploader();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Uploader getUploader(UploadFile uploadFile) {
|
||||
return new ChunkUploader(uploadFile);
|
||||
}
|
||||
|
||||
|
||||
}
|
@ -1,18 +0,0 @@
|
||||
package com.qiwenshare.common.upload.factory;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.product.NormalUploader;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
|
||||
public class NormalUploaderFactory implements UploaderFactory {
|
||||
|
||||
@Override
|
||||
public Uploader getUploader() {
|
||||
return new NormalUploader();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Uploader getUploader(UploadFile uploadFile) {
|
||||
return new NormalUploader();
|
||||
}
|
||||
}
|
@ -1,9 +0,0 @@
|
||||
package com.qiwenshare.common.upload.factory;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
|
||||
public interface UploaderFactory {
|
||||
Uploader getUploader();
|
||||
Uploader getUploader(UploadFile uploadFile);
|
||||
}
|
@ -1,135 +0,0 @@
|
||||
package com.qiwenshare.common.upload.product;
|
||||
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.operation.ImageOperation;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import org.apache.commons.fileupload.disk.DiskFileItemFactory;
|
||||
import org.apache.commons.fileupload.servlet.ServletFileUpload;
|
||||
import org.apache.commons.fileupload.util.Streams;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
import org.springframework.web.multipart.support.StandardMultipartHttpServletRequest;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.io.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
||||
public class NormalUploader extends Uploader {
|
||||
private static final Logger logger = LoggerFactory.getLogger(NormalUploader.class);
|
||||
|
||||
@Override
|
||||
public List<UploadFile> upload(HttpServletRequest httpServletRequest) {
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
this.request = (StandardMultipartHttpServletRequest) httpServletRequest;
|
||||
boolean isMultipart = ServletFileUpload.isMultipartContent(this.request);
|
||||
if (!isMultipart) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(0);
|
||||
uploadFile.setMessage("未包含文件上传域");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
return saveUploadFileList;
|
||||
}
|
||||
DiskFileItemFactory dff = new DiskFileItemFactory();//1、创建工厂
|
||||
String savePath = getSaveFilePath();
|
||||
dff.setRepository(new File(savePath));
|
||||
|
||||
try {
|
||||
ServletFileUpload sfu = new ServletFileUpload(dff);//2、创建文件上传解析器
|
||||
sfu.setSizeMax(this.maxSize * 1024L);
|
||||
sfu.setHeaderEncoding("utf-8");//3、解决文件名的中文乱码
|
||||
Iterator<String> iter = this.request.getFileNames();
|
||||
while (iter.hasNext()) {
|
||||
saveUploadFileList = doUpload(savePath, iter);
|
||||
}
|
||||
} catch (IOException e) {
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setSuccess(1);
|
||||
uploadFile.setMessage("未知错误");
|
||||
saveUploadFileList.add(uploadFile);
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return saveUploadFileList;
|
||||
}
|
||||
|
||||
private List<UploadFile> doUpload(String savePath, Iterator<String> iter) throws IOException {
|
||||
List<UploadFile> saveUploadFileList = new ArrayList<UploadFile>();
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
MultipartFile multipartfile = this.request.getFile(iter.next());
|
||||
|
||||
InputStream inputStream = multipartfile.getInputStream();
|
||||
String timeStampName = getTimeStampName();
|
||||
|
||||
|
||||
String originalName = multipartfile.getOriginalFilename();
|
||||
|
||||
String fileName = getFileName(originalName);
|
||||
|
||||
String fileType = FileUtil.getFileType(originalName);
|
||||
uploadFile.setFileName(fileName);
|
||||
uploadFile.setFileType(fileType);
|
||||
uploadFile.setTimeStampName(timeStampName);
|
||||
|
||||
String saveFilePath = savePath + FILE_SEPARATOR + timeStampName;
|
||||
String minFilePath = savePath + FILE_SEPARATOR + timeStampName;
|
||||
if (StringUtils.isNotEmpty(fileType)) {
|
||||
saveFilePath += "." + fileType;
|
||||
minFilePath += "_min" + "." + fileType;
|
||||
}
|
||||
|
||||
File file = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + saveFilePath);
|
||||
File minFile = new File(PathUtil.getStaticPath() + FILE_SEPARATOR + minFilePath);
|
||||
|
||||
uploadFile.setIsOSS(0);
|
||||
uploadFile.setUrl(saveFilePath);
|
||||
BufferedInputStream in = null;
|
||||
FileOutputStream out = null;
|
||||
BufferedOutputStream output = null;
|
||||
|
||||
try {
|
||||
in = new BufferedInputStream(inputStream);
|
||||
out = new FileOutputStream(file);
|
||||
output = new BufferedOutputStream(out);
|
||||
Streams.copy(in, output, true);
|
||||
if (FileUtil.isImageFile(uploadFile.getFileType())){
|
||||
ImageOperation.thumbnailsImage(file, minFile, 300);
|
||||
}
|
||||
|
||||
} catch (FileNotFoundException e) {
|
||||
logger.error("文件没有发现" + e);
|
||||
} catch (IOException e) {
|
||||
logger.error("文件读取失败" + e);
|
||||
} finally {
|
||||
|
||||
closeStream(in, out, output);
|
||||
}
|
||||
|
||||
|
||||
|
||||
uploadFile.setSuccess(1);
|
||||
uploadFile.setMessage("上传成功");
|
||||
uploadFile.setFileSize(request.getContentLengthLong());
|
||||
saveUploadFileList.add(uploadFile);
|
||||
return saveUploadFileList;
|
||||
}
|
||||
|
||||
|
||||
private void closeStream(BufferedInputStream in, FileOutputStream out,
|
||||
BufferedOutputStream output) throws IOException {
|
||||
if (in != null) {
|
||||
in.close();
|
||||
}
|
||||
if (out != null) {
|
||||
out.close();
|
||||
}
|
||||
if (output != null) {
|
||||
output.close();
|
||||
}
|
||||
}
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.common.cbb;
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.common.cbb;
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import java.text.DateFormat;
|
||||
import java.text.ParseException;
|
||||
@ -7,6 +7,7 @@ import java.util.Calendar;
|
||||
import java.util.Date;
|
||||
|
||||
public class DateUtil {
|
||||
|
||||
/**
|
||||
* 获取系统当前时间
|
||||
*
|
@ -1,6 +1,5 @@
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import java.io.*;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
@ -74,7 +73,7 @@ public class FileUtil {
|
||||
* @param fileName 文件名
|
||||
* @return 文件扩展名
|
||||
*/
|
||||
public static String getFileType(String fileName) {
|
||||
public static String getFileExtendName(String fileName) {
|
||||
if (fileName.lastIndexOf(".") == -1) {
|
||||
return "";
|
||||
//这里暂时用jpg,后续应该去获取真实的文件类型
|
||||
@ -89,7 +88,7 @@ public class FileUtil {
|
||||
* @return 文件名(不带扩展名)
|
||||
*/
|
||||
public static String getFileNameNotExtend(String fileName) {
|
||||
String fileType = getFileType(fileName);
|
||||
String fileType = getFileExtendName(fileName);
|
||||
return fileName.replace("." + fileType, "");
|
||||
}
|
||||
|
||||
|
@ -1,4 +0,0 @@
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
public class OfficeUtil {
|
||||
}
|
@ -1,24 +0,0 @@
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import java.util.Random;
|
||||
|
||||
public class RandomUtil {
|
||||
public static String getStringRandom(int length) {
|
||||
|
||||
String val = "";
|
||||
Random random = new Random();
|
||||
//参数length,表示生成几位随机数
|
||||
for(int i = 0; i < length; i++) {
|
||||
String charOrNum = random.nextInt(2) % 2 == 0 ? "char" : "num";
|
||||
//输出字母还是数字
|
||||
if("char".equalsIgnoreCase(charOrNum)){
|
||||
//输出是大写字母还是小写字母
|
||||
int temp = random.nextInt(2) % 2 == 0 ? 65 : 97;
|
||||
val += (char)(random.nextInt(26) + temp);
|
||||
}else if("num".equalsIgnoreCase(charOrNum)) {
|
||||
val += String.valueOf(random.nextInt(10));
|
||||
}
|
||||
}
|
||||
return val;
|
||||
}
|
||||
}
|
@ -0,0 +1,218 @@
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.data.redis.connection.RedisStringCommands;
|
||||
import org.springframework.data.redis.connection.ReturnType;
|
||||
import org.springframework.data.redis.core.RedisCallback;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.data.redis.core.types.Expiration;
|
||||
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* redis实现分布式锁
|
||||
*
|
||||
*/
|
||||
public class RedisLockUtils {
|
||||
|
||||
private static final Logger log = LoggerFactory.getLogger(RedisLockUtils.class);
|
||||
|
||||
/**
|
||||
* 默认轮休获取锁间隔时间, 单位:毫秒
|
||||
*/
|
||||
private static final int DEFAULT_ACQUIRE_RESOLUTION_MILLIS = 100;
|
||||
|
||||
private static final String UNLOCK_LUA;
|
||||
|
||||
static {
|
||||
StringBuilder lua = new StringBuilder();
|
||||
lua.append("if redis.call(\"get\",KEYS[1]) == ARGV[1] ");
|
||||
lua.append("then ");
|
||||
lua.append(" return redis.call(\"del\",KEYS[1]) ");
|
||||
lua.append("else ");
|
||||
lua.append(" return 0 ");
|
||||
lua.append("end ");
|
||||
UNLOCK_LUA = lua.toString();
|
||||
}
|
||||
|
||||
private RedisTemplate redisTemplate;
|
||||
|
||||
private final ThreadLocal<Map<String, LockVO>> lockMap = new ThreadLocal<>();
|
||||
|
||||
public RedisLockUtils(RedisTemplate redisTemplate) {
|
||||
this.redisTemplate = redisTemplate;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取锁,没有获取到则一直等待
|
||||
*
|
||||
* @param key redis key
|
||||
* @param expire 锁过期时间, 单位 秒
|
||||
*/
|
||||
public void lock(final String key, long expire) {
|
||||
try {
|
||||
acquireLock(key, expire, -1);
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("acquire lock exception", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取锁,指定时间内没有获取到,返回false。否则 返回true
|
||||
*
|
||||
* @param key redis key
|
||||
* @param expire 锁过期时间, 单位 秒
|
||||
* @param waitTime 获取锁超时时间, -1代表永不超时, 单位 秒
|
||||
*/
|
||||
public boolean tryLock(final String key, long expire, long waitTime) {
|
||||
try {
|
||||
return acquireLock(key, expire, waitTime);
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("acquire lock exception", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 释放锁
|
||||
*
|
||||
* @param key redis key
|
||||
*/
|
||||
public void unlock(String key) {
|
||||
try {
|
||||
release(key);
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("release lock exception", e);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param key redis key
|
||||
* @param expire 锁过期时间, 单位 秒
|
||||
* @param waitTime 获取锁超时时间, -1代表永不超时, 单位 秒
|
||||
* @return if true success else fail
|
||||
* @throws InterruptedException 阻塞方法收到中断请求
|
||||
*/
|
||||
private boolean acquireLock(String key, long expire, long waitTime) throws InterruptedException {
|
||||
//如果之前获取到了并且没有超时,则返回获取成功
|
||||
boolean acquired = acquired(key);
|
||||
if (acquired) {
|
||||
return true;
|
||||
}
|
||||
long acquireTime = waitTime == -1 ? -1 : waitTime * 1000 + System.currentTimeMillis();
|
||||
//同一个进程,对于同一个key锁,只允许先到的去尝试获取。
|
||||
// key.intern() 如果常量池中存在当前字符串, 就会直接返回当前字符串.
|
||||
// 如果常量池中没有此字符串, 会将此字符串放入常量池中后, 再返回
|
||||
synchronized (key.intern()) {
|
||||
String lockId = UUID.randomUUID().toString();
|
||||
do {
|
||||
long before = System.currentTimeMillis();
|
||||
boolean hasLock = tryLock(key, expire, lockId);
|
||||
//获取锁成功
|
||||
if (hasLock) {
|
||||
long after = System.currentTimeMillis();
|
||||
Map<String, LockVO> map = lockMap.get();
|
||||
if (map == null) {
|
||||
map = new HashMap<>(2);
|
||||
lockMap.set(map);
|
||||
}
|
||||
map.put(key, new LockVO(1, lockId, expire * 1000 + before, expire * 1000 + after));
|
||||
log.debug("acquire lock {} {} ", key, 1);
|
||||
return true;
|
||||
}
|
||||
Thread.sleep(DEFAULT_ACQUIRE_RESOLUTION_MILLIS);
|
||||
} while (acquireTime == -1 || acquireTime > System.currentTimeMillis());
|
||||
}
|
||||
log.debug("acquire lock {} fail,because timeout ", key);
|
||||
return false;
|
||||
}
|
||||
|
||||
private boolean acquired(String key) {
|
||||
Map<String, LockVO> map = lockMap.get();
|
||||
if (map == null || map.size() == 0 || !map.containsKey(key)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
LockVO vo = map.get(key);
|
||||
if (vo.beforeExpireTime < System.currentTimeMillis()) {
|
||||
log.debug("lock {} maybe release, because timeout ", key);
|
||||
return false;
|
||||
}
|
||||
int after = ++vo.count;
|
||||
log.debug("acquire lock {} {} ", key, after);
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* 释放锁
|
||||
*
|
||||
* @param key redis key
|
||||
*/
|
||||
private void release(String key) {
|
||||
Map<String, LockVO> map = lockMap.get();
|
||||
if (map == null || map.size() == 0 || !map.containsKey(key)) {
|
||||
return;
|
||||
}
|
||||
LockVO vo = map.get(key);
|
||||
if (vo.afterExpireTime < System.currentTimeMillis()) {
|
||||
log.debug("release lock {}, because timeout ", key);
|
||||
map.remove(key);
|
||||
return;
|
||||
}
|
||||
int after = --vo.count;
|
||||
log.debug("release lock {} {} ", key, after);
|
||||
if (after > 0) {
|
||||
return;
|
||||
}
|
||||
map.remove(key);
|
||||
RedisCallback<Boolean> callback = (connection) ->
|
||||
connection.eval(UNLOCK_LUA.getBytes(StandardCharsets.UTF_8), ReturnType.BOOLEAN, 1,
|
||||
(key).getBytes(StandardCharsets.UTF_8), vo.lockId.getBytes(StandardCharsets.UTF_8));
|
||||
redisTemplate.execute(callback);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param key 锁的key
|
||||
* @param expire 锁的超时时间 秒
|
||||
* @param lockId 获取锁后,UUID生成的唯一ID
|
||||
* @return if true success else fail
|
||||
*/
|
||||
private boolean tryLock(String key, long expire, String lockId) {
|
||||
RedisCallback<Boolean> callback = (connection) ->
|
||||
connection.set((key).getBytes(StandardCharsets.UTF_8),
|
||||
lockId.getBytes(StandardCharsets.UTF_8), Expiration.seconds(expire), RedisStringCommands.SetOption.SET_IF_ABSENT);
|
||||
return (Boolean) redisTemplate.execute(callback);
|
||||
}
|
||||
|
||||
private static class LockVO {
|
||||
/**
|
||||
* 锁重入的次数
|
||||
*/
|
||||
private int count;
|
||||
|
||||
/**
|
||||
* 获取锁后,UUID生成的唯一ID
|
||||
*/
|
||||
private String lockId;
|
||||
/**
|
||||
* 获取锁之前的时间戳
|
||||
*/
|
||||
private long beforeExpireTime;
|
||||
/**
|
||||
* 获取到锁的时间戳
|
||||
*/
|
||||
private long afterExpireTime;
|
||||
|
||||
LockVO(int count, String lockId, long beforeExpireTime, long afterExpireTime) {
|
||||
this.count = count;
|
||||
this.lockId = lockId;
|
||||
this.beforeExpireTime = beforeExpireTime;
|
||||
this.afterExpireTime = afterExpireTime;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -0,0 +1,79 @@
|
||||
package com.qiwenshare.common.util;
|
||||
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.dao.DataAccessException;
|
||||
import org.springframework.data.redis.core.RedisOperations;
|
||||
import org.springframework.data.redis.core.RedisTemplate;
|
||||
import org.springframework.data.redis.core.SessionCallback;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
@Component
|
||||
@Slf4j
|
||||
public class RedisUtil {
|
||||
|
||||
@Resource
|
||||
RedisTemplate<String, Object> redisTemplate;
|
||||
|
||||
/**
|
||||
* 将值放入缓存
|
||||
*/
|
||||
public void set(String key, Object value) {
|
||||
redisTemplate.opsForValue().set(key, value);
|
||||
}
|
||||
|
||||
/**
|
||||
* 字符串:取对象
|
||||
*/
|
||||
public <T> T getObject(String key) {
|
||||
Object o = redisTemplate.opsForValue().get(key);
|
||||
if (o != null) {
|
||||
return (T) o;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* 将值放入缓存并设置时间-秒
|
||||
*/
|
||||
public void set(String key, Object value, long time) {
|
||||
if (time > 0) {
|
||||
redisTemplate.opsForValue().set(key, value, time, TimeUnit.SECONDS);
|
||||
} else {
|
||||
redisTemplate.opsForValue().set(key, value);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 删除key
|
||||
*/
|
||||
public void deleteKey(String key) {
|
||||
redisTemplate.delete(key);
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建锁
|
||||
* @param key 锁的Key
|
||||
* @param value 值(随便写毫无意义)
|
||||
* @param releaseTime 锁过期时间 防止死锁
|
||||
* @return boolean
|
||||
*/
|
||||
public boolean lock(String key, int value, long releaseTime) {
|
||||
// 尝试获取锁
|
||||
Boolean boo = redisTemplate.opsForValue().setIfAbsent(key, value, releaseTime, TimeUnit.SECONDS);
|
||||
// 判断结果
|
||||
return boo != null && boo;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 根据key删除锁
|
||||
*/
|
||||
public void deleteLock(String key) {
|
||||
// 删除key即可释放锁
|
||||
deleteKey(key);
|
||||
}
|
||||
}
|
@ -73,12 +73,10 @@
|
||||
<version>4.13</version>
|
||||
<scope>test</scope>
|
||||
</dependency>
|
||||
|
||||
<!-- <dependency>-->
|
||||
<!-- <groupId>com.qiwenshare</groupId>-->
|
||||
<!-- <artifactId>file-office</artifactId>-->
|
||||
<!-- <version>1.0.0-SNAPSHOT</version>-->
|
||||
<!-- </dependency>-->
|
||||
<dependency>
|
||||
<groupId>org.springframework.boot</groupId>
|
||||
<artifactId>spring-boot-starter-data-elasticsearch</artifactId>
|
||||
</dependency>
|
||||
|
||||
</dependencies>
|
||||
|
||||
|
@ -3,6 +3,8 @@ package com.qiwenshare.file;
|
||||
import org.mybatis.spring.annotation.MapperScan;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.context.annotation.ComponentScan;
|
||||
import org.springframework.context.annotation.FilterType;
|
||||
import org.springframework.scheduling.annotation.EnableScheduling;
|
||||
import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
|
||||
@ -11,6 +13,11 @@ import org.springframework.transaction.annotation.EnableTransactionManagement;
|
||||
@EnableScheduling
|
||||
//@EnableDiscoveryClient
|
||||
@EnableTransactionManagement
|
||||
@ComponentScan(value = "com.qiwenshare", excludeFilters = @ComponentScan.Filter(
|
||||
type = FilterType.ASSIGNABLE_TYPE,
|
||||
classes = {
|
||||
}
|
||||
))
|
||||
public class FileApplication {
|
||||
|
||||
public static void main(String[] args) {
|
||||
|
@ -1,6 +1,6 @@
|
||||
package com.qiwenshare.file.advice;
|
||||
|
||||
import com.qiwenshare.common.cbb.ResultCodeEnum;
|
||||
import com.qiwenshare.common.result.ResultCodeEnum;
|
||||
import lombok.Data;
|
||||
|
||||
/**
|
||||
|
@ -1,12 +1,14 @@
|
||||
package com.qiwenshare.file.advice;
|
||||
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.cbb.ResultCodeEnum;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.result.ResultCodeEnum;
|
||||
import com.qiwenshare.common.exception.UploadGeneralException;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.web.bind.annotation.ControllerAdvice;
|
||||
import org.springframework.web.bind.annotation.ExceptionHandler;
|
||||
import org.springframework.web.bind.annotation.ResponseBody;
|
||||
import org.springframework.web.client.HttpClientErrorException;
|
||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
||||
|
||||
/**
|
||||
* 该注解为统一异常处理的核心
|
||||
@ -20,6 +22,7 @@ public class GlobalExceptionHandlerAdvice {
|
||||
/**-------- 通用异常处理方法 --------**/
|
||||
@ExceptionHandler(Exception.class)
|
||||
@ResponseBody
|
||||
@ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
|
||||
public RestResult error(Exception e) {
|
||||
e.printStackTrace();
|
||||
log.error("全局异常捕获:" + e);
|
||||
@ -30,6 +33,7 @@ public class GlobalExceptionHandlerAdvice {
|
||||
/**-------- 指定异常处理方法 --------**/
|
||||
@ExceptionHandler(NullPointerException.class)
|
||||
@ResponseBody
|
||||
@ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
|
||||
public RestResult error(NullPointerException e) {
|
||||
e.printStackTrace();
|
||||
log.error("全局异常捕获:" + e);
|
||||
@ -38,15 +42,26 @@ public class GlobalExceptionHandlerAdvice {
|
||||
/**-------- 下标越界处理方法 --------**/
|
||||
@ExceptionHandler(IndexOutOfBoundsException.class)
|
||||
@ResponseBody
|
||||
@ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
|
||||
public RestResult error(IndexOutOfBoundsException e) {
|
||||
e.printStackTrace();
|
||||
log.error("全局异常捕获:" + e);
|
||||
return RestResult.setResult(ResultCodeEnum.INDEX_OUT_OF_BOUNDS);
|
||||
}
|
||||
|
||||
@ExceptionHandler(UploadGeneralException.class)
|
||||
@ResponseBody
|
||||
@ResponseStatus(HttpStatus.REQUEST_TIMEOUT)
|
||||
public RestResult error(UploadGeneralException e) {
|
||||
e.printStackTrace();
|
||||
log.error("全局异常捕获:" + e);
|
||||
return RestResult.setResult(ResultCodeEnum.REQUEST_TIMEOUT);
|
||||
}
|
||||
|
||||
/**-------- 自定义定异常处理方法 --------**/
|
||||
@ExceptionHandler(CMSException.class)
|
||||
@ResponseBody
|
||||
@ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
|
||||
public RestResult error(CMSException e) {
|
||||
e.printStackTrace();
|
||||
log.error("全局异常捕获:" + e);
|
||||
|
@ -1,6 +1,6 @@
|
||||
package com.qiwenshare.file.aop;
|
||||
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
import com.qiwenshare.file.api.IOperationLogService;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
|
@ -0,0 +1,8 @@
|
||||
package com.qiwenshare.file.api;
|
||||
|
||||
import com.qiwenshare.file.config.es.FileSearch;
|
||||
import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;
|
||||
|
||||
public interface IElasticSearchService extends ElasticsearchRepository<FileSearch,Long> {
|
||||
|
||||
}
|
@ -19,7 +19,7 @@ public interface IFileService extends IService<FileBean> {
|
||||
|
||||
// List<FileBean> selectFileListByPath(FileBean fileBean);
|
||||
|
||||
void deleteLocalFile(FileBean fileBean);
|
||||
// void deleteLocalFile(FileBean fileBean);
|
||||
|
||||
|
||||
|
||||
|
@ -1,9 +1,12 @@
|
||||
package com.qiwenshare.file.api;
|
||||
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.domain.StorageBean;
|
||||
import com.qiwenshare.file.dto.DownloadFileDTO;
|
||||
import com.qiwenshare.file.dto.UploadFileDTO;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
public interface IFiletransferService {
|
||||
|
||||
@ -18,6 +21,8 @@ public interface IFiletransferService {
|
||||
*/
|
||||
void uploadFile(HttpServletRequest request, UploadFileDTO UploadFileDto, Long userId);
|
||||
|
||||
void downloadFile(HttpServletResponse httpServletResponse, DownloadFileDTO downloadFileDTO);
|
||||
void deleteFile(FileBean fileBean);
|
||||
StorageBean selectStorageBean(StorageBean storageBean);
|
||||
|
||||
void insertStorageBean(StorageBean storageBean);
|
||||
|
@ -21,6 +21,6 @@ public interface IUserFileService extends IService<UserFile> {
|
||||
Long selectCountNotInExtendNames(List<String> fileNameList, Long beginCount, Long pageCount, long userId);
|
||||
List<UserFile> selectFileTreeListLikeFilePath(String filePath, long userId);
|
||||
List<UserFile> selectFilePathTreeByUserId(Long userId);
|
||||
void deleteUserFile(UserFile userFile, UserBean sessionUserBean);
|
||||
void deleteUserFile(Long userFileId, Long sessionUserId);
|
||||
|
||||
}
|
||||
|
@ -1,11 +1,9 @@
|
||||
package com.qiwenshare.file.api;
|
||||
|
||||
import com.baomidou.mybatisplus.extension.service.IService;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public interface IUserService extends IService<UserBean> {
|
||||
|
||||
UserBean getUserBeanByToken(String token);
|
||||
|
@ -0,0 +1,52 @@
|
||||
package com.qiwenshare.file.config.es;
|
||||
|
||||
import lombok.Data;
|
||||
import org.springframework.data.annotation.Id;
|
||||
import org.springframework.data.elasticsearch.annotations.Document;
|
||||
import org.springframework.data.elasticsearch.annotations.Field;
|
||||
import org.springframework.data.elasticsearch.annotations.FieldType;
|
||||
|
||||
@Data
|
||||
@Document(indexName = "filesearch", shards = 1, replicas = 0)
|
||||
public class FileSearch {
|
||||
|
||||
@Id
|
||||
private long fileSearchId;
|
||||
@Field(type = FieldType.Long)
|
||||
private Long fileId;
|
||||
@Field(type = FieldType.Text, analyzer = "ik_max_word")
|
||||
private String fileName;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String timeStampName;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String fileUrl;
|
||||
@Field(type = FieldType.Long)
|
||||
private Long fileSize;
|
||||
@Field(type = FieldType.Integer)
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
@Field(type = FieldType.Integer)
|
||||
private Integer storageType;
|
||||
@Field(type = FieldType.Integer)
|
||||
private Integer pointCount;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String identifier;
|
||||
@Field(type = FieldType.Long)
|
||||
private Long userFileId;
|
||||
@Field(type = FieldType.Long)
|
||||
private Long userId;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String filePath;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String extendName;
|
||||
@Field(type = FieldType.Integer)
|
||||
private Integer isDir;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String uploadTime;
|
||||
@Field(type = FieldType.Integer)
|
||||
private Integer deleteFlag;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String deleteTime;
|
||||
@Field(type = FieldType.Keyword)
|
||||
private String deleteBatchNum;
|
||||
}
|
@ -1,13 +1,16 @@
|
||||
package com.qiwenshare.file.controller;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.aliyun.oss.OSS;
|
||||
import com.aliyun.oss.OSSClientBuilder;
|
||||
import com.aliyun.oss.model.CopyObjectResult;
|
||||
import com.aliyun.oss.model.ObjectMetadata;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.common.operation.FileOperation;
|
||||
import com.qiwenshare.common.oss.AliyunOSSRename;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
@ -15,14 +18,24 @@ import com.qiwenshare.file.api.IFileService;
|
||||
import com.qiwenshare.file.api.IRecoveryFileService;
|
||||
import com.qiwenshare.file.api.IUserFileService;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.config.es.FileSearch;
|
||||
import com.qiwenshare.file.domain.*;
|
||||
import com.qiwenshare.file.dto.*;
|
||||
import com.qiwenshare.file.dto.file.*;
|
||||
import com.qiwenshare.file.vo.file.FileListVo;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.codec.digest.DigestUtils;
|
||||
import org.elasticsearch.index.query.QueryBuilders;
|
||||
import org.elasticsearch.search.fetch.subphase.highlight.HighlightBuilder;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.data.domain.PageRequest;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.elasticsearch.core.ElasticsearchRestTemplate;
|
||||
import org.springframework.data.elasticsearch.core.SearchHits;
|
||||
import org.springframework.data.elasticsearch.core.query.NativeSearchQueryBuilder;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
@ -54,7 +67,8 @@ public class FileController {
|
||||
|
||||
public static final String CURRENT_MODULE = "文件接口";
|
||||
|
||||
|
||||
@Autowired
|
||||
private ElasticsearchRestTemplate elasticsearchRestTemplate;
|
||||
public static long treeid = 0;
|
||||
|
||||
|
||||
@ -86,41 +100,79 @@ public class FileController {
|
||||
return RestResult.success();
|
||||
}
|
||||
|
||||
@Operation(summary = "文件搜索", description = "文件搜索", tags = {"file"})
|
||||
@GetMapping(value = "/search")
|
||||
@MyLog(operation = "文件搜索", module = CURRENT_MODULE)
|
||||
@ResponseBody
|
||||
public RestResult<SearchHits<FileSearch>> searchFile(SearchFileDTO searchFileDTO) {
|
||||
NativeSearchQueryBuilder queryBuilder = new NativeSearchQueryBuilder();
|
||||
HighlightBuilder.Field allHighLight = new HighlightBuilder.Field("*").preTags("<span class='keyword'>")
|
||||
.postTags("</span>");
|
||||
|
||||
queryBuilder.withHighlightFields(allHighLight);
|
||||
|
||||
//设置分页
|
||||
int currentPage = (int)searchFileDTO.getCurrentPage() - 1;
|
||||
int pageCount = (int)(searchFileDTO.getPageCount() == 0 ? 10 : searchFileDTO.getPageCount());
|
||||
String order = searchFileDTO.getOrder();
|
||||
Sort.Direction direction = null;
|
||||
if (searchFileDTO.getDirection() == null) {
|
||||
direction = Sort.Direction.DESC;
|
||||
} else if ("asc".equals(searchFileDTO.getDirection())) {
|
||||
direction = Sort.Direction.ASC;
|
||||
} else if ("desc".equals(searchFileDTO.getDirection())) {
|
||||
direction = Sort.Direction.DESC;
|
||||
} else {
|
||||
direction = Sort.Direction.DESC;
|
||||
}
|
||||
if (order == null) {
|
||||
queryBuilder.withPageable(PageRequest.of(currentPage, pageCount));
|
||||
} else {
|
||||
queryBuilder.withPageable(PageRequest.of(currentPage, pageCount, Sort.by(direction, order)));
|
||||
}
|
||||
|
||||
queryBuilder.withQuery(QueryBuilders.matchQuery("fileName", searchFileDTO.getFileName()));
|
||||
SearchHits<FileSearch> search = elasticsearchRestTemplate.search(queryBuilder.build(), FileSearch.class);
|
||||
|
||||
return RestResult.success().data(search);
|
||||
}
|
||||
|
||||
@Operation(summary = "文件重命名", description = "文件重命名", tags = {"file"})
|
||||
@RequestMapping(value = "/renamefile", method = RequestMethod.POST)
|
||||
@MyLog(operation = "文件重命名", module = CURRENT_MODULE)
|
||||
@ResponseBody
|
||||
public RestResult<String> renameFile(@RequestBody RenameFileDTO renameFileDto, @RequestHeader("token") String token) {
|
||||
RestResult<String> restResult = new RestResult<>();
|
||||
if (!operationCheck(token).getSuccess()){
|
||||
return operationCheck(token);
|
||||
}
|
||||
UserBean sessionUserBean = userService.getUserBeanByToken(token);
|
||||
UserFile userFile = userFileService.getById(renameFileDto.getUserFileId());
|
||||
|
||||
List<UserFile> userFiles = userFileService.selectUserFileByNameAndPath(renameFileDto.getFileName(), renameFileDto.getFilePath(), sessionUserBean.getUserId());
|
||||
if (userFiles != null && !userFiles.isEmpty()) {
|
||||
return RestResult.fail().message("同名文件已存在");
|
||||
|
||||
}
|
||||
if (1 == renameFileDto.getIsDir()) {
|
||||
if (1 == userFile.getIsDir()) {
|
||||
LambdaUpdateWrapper<UserFile> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
lambdaUpdateWrapper.set(UserFile::getFileName, renameFileDto.getFileName())
|
||||
.set(UserFile::getUploadTime, DateUtil.getCurrentTime())
|
||||
.eq(UserFile::getUserFileId, renameFileDto.getUserFileId());
|
||||
userFileService.update(lambdaUpdateWrapper);
|
||||
userFileService.replaceUserFilePath(renameFileDto.getFilePath() + renameFileDto.getFileName() + "/",
|
||||
renameFileDto.getFilePath() + renameFileDto.getOldFileName() + "/", sessionUserBean.getUserId());
|
||||
userFileService.replaceUserFilePath(userFile.getFilePath() + renameFileDto.getFileName() + "/",
|
||||
userFile.getFilePath() + userFile.getFileName() + "/", sessionUserBean.getUserId());
|
||||
} else {
|
||||
if (renameFileDto.getIsOSS() == 1) {
|
||||
LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
lambdaQueryWrapper.eq(UserFile::getUserFileId, renameFileDto.getUserFileId());
|
||||
UserFile userFile = userFileService.getOne(lambdaQueryWrapper);
|
||||
FileBean file = fileService.getById(userFile.getFileId());
|
||||
if (file.getIsOSS() == 1 || file.getStorageType() == 1) {
|
||||
// LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
// lambdaQueryWrapper.eq(UserFile::getUserFileId, renameFileDto.getUserFileId());
|
||||
// UserFile userFile = userFileService.getOne(lambdaQueryWrapper);
|
||||
|
||||
|
||||
FileBean file = fileService.getById(userFile.getFileId());
|
||||
String fileUrl = file.getFileUrl();
|
||||
String newFileUrl = fileUrl.replace(userFile.getFileName(), renameFileDto.getFileName());
|
||||
|
||||
AliyunOSSRename.rename(qiwenFileConfig.getAliyun().getOss(),
|
||||
rename(qiwenFileConfig.getAliyun().getOss(),
|
||||
fileUrl.substring(1),
|
||||
newFileUrl.substring(1));
|
||||
LambdaUpdateWrapper<FileBean> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
@ -143,12 +195,32 @@ public class FileController {
|
||||
userFileService.update(lambdaUpdateWrapper);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
return RestResult.success();
|
||||
}
|
||||
|
||||
private void rename(AliyunOSS aliyunOSS, String sourceObjectName, String destinationObjectName) {
|
||||
String endpoint = aliyunOSS.getEndpoint();
|
||||
String accessKeyId = aliyunOSS.getAccessKeyId();
|
||||
String accessKeySecret = aliyunOSS.getAccessKeySecret();
|
||||
String bucketName = aliyunOSS.getBucketName();
|
||||
OSS ossClient = new OSSClientBuilder().build(endpoint, accessKeyId, accessKeySecret);
|
||||
CopyObjectResult result = ossClient.copyObject(bucketName, sourceObjectName, bucketName, destinationObjectName);
|
||||
|
||||
ossClient.deleteObject(bucketName, sourceObjectName);
|
||||
ObjectMetadata metadata = new ObjectMetadata();
|
||||
// if ("pdf".equals(FileUtil.getFileType(objectName))) {
|
||||
// metadata.setContentDisposition("attachment");
|
||||
// }
|
||||
|
||||
// ossClient.putObject(bucketName, objectName, inputStream, metadata);
|
||||
|
||||
|
||||
// 关闭OSSClient。
|
||||
ossClient.shutdown();
|
||||
}
|
||||
|
||||
|
||||
@Operation(summary = "获取文件列表", description = "用来做前台列表展示", tags = {"file"})
|
||||
@RequestMapping(value = "/getfilelist", method = RequestMethod.GET)
|
||||
@ -206,15 +278,9 @@ public class FileController {
|
||||
List<UserFile> userFiles = JSON.parseArray(batchDeleteFileDto.getFiles(), UserFile.class);
|
||||
DigestUtils.md5Hex("data");
|
||||
for (UserFile userFile : userFiles) {
|
||||
String uuid = UUID.randomUUID().toString();
|
||||
userFile.setDeleteBatchNum(uuid);
|
||||
userFileService.deleteUserFile(userFile,sessionUserBean);
|
||||
|
||||
RecoveryFile recoveryFile = new RecoveryFile();
|
||||
recoveryFile.setUserFileId(userFile.getUserFileId());
|
||||
recoveryFile.setDeleteTime(DateUtil.getCurrentTime());
|
||||
recoveryFile.setDeleteBatchNum(uuid);
|
||||
recoveryFileService.save(recoveryFile);
|
||||
//userFile.setDeleteBatchNum(uuid);
|
||||
userFileService.deleteUserFile(userFile.getUserFileId(),sessionUserBean.getUserId());
|
||||
}
|
||||
|
||||
return RestResult.success().message("批量删除文件成功");
|
||||
@ -230,20 +296,16 @@ public class FileController {
|
||||
return operationCheck(token);
|
||||
}
|
||||
|
||||
String uuid = UUID.randomUUID().toString();
|
||||
UserBean sessionUserBean = userService.getUserBeanByToken(token);
|
||||
UserFile userFile = new UserFile();
|
||||
userFile.setUserFileId(deleteFileDto.getUserFileId());
|
||||
userFile.setDeleteBatchNum(uuid);
|
||||
BeanUtil.copyProperties(deleteFileDto, userFile);
|
||||
userFileService.deleteUserFile(userFile, sessionUserBean);
|
||||
// String uuid = UUID.randomUUID().toString();
|
||||
|
||||
// UserFile userFile = new UserFile();
|
||||
// userFile.setUserFileId(deleteFileDto.getUserFileId());
|
||||
//// userFile.setDeleteBatchNum(uuid);
|
||||
// BeanUtil.copyProperties(deleteFileDto, userFile);
|
||||
userFileService.deleteUserFile(deleteFileDto.getUserFileId(), sessionUserBean.getUserId());
|
||||
|
||||
|
||||
RecoveryFile recoveryFile = new RecoveryFile();
|
||||
recoveryFile.setUserFileId(deleteFileDto.getUserFileId());
|
||||
recoveryFile.setDeleteTime(DateUtil.getCurrentTime());
|
||||
recoveryFile.setDeleteBatchNum(uuid);
|
||||
recoveryFileService.save(recoveryFile);
|
||||
return RestResult.success();
|
||||
|
||||
}
|
||||
@ -309,7 +371,7 @@ public class FileController {
|
||||
}else{
|
||||
|
||||
userFile.setIsDir(0);
|
||||
userFile.setExtendName(FileUtil.getFileType(totalFileUrl));
|
||||
userFile.setExtendName(FileUtil.getFileExtendName(totalFileUrl));
|
||||
userFile.setFileName(FileUtil.getFileNameNotExtend(currentFile.getName()));
|
||||
tempFileBean.setFileSize(currentFile.length());
|
||||
tempFileBean.setTimeStampName(FileUtil.getFileNameNotExtend(currentFile.getName()));
|
||||
|
@ -1,18 +1,23 @@
|
||||
package com.qiwenshare.file.controller;
|
||||
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.github.tobato.fastdfs.proto.storage.DownloadByteArray;
|
||||
import com.github.tobato.fastdfs.service.FastFileStorageClient;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.operation.FileOperation;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
import com.qiwenshare.file.api.IFileService;
|
||||
import com.qiwenshare.file.api.IFiletransferService;
|
||||
import com.qiwenshare.file.api.IUserFileService;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.domain.StorageBean;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
import com.qiwenshare.file.domain.UserFile;
|
||||
import com.qiwenshare.file.dto.DownloadFileDTO;
|
||||
import com.qiwenshare.file.dto.UploadFileDTO;
|
||||
import com.qiwenshare.file.vo.file.UploadFileVo;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
@ -21,7 +26,10 @@ import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.ServletOutputStream;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.*;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
@ -45,6 +53,8 @@ public class FiletransferController {
|
||||
IUserService userService;
|
||||
@Resource
|
||||
IUserFileService userFileService;
|
||||
@Autowired
|
||||
private FastFileStorageClient fastFileStorageClient;
|
||||
public static final String CURRENT_MODULE = "文件传输接口";
|
||||
|
||||
@Operation(summary = "极速上传", description = "校验文件MD5判断文件是否存在,如果存在直接上传成功并返回skipUpload=true,如果不存在返回skipUpload=false需要再次调用该接口的POST方法", tags = {"filetransfer"})
|
||||
@ -76,7 +86,7 @@ public class FiletransferController {
|
||||
userFile.setFilePath(uploadFileDto.getFilePath());
|
||||
String fileName = uploadFileDto.getFilename();
|
||||
userFile.setFileName(fileName.substring(0, fileName.lastIndexOf(".")));
|
||||
userFile.setExtendName(FileUtil.getFileType(fileName));
|
||||
userFile.setExtendName(FileUtil.getFileExtendName(fileName));
|
||||
userFile.setDeleteFlag(0);
|
||||
userFile.setIsDir(0);
|
||||
userFile.setUploadTime(DateUtil.getCurrentTime());
|
||||
@ -120,6 +130,81 @@ public class FiletransferController {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* 下载文件
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
@Operation(summary = "下载文件", description = "下载文件接口", tags = {"filetransfer"})
|
||||
@MyLog(operation = "下载文件", module = CURRENT_MODULE)
|
||||
@RequestMapping(value = "/downloadfile", method = RequestMethod.GET)
|
||||
public void downloadFile(HttpServletResponse response, DownloadFileDTO downloadFileDTO) {
|
||||
filetransferService.downloadFile(response, downloadFileDTO);
|
||||
}
|
||||
|
||||
private void localFileDownload(HttpServletResponse response, FileBean fileBean) {
|
||||
BufferedInputStream bis = null;
|
||||
byte[] buffer = new byte[1024];
|
||||
//设置文件路径
|
||||
File file = FileOperation.newFile(PathUtil.getStaticPath() + fileBean.getFileUrl());
|
||||
if (file.exists()) {
|
||||
|
||||
|
||||
FileInputStream fis = null;
|
||||
|
||||
try {
|
||||
fis = new FileInputStream(file);
|
||||
bis = new BufferedInputStream(fis);
|
||||
OutputStream os = response.getOutputStream();
|
||||
int i = bis.read(buffer);
|
||||
while (i != -1) {
|
||||
os.write(buffer, 0, i);
|
||||
i = bis.read(buffer);
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
if (bis != null) {
|
||||
try {
|
||||
bis.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
public void fastFDSDownload(HttpServletResponse response, FileBean fileBean){
|
||||
String group = fileBean.getFileUrl().substring(0, fileBean.getFileUrl().indexOf("/"));
|
||||
String path = fileBean.getFileUrl().substring(fileBean.getFileUrl().indexOf("/") + 1);
|
||||
DownloadByteArray downloadByteArray = new DownloadByteArray();
|
||||
byte[] bytes = fastFileStorageClient.downloadFile(group, path, downloadByteArray);
|
||||
|
||||
// // 这里只是为了整合fastdfs,所以写死了文件格式。需要在上传的时候保存文件名。下载的时候使用对应的格式
|
||||
// response.setHeader("Content-disposition", "attachment;filename=" + URLEncoder.encode("sb.xlsx", "UTF-8"));
|
||||
// response.setCharacterEncoding("UTF-8");
|
||||
ServletOutputStream outputStream = null;
|
||||
try {
|
||||
outputStream = response.getOutputStream();
|
||||
outputStream.write(bytes);
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
} finally {
|
||||
try {
|
||||
outputStream.flush();
|
||||
outputStream.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Operation(summary = "获取存储信息", description = "获取存储信息", tags = {"filetransfer"})
|
||||
@RequestMapping(value = "/getstorage", method = RequestMethod.GET)
|
||||
@ResponseBody
|
||||
|
@ -3,8 +3,8 @@ package com.qiwenshare.file.controller;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
import com.qiwenshare.file.api.IRecoveryFileService;
|
||||
|
@ -1,11 +1,11 @@
|
||||
package com.qiwenshare.file.controller;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import cn.hutool.core.util.RandomUtil;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.util.RandomUtil;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
import com.qiwenshare.file.api.IShareService;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
@ -46,7 +46,7 @@ public class ShareController {
|
||||
public RestResult<ShareFileVO> shareFile(ShareFileDTO shareSecretDTO, @RequestHeader("token") String token) {
|
||||
ShareFileVO shareSecretVO = new ShareFileVO();
|
||||
UserBean sessionUserBean = userService.getUserBeanByToken(token);
|
||||
String extractionCode = RandomUtil.getStringRandom(6);
|
||||
String extractionCode = RandomUtil.randomNumbers(6);
|
||||
String uuid = UUID.randomUUID().toString();
|
||||
Share share = new Share();
|
||||
BeanUtil.copyProperties(sessionUserBean, share);
|
||||
|
@ -1,13 +1,20 @@
|
||||
package com.qiwenshare.file.controller;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.qiwenshare.file.api.IElasticSearchService;
|
||||
import com.qiwenshare.file.config.es.FileSearch;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.domain.UserFile;
|
||||
import com.qiwenshare.file.service.FileService;
|
||||
import com.qiwenshare.file.service.FiletransferService;
|
||||
import com.qiwenshare.file.service.UserFileService;
|
||||
import com.qiwenshare.file.service.UserService;
|
||||
import com.qiwenshare.file.vo.file.FileListVo;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.catalina.User;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.scheduling.annotation.Scheduled;
|
||||
import org.springframework.stereotype.Controller;
|
||||
|
||||
@ -20,15 +27,18 @@ import java.util.List;
|
||||
@Controller
|
||||
public class TaskController {
|
||||
|
||||
@Resource
|
||||
UserFileService userFileService;
|
||||
|
||||
@Resource
|
||||
FileService fileService;
|
||||
@Resource
|
||||
UserFileService userFileService;
|
||||
@Resource
|
||||
FiletransferService filetransferService;
|
||||
@Autowired
|
||||
private IElasticSearchService elasticSearchService;
|
||||
|
||||
@Scheduled(cron = "0 0/1 * * * ?")
|
||||
public void deleteFile() {
|
||||
log.info("111112");
|
||||
|
||||
LambdaQueryWrapper<FileBean> fileBeanLambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
fileBeanLambdaQueryWrapper.eq(FileBean::getPointCount, 0);
|
||||
|
||||
@ -36,11 +46,31 @@ public class TaskController {
|
||||
for (int i = 0; i < fileBeanList.size(); i++) {
|
||||
FileBean fileBean = fileBeanList.get(i);
|
||||
log.info("删除本地文件:" + JSON.toJSONString(fileBean));
|
||||
fileService.deleteLocalFile(fileBean);
|
||||
filetransferService.deleteFile(fileBean);
|
||||
fileService.removeById(fileBean.getFileId());
|
||||
}
|
||||
fileService.remove(fileBeanLambdaQueryWrapper);
|
||||
|
||||
log.info("11111");
|
||||
}
|
||||
|
||||
@Scheduled(fixedRate = 1000 * 60 * 60 * 24)
|
||||
public void updateElasticSearch() {
|
||||
|
||||
UserFile userFile = new UserFile();
|
||||
try {
|
||||
elasticSearchService.deleteAll();
|
||||
} catch (Exception e) {
|
||||
log.error("删除ES失败:" + e);
|
||||
}
|
||||
try {
|
||||
List<FileListVo> userfiles = userFileService.userFileList(userFile, 0L, 999999L);
|
||||
for (FileListVo fileListVo : userfiles) {
|
||||
log.info(JSON.toJSONString(fileListVo));
|
||||
FileSearch fileSearch = new FileSearch();
|
||||
BeanUtil.copyProperties(fileListVo, fileSearch);
|
||||
elasticSearchService.save(fileSearch);
|
||||
}
|
||||
} catch (Exception e) {
|
||||
log.error("更新ES失败:" + e);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -2,14 +2,14 @@ package com.qiwenshare.file.controller;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.common.util.JjwtUtil;
|
||||
import com.qiwenshare.file.anno.MyLog;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
import com.qiwenshare.file.dto.RegisterDTO;
|
||||
import com.qiwenshare.file.dto.user.RegisterDTO;
|
||||
import com.qiwenshare.file.vo.user.UserLoginVo;
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.Parameter;
|
||||
|
@ -34,8 +34,12 @@ public class FileBean {
|
||||
private Long fileSize;
|
||||
|
||||
@Column(columnDefinition="int(1)")
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
|
||||
@Column(columnDefinition="int(1)")
|
||||
private Integer storageType;
|
||||
|
||||
@Column(columnDefinition="int(11)")
|
||||
private Integer pointCount;
|
||||
|
||||
|
@ -0,0 +1,10 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@Schema(name = "下载文件DTO",required = true)
|
||||
public class DownloadFileDTO {
|
||||
private Long userFileId;
|
||||
}
|
@ -1,15 +0,0 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@Schema(name = "用户注册DTO",required = true)
|
||||
public class RegisterDTO {
|
||||
@Schema(description = "用户名")
|
||||
private String username;
|
||||
@Schema(description = "手机号")
|
||||
private String telephone;
|
||||
@Schema(description = "密码")
|
||||
private String password;
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
@ -8,10 +8,15 @@ import lombok.Data;
|
||||
public class DeleteFileDTO {
|
||||
@Schema(description = "用户文件id")
|
||||
private Long userFileId;
|
||||
|
||||
|
||||
@Schema(description = "文件路径")
|
||||
@Deprecated
|
||||
private String filePath;
|
||||
@Schema(description = "文件名")
|
||||
@Deprecated
|
||||
private String fileName;
|
||||
@Schema(description = "是否是目录")
|
||||
@Deprecated
|
||||
private Integer isDir;
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
@ -11,6 +11,7 @@ public class RenameFileDTO {
|
||||
* 文件路径
|
||||
*/
|
||||
@Schema(description = "文件路径")
|
||||
@Deprecated
|
||||
private String filePath;
|
||||
|
||||
/**
|
||||
@ -19,9 +20,12 @@ public class RenameFileDTO {
|
||||
@Schema(description = "文件名")
|
||||
private String fileName;
|
||||
@Schema(description = "是否是目录")
|
||||
@Deprecated
|
||||
private Integer isDir;
|
||||
@Schema(description = "旧文件名")
|
||||
@Deprecated
|
||||
private String oldFileName;
|
||||
@Schema(description = "是否是OSS")
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
}
|
@ -0,0 +1,12 @@
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
public class SearchFileDTO {
|
||||
private String fileName;
|
||||
private long currentPage;
|
||||
private long pageCount;
|
||||
private String order;
|
||||
private String direction;
|
||||
}
|
@ -1,4 +1,4 @@
|
||||
package com.qiwenshare.file.dto;
|
||||
package com.qiwenshare.file.dto.file;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
@ -1,6 +1,15 @@
|
||||
package com.qiwenshare.file.dto.user;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import lombok.Data;
|
||||
|
||||
@Data
|
||||
@Schema(name = "用户注册DTO",required = true)
|
||||
public class RegisterDTO {
|
||||
|
||||
@Schema(description = "用户名")
|
||||
private String username;
|
||||
@Schema(description = "手机号")
|
||||
private String telephone;
|
||||
@Schema(description = "密码")
|
||||
private String password;
|
||||
}
|
||||
|
@ -1,17 +1,14 @@
|
||||
package com.qiwenshare.file.service;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.qiwenshare.common.operation.FileOperation;
|
||||
import com.qiwenshare.common.oss.AliyunOSSDelete;
|
||||
import com.qiwenshare.common.util.FileUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import com.github.tobato.fastdfs.service.FastFileStorageClient;
|
||||
import com.qiwenshare.file.api.IFileService;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.mapper.FileMapper;
|
||||
import com.qiwenshare.file.mapper.UserFileMapper;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
@ -28,6 +25,8 @@ public class FileService extends ServiceImpl<FileMapper, FileBean> implements IF
|
||||
FiletransferService filetransferService;
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
@Autowired
|
||||
private FastFileStorageClient fastFileStorageClient;
|
||||
|
||||
// @Override
|
||||
// public void batchInsertFile(List<FileBean> fileBeanList, Long userId) {
|
||||
@ -78,21 +77,31 @@ public class FileService extends ServiceImpl<FileMapper, FileBean> implements IF
|
||||
// .orderByDesc(FileBean::getIsDir);
|
||||
// return fileMapper.selectList(lambdaQueryWrapper);
|
||||
// }
|
||||
@Override
|
||||
public void deleteLocalFile(FileBean fileBean) {
|
||||
log.info("删除本地文件:" + JSON.toJSONString(fileBean));
|
||||
//删除服务器文件
|
||||
if (fileBean.getFileUrl() != null && fileBean.getFileUrl().indexOf("upload") != -1){
|
||||
if (fileBean.getIsOSS() != null && fileBean.getIsOSS() == 1) {
|
||||
AliyunOSSDelete.deleteObject(qiwenFileConfig.getAliyun().getOss(), fileBean.getFileUrl().substring(1));
|
||||
} else {
|
||||
FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl());
|
||||
if (FileUtil.isImageFile(FileUtil.getFileType(fileBean.getFileUrl()))) {
|
||||
FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl().replace(fileBean.getTimeStampName(), fileBean.getTimeStampName() + "_min"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// @Override
|
||||
// public void deleteLocalFile(FileBean fileBean) {
|
||||
// log.info("删除本地文件:" + JSON.toJSONString(fileBean));
|
||||
// //删除服务器文件
|
||||
// if (fileBean.getFileUrl() != null && fileBean.getFileUrl().indexOf("upload") != -1){
|
||||
// if (fileBean.getIsOSS() != null && fileBean.getIsOSS() == 1) {
|
||||
// AliyunOSSDelete.deleteObject(qiwenFileConfig.getAliyun().getOss(), fileBean.getFileUrl().substring(1));
|
||||
// } else if (fileBean.getStorageType() == 0) {
|
||||
// FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl());
|
||||
// if (FileUtil.isImageFile(FileUtil.getFileExtendName(fileBean.getFileUrl()))) {
|
||||
// FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl().replace(fileBean.getTimeStampName(), fileBean.getTimeStampName() + "_min"));
|
||||
// }
|
||||
// } else if (fileBean.getStorageType() == 1) {
|
||||
// AliyunOSSDelete.deleteObject(qiwenFileConfig.getAliyun().getOss(), fileBean.getFileUrl().substring(1));
|
||||
// } else if (fileBean.getStorageType() == 2){
|
||||
// fastFileStorageClient.deleteFile(fileBean.getFileUrl());
|
||||
//
|
||||
// } else {
|
||||
// FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl());
|
||||
// if (FileUtil.isImageFile(FileUtil.getFileExtendName(fileBean.getFileUrl()))) {
|
||||
// FileOperation.deleteFile(PathUtil.getStaticPath() + fileBean.getFileUrl().replace(fileBean.getTimeStampName(), fileBean.getTimeStampName() + "_min"));
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
|
||||
|
||||
|
@ -1,23 +1,30 @@
|
||||
package com.qiwenshare.file.service;
|
||||
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.util.List;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
import cn.hutool.core.bean.BeanUtil;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.domain.DeleteFile;
|
||||
import com.qiwenshare.common.domain.DownloadFile;
|
||||
import com.qiwenshare.common.domain.UploadFile;
|
||||
import com.qiwenshare.common.upload.factory.AliyunOSSUploaderFactory;
|
||||
import com.qiwenshare.common.upload.factory.ChunkUploaderFactory;
|
||||
import com.qiwenshare.common.upload.Uploader;
|
||||
//import com.qiwenshare.common.factory.FileOperationFactory;
|
||||
import com.qiwenshare.common.operation.delete.Deleter;
|
||||
import com.qiwenshare.common.operation.download.Downloader;
|
||||
import com.qiwenshare.common.factory.FileOperationFactory;
|
||||
import com.qiwenshare.common.operation.upload.Uploader;
|
||||
|
||||
import com.qiwenshare.file.api.IFiletransferService;
|
||||
|
||||
import com.qiwenshare.common.domain.AliyunOSS;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.domain.UserFile;
|
||||
import com.qiwenshare.file.dto.DownloadFileDTO;
|
||||
import com.qiwenshare.file.dto.UploadFileDTO;
|
||||
import com.qiwenshare.file.mapper.FileMapper;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
@ -34,19 +41,23 @@ public class FiletransferService implements IFiletransferService {
|
||||
StorageMapper storageMapper;
|
||||
@Resource
|
||||
FileMapper fileMapper;
|
||||
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
|
||||
@Resource
|
||||
UserFileMapper userFileMapper;
|
||||
|
||||
|
||||
@Resource
|
||||
FileOperationFactory fastDFSOperationFactory;
|
||||
@Resource
|
||||
FileOperationFactory aliyunOSSOperationFactory;
|
||||
@Resource
|
||||
FileOperationFactory localStorageOperationFactory;
|
||||
|
||||
@Override
|
||||
public void uploadFile(HttpServletRequest request, UploadFileDTO UploadFileDto, Long userId) {
|
||||
AliyunOSS oss = qiwenFileConfig.getAliyun().getOss();
|
||||
request.setAttribute("oss", oss);
|
||||
Uploader uploader;
|
||||
|
||||
Uploader uploader = null;
|
||||
UploadFile uploadFile = new UploadFile();
|
||||
uploadFile.setChunkNumber(UploadFileDto.getChunkNumber());
|
||||
uploadFile.setChunkSize(UploadFileDto.getChunkSize());
|
||||
@ -54,13 +65,18 @@ public class FiletransferService implements IFiletransferService {
|
||||
uploadFile.setIdentifier(UploadFileDto.getIdentifier());
|
||||
uploadFile.setTotalSize(UploadFileDto.getTotalSize());
|
||||
uploadFile.setCurrentChunkSize(UploadFileDto.getCurrentChunkSize());
|
||||
if (oss.isEnabled()) {
|
||||
uploader = new AliyunOSSUploaderFactory().getUploader(uploadFile);
|
||||
} else {
|
||||
uploader = new ChunkUploaderFactory().getUploader(uploadFile);
|
||||
synchronized (FiletransferService.class) {
|
||||
String storageType = qiwenFileConfig.getStorageType();
|
||||
if ("0".equals(storageType)) {
|
||||
uploader = localStorageOperationFactory.getUploader();
|
||||
} else if ("1".equals(storageType)) {
|
||||
uploader = aliyunOSSOperationFactory.getUploader();
|
||||
} else if ("2".equals(storageType)) {
|
||||
uploader = fastDFSOperationFactory.getUploader();
|
||||
}
|
||||
}
|
||||
|
||||
List<UploadFile> uploadFileList = uploader.upload(request);
|
||||
List<UploadFile> uploadFileList = uploader.upload(request, uploadFile);
|
||||
for (int i = 0; i < uploadFileList.size(); i++){
|
||||
uploadFile = uploadFileList.get(i);
|
||||
FileBean fileBean = new FileBean();
|
||||
@ -71,7 +87,7 @@ public class FiletransferService implements IFiletransferService {
|
||||
fileBean.setFileSize(uploadFile.getFileSize());
|
||||
//fileBean.setUploadTime(DateUtil.getCurrentTime());
|
||||
fileBean.setIsOSS(uploadFile.getIsOSS());
|
||||
|
||||
fileBean.setStorageType(uploadFile.getStorageType());
|
||||
fileBean.setPointCount(1);
|
||||
fileMapper.insert(fileBean);
|
||||
UserFile userFile = new UserFile();
|
||||
@ -103,6 +119,55 @@ public class FiletransferService implements IFiletransferService {
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void downloadFile(HttpServletResponse httpServletResponse, DownloadFileDTO downloadFileDTO) {
|
||||
UserFile userFile = userFileMapper.selectById(downloadFileDTO.getUserFileId());
|
||||
|
||||
String fileName = userFile.getFileName() + "." + userFile.getExtendName();
|
||||
try {
|
||||
fileName = new String(fileName.getBytes("utf-8"), "ISO-8859-1");
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
httpServletResponse.setContentType("application/force-download");// 设置强制下载不打开
|
||||
httpServletResponse.addHeader("Content-Disposition", "attachment;fileName=" + fileName);// 设置文件名
|
||||
|
||||
|
||||
FileBean fileBean = fileMapper.selectById(userFile.getFileId());
|
||||
Downloader downloader = null;
|
||||
if (fileBean.getIsOSS() != null && fileBean.getIsOSS() == 1) {
|
||||
downloader = aliyunOSSOperationFactory.getDownloader();
|
||||
} else if (fileBean.getStorageType() == 0) {
|
||||
downloader = localStorageOperationFactory.getDownloader();
|
||||
} else if (fileBean.getStorageType() == 1) {
|
||||
downloader = aliyunOSSOperationFactory.getDownloader();
|
||||
} else if (fileBean.getStorageType() == 2) {
|
||||
downloader = fastDFSOperationFactory.getDownloader();
|
||||
}
|
||||
DownloadFile uploadFile = new DownloadFile();
|
||||
uploadFile.setFileUrl(fileBean.getFileUrl());
|
||||
uploadFile.setTimeStampName(fileBean.getTimeStampName());
|
||||
downloader.download(httpServletResponse, uploadFile);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deleteFile(FileBean fileBean) {
|
||||
Deleter deleter = null;
|
||||
if (fileBean.getIsOSS() != null && fileBean.getIsOSS() == 1) {
|
||||
deleter = aliyunOSSOperationFactory.getDeleter();
|
||||
} else if (fileBean.getStorageType() == 0) {
|
||||
deleter = localStorageOperationFactory.getDeleter();
|
||||
} else if (fileBean.getStorageType() == 1) {
|
||||
deleter = aliyunOSSOperationFactory.getDeleter();
|
||||
} else if (fileBean.getStorageType() == 2) {
|
||||
deleter = fastDFSOperationFactory.getDeleter();
|
||||
}
|
||||
DeleteFile deleteFile = new DeleteFile();
|
||||
deleteFile.setFileUrl(fileBean.getFileUrl());
|
||||
deleteFile.setTimeStampName(fileBean.getTimeStampName());
|
||||
deleter.delete(deleteFile);
|
||||
}
|
||||
|
||||
@Override
|
||||
public StorageBean selectStorageBean(StorageBean storageBean) {
|
||||
LambdaQueryWrapper<StorageBean> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
|
@ -1,13 +1,14 @@
|
||||
package com.qiwenshare.file.service;
|
||||
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.util.PathUtil;
|
||||
import com.qiwenshare.file.api.IRecoveryFileService;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.domain.RecoveryFile;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
import com.qiwenshare.file.domain.UserFile;
|
||||
import com.qiwenshare.file.mapper.FileMapper;
|
||||
import com.qiwenshare.file.mapper.RecoveryFileMapper;
|
||||
@ -56,6 +57,67 @@ public class RecoveryFileService extends ServiceImpl<RecoveryFileMapper, Recove
|
||||
|
||||
|
||||
}
|
||||
|
||||
public void restorefile(String deleteBatchNum, String filePath, Long sessionUserId) {
|
||||
LambdaUpdateWrapper<UserFile> userFileLambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
userFileLambdaUpdateWrapper.set(UserFile::getDeleteFlag, 0)
|
||||
.set(UserFile::getDeleteBatchNum, "")
|
||||
.eq(UserFile::getDeleteBatchNum, deleteBatchNum);
|
||||
userFileMapper.update(null, userFileLambdaUpdateWrapper);
|
||||
|
||||
String parentFilePath = PathUtil.getParentPath(filePath);
|
||||
while(parentFilePath.indexOf("/") != -1) {
|
||||
String fileName = parentFilePath.substring(parentFilePath.lastIndexOf("/") + 1);
|
||||
parentFilePath = PathUtil.getParentPath(parentFilePath);
|
||||
LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
lambdaQueryWrapper.eq(UserFile::getFilePath, parentFilePath + "/")
|
||||
.eq(UserFile::getDeleteFlag, 0)
|
||||
.eq(UserFile::getUserId, sessionUserId);
|
||||
List<UserFile> userFileList = userFileMapper.selectList(lambdaQueryWrapper);
|
||||
if (userFileList.size() == 0) {
|
||||
UserFile userFile = new UserFile();
|
||||
userFile.setUserId(sessionUserId);
|
||||
userFile.setFileName(fileName);
|
||||
userFile.setFilePath(parentFilePath + "/");
|
||||
userFile.setDeleteFlag(0);
|
||||
userFile.setIsDir(1);
|
||||
userFile.setUploadTime(DateUtil.getCurrentTime());
|
||||
|
||||
userFileMapper.insert(userFile);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
|
||||
lambdaQueryWrapper.select(UserFile::getFileName, UserFile::getFilePath)
|
||||
.likeRight(UserFile::getFilePath, filePath)
|
||||
.eq(UserFile::getIsDir, 1)
|
||||
.eq(UserFile::getDeleteFlag, 0)
|
||||
.groupBy(UserFile::getFilePath, UserFile::getFileName)
|
||||
.having("count(fileName) >= 2");
|
||||
List<UserFile> repeatList = userFileMapper.selectList(lambdaQueryWrapper);
|
||||
|
||||
for (UserFile userFile : repeatList) {
|
||||
LambdaQueryWrapper<UserFile> lambdaQueryWrapper1 = new LambdaQueryWrapper<>();
|
||||
lambdaQueryWrapper1.eq(UserFile::getFilePath, userFile.getFilePath())
|
||||
.eq(UserFile::getFileName, userFile.getFileName())
|
||||
.eq(UserFile::getDeleteFlag, "0");
|
||||
List<UserFile> userFiles = userFileMapper.selectList(lambdaQueryWrapper1);
|
||||
log.info("重复的文件:" + JSON.toJSONString(userFiles));
|
||||
for (int i = 0; i < userFiles.size() - 1; i ++) {
|
||||
log.info("删除文件:" + JSON.toJSONString(userFiles.get(i)));
|
||||
userFileMapper.deleteById(userFiles.get(i).getUserFileId());
|
||||
}
|
||||
}
|
||||
|
||||
log.info(JSON.toJSONString(repeatList));
|
||||
|
||||
LambdaQueryWrapper<RecoveryFile> recoveryFileServiceLambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
recoveryFileServiceLambdaQueryWrapper.eq(RecoveryFile::getDeleteBatchNum, deleteBatchNum);
|
||||
recoveryFileMapper.delete(recoveryFileServiceLambdaQueryWrapper);
|
||||
}
|
||||
|
||||
|
||||
|
||||
private void updateFilePointCountByBatchNum(String deleteBatchNum) {
|
||||
|
@ -3,13 +3,14 @@ package com.qiwenshare.file.service;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.file.api.IUserFileService;
|
||||
import com.qiwenshare.file.config.QiwenFileConfig;
|
||||
import com.qiwenshare.common.config.QiwenFileConfig;
|
||||
import com.qiwenshare.file.domain.FileBean;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
import com.qiwenshare.file.domain.RecoveryFile;
|
||||
import com.qiwenshare.file.domain.UserFile;
|
||||
import com.qiwenshare.file.mapper.FileMapper;
|
||||
import com.qiwenshare.file.mapper.RecoveryFileMapper;
|
||||
import com.qiwenshare.file.mapper.UserFileMapper;
|
||||
import com.qiwenshare.file.vo.file.FileListVo;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
@ -17,7 +18,7 @@ import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.Executors;
|
||||
|
||||
@ -29,6 +30,8 @@ public class UserFileService extends ServiceImpl<UserFileMapper, UserFile> impl
|
||||
@Resource
|
||||
FileMapper fileMapper;
|
||||
@Resource
|
||||
RecoveryFileMapper recoveryFileMapper;
|
||||
@Resource
|
||||
FiletransferService filetransferService;
|
||||
@Resource
|
||||
QiwenFileConfig qiwenFileConfig;
|
||||
@ -56,7 +59,53 @@ public class UserFileService extends ServiceImpl<UserFileMapper, UserFile> impl
|
||||
return userFileMapper.userFileList(userFile, beginCount, pageCount);
|
||||
}
|
||||
|
||||
|
||||
// public void renameUserFile(Long userFileId, String newFileName, Long userId) {
|
||||
// UserFile userFile = userFileMapper.selectById(userFileId);
|
||||
// if (1 == userFile.getIsDir()) {
|
||||
// LambdaUpdateWrapper<UserFile> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
// lambdaUpdateWrapper.set(UserFile::getFileName, newFileName)
|
||||
// .set(UserFile::getUploadTime, DateUtil.getCurrentTime())
|
||||
// .eq(UserFile::getUserFileId, userFile.getUserFileId());
|
||||
// userFileMapper.update(null, lambdaUpdateWrapper);
|
||||
// replaceUserFilePath(userFile.getFilePath() + newFileName + "/",
|
||||
// userFile.getFilePath() + userFile.getFileName() + "/", userId);
|
||||
// } else {
|
||||
// FileBean fileBean = fileMapper.selectById(userFile.getFileId());
|
||||
// if (fileBean.getIsOSS() == 1) {
|
||||
//// LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
|
||||
//// lambdaQueryWrapper.eq(UserFile::getUserFileId, renameFileDto.getUserFileId());
|
||||
//// UserFile userFile = userFileService.getOne(lambdaQueryWrapper);
|
||||
////
|
||||
//// FileBean file = fileService.getById(userFile.getFileId());
|
||||
// String fileUrl = fileBean.getFileUrl();
|
||||
// String newFileUrl = fileUrl.replace(userFile.getFileName(), newFileName);
|
||||
//
|
||||
// AliyunOSSRename.rename(qiwenFileConfig.getAliyun().getOss(),
|
||||
// fileUrl.substring(1),
|
||||
// newFileUrl.substring(1));
|
||||
// LambdaUpdateWrapper<FileBean> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
// lambdaUpdateWrapper
|
||||
// .set(FileBean::getFileUrl, newFileUrl)
|
||||
// .eq(FileBean::getFileId, fileBean.getFileId());
|
||||
// fileMapper.update(null, lambdaUpdateWrapper);
|
||||
//
|
||||
// LambdaUpdateWrapper<UserFile> userFileLambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
// userFileLambdaUpdateWrapper
|
||||
// .set(UserFile::getFileName, newFileName)
|
||||
// .set(UserFile::getUploadTime, DateUtil.getCurrentTime())
|
||||
// .eq(UserFile::getUserFileId, userFileId);
|
||||
// userFileMapper.update(null, userFileLambdaUpdateWrapper);
|
||||
// } else {
|
||||
// LambdaUpdateWrapper<UserFile> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
// lambdaUpdateWrapper.set(UserFile::getFileName, newFileName)
|
||||
// .set(UserFile::getUploadTime, DateUtil.getCurrentTime())
|
||||
// .eq(UserFile::getUserFileId, userFileId);
|
||||
// userFileMapper.update(null, lambdaUpdateWrapper);
|
||||
// }
|
||||
//
|
||||
//
|
||||
// }
|
||||
// }
|
||||
|
||||
@Override
|
||||
public void updateFilepathByFilepath(String oldfilePath, String newfilePath, String fileName, String extendName) {
|
||||
@ -131,37 +180,43 @@ public class UserFileService extends ServiceImpl<UserFileMapper, UserFile> impl
|
||||
|
||||
|
||||
@Override
|
||||
public void deleteUserFile(UserFile userFile, UserBean sessionUserBean) {
|
||||
|
||||
public void deleteUserFile(Long userFileId, Long sessionUserId) {
|
||||
// UserFile userFile
|
||||
UserFile userFile = userFileMapper.selectById(userFileId);
|
||||
String uuid = UUID.randomUUID().toString();
|
||||
if (userFile.getIsDir() == 1) {
|
||||
LambdaUpdateWrapper<UserFile> userFileLambdaUpdateWrapper = new LambdaUpdateWrapper<UserFile>();
|
||||
userFileLambdaUpdateWrapper.set(UserFile::getDeleteFlag, 1)
|
||||
.set(UserFile::getDeleteBatchNum, userFile.getDeleteBatchNum())
|
||||
.set(UserFile::getDeleteBatchNum, uuid)
|
||||
.set(UserFile::getDeleteTime, DateUtil.getCurrentTime())
|
||||
.eq(UserFile::getUserFileId, userFile.getUserFileId());
|
||||
.eq(UserFile::getUserFileId, userFileId);
|
||||
userFileMapper.update(null, userFileLambdaUpdateWrapper);
|
||||
|
||||
String filePath = userFile.getFilePath() + userFile.getFileName() + "/";
|
||||
updateFileDeleteStateByFilePath(filePath, userFile.getDeleteBatchNum(), sessionUserBean.getUserId());
|
||||
updateFileDeleteStateByFilePath(filePath, userFile.getDeleteBatchNum(), sessionUserId);
|
||||
|
||||
}else{
|
||||
|
||||
UserFile userFileTemp = userFileMapper.selectById(userFile.getUserFileId());
|
||||
UserFile userFileTemp = userFileMapper.selectById(userFileId);
|
||||
FileBean fileBean = fileMapper.selectById(userFileTemp.getFileId());
|
||||
|
||||
LambdaUpdateWrapper<UserFile> userFileLambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
userFileLambdaUpdateWrapper.set(UserFile::getDeleteFlag, 1)
|
||||
.set(UserFile::getDeleteTime, DateUtil.getCurrentTime())
|
||||
.set(UserFile::getDeleteBatchNum, userFile.getDeleteBatchNum())
|
||||
.set(UserFile::getDeleteBatchNum, uuid)
|
||||
.eq(UserFile::getUserFileId, userFileTemp.getUserFileId());
|
||||
userFileMapper.update(null, userFileLambdaUpdateWrapper);
|
||||
|
||||
// LambdaUpdateWrapper<FileBean> fileBeanLambdaUpdateWrapper = new LambdaUpdateWrapper<>();
|
||||
// fileBeanLambdaUpdateWrapper.set(FileBean::getPointCount, fileBean.getPointCount() -1)
|
||||
// .eq(FileBean::getFileId, fileBean.getFileId());
|
||||
}
|
||||
|
||||
|
||||
RecoveryFile recoveryFile = new RecoveryFile();
|
||||
recoveryFile.setUserFileId(userFileId);
|
||||
recoveryFile.setDeleteTime(DateUtil.getCurrentTime());
|
||||
recoveryFile.setDeleteBatchNum(uuid);
|
||||
recoveryFileMapper.insert(recoveryFile);
|
||||
|
||||
|
||||
}
|
||||
|
||||
private void updateFileDeleteStateByFilePath(String filePath, String deleteBatchNum, Long userId) {
|
||||
|
@ -3,8 +3,8 @@ package com.qiwenshare.file.service;
|
||||
import com.alibaba.fastjson.JSON;
|
||||
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
|
||||
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.cbb.RestResult;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.common.result.RestResult;
|
||||
import com.qiwenshare.common.util.JjwtUtil;
|
||||
import com.qiwenshare.common.util.PasswordUtil;
|
||||
import com.qiwenshare.file.api.IUserService;
|
||||
@ -15,8 +15,6 @@ import io.jsonwebtoken.Claims;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.shiro.crypto.hash.SimpleHash;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.Resource;
|
||||
|
@ -1,10 +1,9 @@
|
||||
package com.qiwenshare.file.util;
|
||||
|
||||
import com.qiwenshare.common.cbb.CollectUtil;
|
||||
import com.qiwenshare.common.cbb.DateUtil;
|
||||
import com.qiwenshare.common.util.CollectUtil;
|
||||
import com.qiwenshare.common.util.DateUtil;
|
||||
import com.qiwenshare.file.domain.OperationLogBean;
|
||||
import com.qiwenshare.file.domain.UserBean;
|
||||
import org.apache.shiro.SecurityUtils;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
|
||||
|
@ -12,8 +12,11 @@ public class FileListVo {
|
||||
|
||||
private Long fileSize;
|
||||
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
|
||||
private Integer storageType;
|
||||
|
||||
private Integer pointCount;
|
||||
|
||||
private String identifier;
|
||||
|
@ -15,7 +15,10 @@ public class ShareFileListVO {
|
||||
@Schema(description="文件大小")
|
||||
private Long fileSize;
|
||||
@Schema(description="是否sso存储")
|
||||
@Deprecated
|
||||
private Integer isOSS;
|
||||
@Schema(description="存储类型")
|
||||
private Integer storageType;
|
||||
//
|
||||
// private Long userFileId;
|
||||
//
|
||||
|
@ -49,11 +49,13 @@ mybatis-plus.mapper-locations=classpath:mybatis/mapper/*.xml
|
||||
mybatis-plus.configuration.map-underscore-to-camel-case=false
|
||||
mybatis-plus.global-config.banner=false
|
||||
|
||||
qiwen-file.remote-login=false
|
||||
qiwen-file.share-mode=false
|
||||
|
||||
qiwen-file.storage-type=0
|
||||
qiwen-file.cache-mode=0
|
||||
|
||||
#是否启用阿里云oss
|
||||
qiwen-file.aliyun.oss.enabled=false
|
||||
#qiwen-file.aliyun.oss.enabled=false
|
||||
#阿里云oss基本配置
|
||||
qiwen-file.aliyun.oss.endpoint=
|
||||
qiwen-file.aliyun.oss.access-key-id=
|
||||
@ -62,3 +64,34 @@ qiwen-file.aliyun.oss.bucket-name=
|
||||
#阿里云oss绑定域名
|
||||
qiwen-file.aliyun.oss.domain=
|
||||
|
||||
|
||||
fdfs.so-timeout=1501
|
||||
fdfs.connect-timeout=601
|
||||
fdfs.thumb-image.width=150
|
||||
fdfs.thumb-image.height=150
|
||||
fdfs.tracker-list=121.89.222.103:22122
|
||||
|
||||
|
||||
# Redis数据库索引(默认为0)
|
||||
spring.redis.database=0
|
||||
# Redis服务器地址
|
||||
spring.redis.host=123.56.9.174
|
||||
# Redis服务器连接端口
|
||||
spring.redis.port=6379
|
||||
# Redis服务器连接密码(默认为空)
|
||||
spring.redis.password=ma123456
|
||||
# 连接池最大连接数(使用负值表示没有限制) 默认 8
|
||||
spring.redis.lettuce.pool.max-active=8
|
||||
# 连接池最大阻塞等待时间(使用负值表示没有限制) 默认 -1
|
||||
spring.redis.lettuce.pool.max-wait=10000
|
||||
# 连接池中的最大空闲连接 默认 8
|
||||
spring.redis.lettuce.pool.max-idle=30
|
||||
# 连接池中的最小空闲连接 默认 0
|
||||
spring.redis.lettuce.pool.min-idle=10
|
||||
#连接超时时间(毫秒)
|
||||
spring.redis.timeout=5000
|
||||
|
||||
|
||||
spring.data.elasticsearch.client.reactive.endpoints=127.0.0.1:9200
|
||||
spring.elasticsearch.rest.uris=127.0.0.1:9200
|
||||
|
||||
|
@ -30,9 +30,7 @@
|
||||
limit #{beginCount}, #{pageCount}
|
||||
|
||||
</select>
|
||||
|
||||
<select id="selectFileByExtendName" parameterType="com.qiwenshare.file.domain.UserFile" resultType="com.qiwenshare.file.vo.file.FileListVo">
|
||||
select * from userfile
|
||||
<sql id="selectByExtendName" >
|
||||
left join file on file.fileId = userfile.fileId
|
||||
where extendName in
|
||||
<foreach collection="fileNameList" open="(" close=")" separator="," item="fileName" >
|
||||
@ -40,41 +38,36 @@
|
||||
</foreach>
|
||||
and userId = #{userId}
|
||||
and deleteFlag = 0
|
||||
</sql>
|
||||
<sql id="selectByNotExtendName">
|
||||
left join file on file.fileId = userfile.fileId
|
||||
where extendName not in
|
||||
<foreach collection="fileNameList" open="(" close=")" separator="," item="fileName" >
|
||||
#{fileName}
|
||||
</foreach>
|
||||
and userId = #{userId}
|
||||
and deleteFlag = 0
|
||||
</sql>
|
||||
<select id="selectFileByExtendName" parameterType="com.qiwenshare.file.domain.UserFile" resultType="com.qiwenshare.file.vo.file.FileListVo">
|
||||
select * from userfile
|
||||
<include refid="selectByExtendName"></include>
|
||||
limit #{beginCount}, #{pageCount}
|
||||
</select>
|
||||
|
||||
<select id="selectCountByExtendName" parameterType="com.qiwenshare.file.domain.UserFile" resultType="java.lang.Long">
|
||||
select count(*) from userfile
|
||||
left join file on file.fileId = userfile.fileId
|
||||
where extendName in
|
||||
<foreach collection="fileNameList" open="(" close=")" separator="," item="fileName" >
|
||||
#{fileName}
|
||||
</foreach>
|
||||
and userId = #{userId}
|
||||
and deleteFlag = 0
|
||||
<include refid="selectByExtendName"></include>
|
||||
</select>
|
||||
|
||||
<select id="selectFileNotInExtendNames" parameterType="com.qiwenshare.file.domain.UserFile" resultType="com.qiwenshare.file.vo.file.FileListVo">
|
||||
select * from userfile
|
||||
left join file on file.fileId = userfile.fileId
|
||||
where extendName not in
|
||||
<foreach collection="fileNameList" open="(" close=")" separator="," item="fileName" >
|
||||
#{fileName}
|
||||
</foreach>
|
||||
and userId = #{userId}
|
||||
and deleteFlag = 0
|
||||
<include refid="selectByNotExtendName"></include>
|
||||
limit #{beginCount}, #{pageCount}
|
||||
</select>
|
||||
|
||||
<select id="selectCountNotInExtendNames" parameterType="com.qiwenshare.file.domain.UserFile" resultType="java.lang.Long">
|
||||
select count(*) from userfile
|
||||
left join file on file.fileId = userfile.fileId
|
||||
where extendName not in
|
||||
<foreach collection="fileNameList" open="(" close=")" separator="," item="fileName" >
|
||||
#{fileName}
|
||||
</foreach>
|
||||
and userId = #{userId}
|
||||
and deleteFlag = 0
|
||||
<include refid="selectByNotExtendName"></include>
|
||||
</select>
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user