Sfoglia il codice sorgente

1.将网盘系统成功移植进小诺中
2.将网盘的用户系统干掉,用户从小诺中查询
3.修复国密解密都mac电脑的bug

jasonk5949 8 mesi fa
parent
commit
1e05e544d3
100 ha cambiato i file con 5226 aggiunte e 0 eliminazioni
  1. 14 0
      pom.xml
  2. 7 0
      snowy-base/snowy-common/pom.xml
  3. 5 0
      snowy-modules/snowy-web-app/pom.xml
  4. 3 0
      snowy-plugin/pom.xml
  5. 25 0
      snowy-plugin/snowy-plugin-disk/pom.xml
  6. 1 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/README.md
  7. 24 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/pom.xml
  8. 13 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/src/main/java/vip/xiaonuo/disk/package-info.java
  9. 1 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/README.md
  10. 204 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/pom.xml
  11. 13 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/ICommonFileService.java
  12. 10 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IElasticSearchService.java
  13. 8 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFilePermissionService.java
  14. 16 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFileService.java
  15. 28 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFiletransferService.java
  16. 13 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/INoticeService.java
  17. 16 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IOperationLogService.java
  18. 14 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IRecoveryFileService.java
  19. 13 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IShareFileService.java
  20. 17 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IShareService.java
  21. 9 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IStorageService.java
  22. 14 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/ISysParamService.java
  23. 10 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUploadTaskDetailService.java
  24. 11 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUploadTaskService.java
  25. 26 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserFileService.java
  26. 8 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserLoginInfoService.java
  27. 37 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserService.java
  28. 196 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/AsyncTaskComp.java
  29. 561 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/FileDealComp.java
  30. 69 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/JwtComp.java
  31. 58 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/UserDealComp.java
  32. 20 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/es/ElasticSearchConfig.java
  33. 26 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/es/FileSearch.java
  34. 9 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtHeader.java
  35. 10 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtPayload.java
  36. 15 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtProperties.java
  37. 11 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/RegisterdClaims.java
  38. 85 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/onlyoffice/OnlyofficeConfiguration.java
  39. 85 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/AsyncThreadPoolAutoConfiguration.java
  40. 51 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/AsyncThreadPoolProperties.java
  41. 16 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/BaseAsyncUncaughtExceptionHandler.java
  42. 22 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/CommonFileTypeEnum.java
  43. 26 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/FileType.java
  44. 28 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/FileTypeEnum.java
  45. 113 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/CommonFileController.java
  46. 527 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/FileController.java
  47. 313 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/FiletransferController.java
  48. 64 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/NoticeController.java
  49. 252 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/OfficeController.java
  50. 109 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/RecoveryFileController.java
  51. 246 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/ShareController.java
  52. 47 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/SysParamController.java
  53. 85 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/TaskController.java
  54. 156 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/UserController.java
  55. 30 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/CommonFile.java
  56. 84 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileBean.java
  57. 30 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileClassification.java
  58. 30 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileExtend.java
  59. 33 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FilePermission.java
  60. 29 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileType.java
  61. 32 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Image.java
  62. 62 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Music.java
  63. 49 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Notice.java
  64. 85 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/OperationLogBean.java
  65. 60 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/PictureFile.java
  66. 29 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/RecoveryFile.java
  67. 35 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Share.java
  68. 27 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/ShareFile.java
  69. 49 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/StorageBean.java
  70. 28 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/SysParam.java
  71. 42 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UploadTask.java
  72. 42 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UploadTaskDetail.java
  73. 90 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UserFile.java
  74. 29 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UserLoginInfo.java
  75. 50 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/Permission.java
  76. 54 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/Role.java
  77. 29 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/RolePermission.java
  78. 85 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/UserBean.java
  79. 21 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/UserRole.java
  80. 19 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/commonfile/CommonFileDTO.java
  81. 16 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchDeleteFileDTO.java
  82. 16 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchDownloadFileDTO.java
  83. 15 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchMoveFileDTO.java
  84. 15 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CopyFileDTO.java
  85. 24 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateFileDTO.java
  86. 20 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateFoldDTO.java
  87. 10 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateOfficeFileDTO.java
  88. 13 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DeleteFileDTO.java
  89. 12 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DeleteRecoveryFileDTO.java
  90. 14 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DownloadFileDTO.java
  91. 12 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/EditOfficeFileDTO.java
  92. 15 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/FileListDTO.java
  93. 22 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/MoveFileDTO.java
  94. 15 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/OnlyofficeDTO.java
  95. 18 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/PreviewDTO.java
  96. 12 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/PreviewOfficeFileDTO.java
  97. 14 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/RenameFileDTO.java
  98. 14 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/SearchFileDTO.java
  99. 17 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/UnzipFileDTO.java
  100. 19 0
      snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/UpdateFileDTO.java

+ 14 - 0
pom.xml

@@ -332,6 +332,20 @@
                 <version>${snowy.version}</version>
             </dependency>
 
+            <!-- snowy-plugin-ten-api -->
+            <dependency>
+                <groupId>vip.xiaonuo</groupId>
+                <artifactId>snowy-plugin-disk-api</artifactId>
+                <version>${snowy.version}</version>
+            </dependency>
+
+            <!-- snowy-plugin-ten-func -->
+            <dependency>
+                <groupId>vip.xiaonuo</groupId>
+                <artifactId>snowy-plugin-disk-func</artifactId>
+                <version>${snowy.version}</version>
+            </dependency>
+
             <!-- snowy-plugin-urp-api -->
             <dependency>
                 <groupId>vip.xiaonuo</groupId>

+ 7 - 0
snowy-base/snowy-common/pom.xml

@@ -179,6 +179,13 @@
             <groupId>com.github.wnameless.json</groupId>
             <artifactId>json-flattener</artifactId>
         </dependency>
+
+        <dependency>
+            <groupId>org.openjdk.nashorn</groupId>
+            <artifactId>nashorn-core</artifactId>
+            <version>15.4</version>
+        </dependency>
+
     </dependencies>
 
 </project>

+ 5 - 0
snowy-modules/snowy-web-app/pom.xml

@@ -136,6 +136,11 @@
             <artifactId>snowy-plugin-ten-func</artifactId>
         </dependency>
 
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-disk-func</artifactId>
+        </dependency>
+
         <!-- bootstrap 配置加载 -->
         <dependency>
             <groupId>org.springframework.cloud</groupId>

+ 3 - 0
snowy-plugin/pom.xml

@@ -54,6 +54,9 @@
         <!-- 报表设计插件 -->
         <module>snowy-plugin-urp</module>
 
+        <module>snowy-plugin-disk</module>
+
+
         <!-- 考试系统插件 -->
         <module>snowy-plugin-exam</module>
     </modules>

+ 25 - 0
snowy-plugin/snowy-plugin-disk/pom.xml

@@ -0,0 +1,25 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>vip.xiaonuo</groupId>
+        <artifactId>snowy-plugin</artifactId>
+        <version>2.0.0</version>
+    </parent>
+
+    <artifactId>snowy-plugin-disk</artifactId>
+    <packaging>pom</packaging>
+    <description>资源功能插件</description>
+
+    <modules>
+        <!-- 资源功能插件api接口 -->
+        <module>snowy-plugin-disk-api</module>
+
+        <!-- 资源功能插件func实现 -->
+        <module>snowy-plugin-disk-func</module>
+    </modules>
+
+</project>

+ 1 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/README.md

@@ -0,0 +1 @@
+# 业务功能插件api接口

+ 24 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/pom.xml

@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>vip.xiaonuo</groupId>
+        <artifactId>snowy-plugin-disk</artifactId>
+        <version>2.0.0</version>
+    </parent>
+
+    <artifactId>snowy-plugin-disk-api</artifactId>
+    <packaging>jar</packaging>
+    <description>业务功能插件api接口</description>
+
+    <dependencies>
+        <!-- 每个插件接口都要引入common -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-common</artifactId>
+        </dependency>
+    </dependencies>
+</project>

+ 13 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-api/src/main/java/vip/xiaonuo/disk/package-info.java

@@ -0,0 +1,13 @@
+/*
+ * Copyright [2022] [https://www.xiaonuo.vip]
+ *
+ * Snowy采用APACHE LICENSE 2.0开源协议,您在使用过程中,需要注意以下几点:
+ *
+ * 1.请不要删除和修改根目录下的LICENSE文件。
+ * 2.请不要删除和修改Snowy源码头部的版权声明。
+ * 3.本项目代码可免费商业使用,商业使用请保留源码和相关描述文件的项目出处,作者声明等。
+ * 4.分发源码时候,请注明软件出处 https://www.xiaonuo.vip
+ * 5.不可二次分发开源参与同类竞品,如有想法可联系团队xiaonuobase@qq.com商议合作。
+ * 6.若您的项目无法满足以上几点,需要更多功能代码,获取Snowy商业授权许可,请在官网购买授权,地址为 https://www.xiaonuo.vip
+ */
+package vip.xiaonuo.disk;

+ 1 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/README.md

@@ -0,0 +1 @@
+# 业务功能插件func实现

+ 204 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/pom.xml

@@ -0,0 +1,204 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0"
+         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+         xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>vip.xiaonuo</groupId>
+        <artifactId>snowy-plugin-disk</artifactId>
+        <version>2.0.0</version>
+    </parent>
+
+    <artifactId>snowy-plugin-disk-func</artifactId>
+    <version>2.0.0</version>
+    <packaging>jar</packaging>
+    <description>业务功能插件func实现</description>
+    <name>qiwen-file</name>
+    <properties>
+        <java.version>1.8</java.version>
+        <spring-cloud.version>Hoxton.SR1</spring-cloud.version>
+        <skipTests>true</skipTests>
+        <docker.image.prefix>scp</docker.image.prefix>
+        <release-path>target/../release</release-path>
+        <app-name>${project.artifactId}-${project.version}</app-name>
+        <qiwenshare.version>1.2.8</qiwenshare.version>
+        <java.version>1.8</java.version>
+        <spring-cloud.version>Hoxton.SR9</spring-cloud.version>
+        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
+        <maven.compiler.encoding>UTF-8</maven.compiler.encoding>
+
+        <qiwenshare-common.version>${qiwenshare.version}</qiwenshare-common.version>
+        <ufop.version>${qiwenshare.version}</ufop.version>
+
+        <aliyun.sdk.oss.version>3.13.2</aliyun.sdk.oss.version>
+        <fastdfs-client.version>1.26.2</fastdfs-client.version>
+        <commons-fileupload.version>1.4</commons-fileupload.version>
+        <commons-io.version>2.11.0</commons-io.version>
+        <jjwt.version>0.9.1</jjwt.version>
+        <thumbnailator.version>0.4.16</thumbnailator.version>
+        <fastjson2.version>2.0.5.graal</fastjson2.version>
+        <swagger-annotations.version>2.1.4</swagger-annotations.version>
+        <mybatis-plus.version>3.5.2</mybatis-plus.version>
+        <poi-version>5.2.2</poi-version>
+        <xdocreport-version>2.0.2</xdocreport-version>
+        <pdf-box-version>3.0.0-RC1</pdf-box-version>
+        <javacpp.version>1.5.7</javacpp.version>
+        <javacv.version>1.5.7</javacv.version>
+        <ffmpeg.version>5.0-1.5.7</ffmpeg.version>
+        <minio.version>8.3.4</minio.version>
+        <qiniu.version>7.9.2</qiniu.version>
+        <hutool.version>5.8.16</hutool.version>
+        <springdoc-openapi.version>1.6.1</springdoc-openapi.version>
+        <okhttp.version>5.0.0-alpha.3</okhttp.version>
+        <aliyun-sdk.version>4.0.3</aliyun-sdk.version>
+        <sevenzipjbinding.version>16.02-2.01</sevenzipjbinding.version>
+        <jpinyin.version>1.1.8</jpinyin.version>
+        <jaudiotagger.version>2.0.1</jaudiotagger.version>
+        <htmlunit.version>2.62.0</htmlunit.version>
+    </properties>
+
+
+    <dependencies>
+        <!-- 每个插件都要引入自己的对外接口 -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-disk-api</artifactId>
+        </dependency>
+
+        <!-- 引入登录鉴权接口,用于获取登录用户 -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-auth-api</artifactId>
+        </dependency>
+
+        <!-- 引入系统接口,用于授权角色等功能 -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-sys-api</artifactId>
+        </dependency>
+
+        <!-- 引入开发工具接口,用于配置信息 -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-dev-api</artifactId>
+        </dependency>
+
+        <!-- 引入多数据源接口,用于提供数据源 -->
+        <dependency>
+            <groupId>vip.xiaonuo</groupId>
+            <artifactId>snowy-plugin-dbs-api</artifactId>
+        </dependency>
+
+        <dependency>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-web</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.commons</groupId>
+            <artifactId>commons-lang3</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.springdoc</groupId>
+            <artifactId>springdoc-openapi-ui</artifactId>
+            <version>${springdoc-openapi.version}</version>
+        </dependency>
+
+        <dependency>
+            <groupId>org.projectlombok</groupId>
+            <artifactId>lombok</artifactId>
+            <optional>true</optional>
+        </dependency>
+        <!-- fastjson  -->
+        <dependency>
+            <groupId>com.alibaba.fastjson2</groupId>
+            <artifactId>fastjson2</artifactId>
+            <version>${fastjson2.version}</version>
+        </dependency>
+
+        <!-- 导入Mysql数据库链接jar包-->
+        <dependency>
+            <groupId>mysql</groupId>
+            <artifactId>mysql-connector-java</artifactId>
+            <scope>runtime</scope>
+        </dependency>
+
+
+        <!--jpa-->
+        <dependency>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-data-jpa</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-aop</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.springframework.boot</groupId>
+            <artifactId>spring-boot-starter-test</artifactId>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>com.baomidou</groupId>
+            <artifactId>mybatis-plus-boot-starter</artifactId>
+        </dependency>
+        <!--mybatis end-->
+
+        <dependency>
+            <groupId>com.qiwenshare</groupId>
+            <artifactId>ufop-spring-boot-starter</artifactId>
+            <version>${ufop.version}</version>
+        </dependency>
+
+        <dependency>
+            <groupId>co.elastic.clients</groupId>
+            <artifactId>elasticsearch-java</artifactId>
+            <version>8.1.2</version>
+        </dependency>
+        <dependency>
+            <groupId>com.fasterxml.jackson.core</groupId>
+            <artifactId>jackson-databind</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>jakarta.json</groupId>
+            <artifactId>jakarta.json-api</artifactId>
+            <version>2.0.1</version>
+        </dependency>
+
+        <dependency>
+            <groupId>commons-io</groupId>
+            <artifactId>commons-io</artifactId>
+        </dependency>
+
+        <dependency>
+            <groupId>org</groupId>
+            <artifactId>jaudiotagger</artifactId>
+            <version>${jaudiotagger.version}</version>
+        </dependency>
+
+        <dependency>
+            <groupId>com.inversoft</groupId>
+            <artifactId>prime-jwt</artifactId>
+            <version>2.0.0</version>
+        </dependency>
+        <dependency>
+            <groupId>org.modelmapper</groupId>
+            <artifactId>modelmapper</artifactId>
+            <version>2.4.2</version>
+        </dependency>
+
+        <dependency>
+            <groupId>jakarta.json</groupId>
+            <artifactId>jakarta.json-api</artifactId>
+            <version>2.0.1</version>
+        </dependency>
+        <dependency>
+            <groupId>org.glassfish</groupId>
+            <artifactId>jakarta.json</artifactId>
+            <version>2.0.1</version>
+            <scope>runtime</scope>
+        </dependency>
+
+    </dependencies>
+</project>

+ 13 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/ICommonFileService.java

@@ -0,0 +1,13 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.CommonFile;
+import vip.xiaonuo.disk.vo.commonfile.CommonFileListVo;
+import vip.xiaonuo.disk.vo.commonfile.CommonFileUser;
+
+import java.util.List;
+
+public interface ICommonFileService extends IService<CommonFile> {
+    List<CommonFileUser> selectCommonFileUser(String userId);
+    List<CommonFileListVo> selectCommonFileByUser(String userId, String sessionUserId);
+}

+ 10 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IElasticSearchService.java

@@ -0,0 +1,10 @@
+//package vip.xiaonuo.disk.api;
+//
+//import vip.xiaonuo.disk.config.es.FileSearch;
+//import org.springframework.context.annotation.Lazy;
+//import org.springframework.data.elasticsearch.repository.ElasticsearchRepository;
+//
+//@Lazy
+//public interface IElasticSearchService extends ElasticsearchRepository<FileSearch,Long> {
+//
+//}

+ 8 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFilePermissionService.java

@@ -0,0 +1,8 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.FilePermission;
+
+public interface IFilePermissionService extends IService<FilePermission> {
+
+}

+ 16 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFileService.java

@@ -0,0 +1,16 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.vo.file.FileDetailVO;
+
+public interface IFileService  extends IService<FileBean> {
+
+    Long getFilePointCount(String fileId);
+    void unzipFile(String userFileId, int unzipMode, String filePath);
+
+    void updateFileDetail(String userFileId, String identifier, long fileSize);
+
+    FileDetailVO getFileDetail(String userFileId);
+
+}

+ 28 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IFiletransferService.java

@@ -0,0 +1,28 @@
+package vip.xiaonuo.disk.api;
+
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.dto.file.DownloadFileDTO;
+import vip.xiaonuo.disk.dto.file.PreviewDTO;
+import vip.xiaonuo.disk.dto.file.UploadFileDTO;
+import vip.xiaonuo.disk.vo.file.UploadFileVo;
+import com.qiwenshare.ufop.constant.StorageTypeEnum;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import java.util.List;
+
+public interface IFiletransferService {
+
+    UploadFileVo uploadFileSpeed(UploadFileDTO uploadFileDTO);
+
+    void uploadFile(HttpServletRequest request, UploadFileDTO UploadFileDto, String userId);
+
+    void downloadFile(HttpServletResponse httpServletResponse, DownloadFileDTO downloadFileDTO);
+    void downloadUserFileList(HttpServletResponse httpServletResponse, String filePath, String fileName, List<String> userFileIds);
+    void previewFile(HttpServletResponse httpServletResponse, PreviewDTO previewDTO);
+    void previewPictureFile(HttpServletResponse httpServletResponse, PreviewDTO previewDTO);
+    void deleteFile(FileBean fileBean);
+
+    Long selectStorageSizeByUserId(String userId);
+}

+ 13 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/INoticeService.java

@@ -0,0 +1,13 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.Notice;
+import vip.xiaonuo.disk.dto.notice.NoticeListDTO;
+
+public interface INoticeService extends IService<Notice> {
+
+
+    IPage<Notice> selectUserPage(NoticeListDTO noticeListDTO);
+
+}

+ 16 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IOperationLogService.java

@@ -0,0 +1,16 @@
+package vip.xiaonuo.disk.api;
+
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.OperationLogBean;
+
+import java.util.List;
+
+public interface IOperationLogService  extends IService<OperationLogBean> {
+    IPage<OperationLogBean> selectOperationLogPage(Integer current, Integer size);
+
+    List<OperationLogBean> selectOperationLog();
+
+    void insertOperationLog(OperationLogBean operationlogBean);
+}

+ 14 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IRecoveryFileService.java

@@ -0,0 +1,14 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.RecoveryFile;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.vo.file.RecoveryFileListVo;
+
+import java.util.List;
+
+public interface IRecoveryFileService extends IService<RecoveryFile> {
+    void deleteUserFileByDeleteBatchNum(String deleteBatchNum);
+    void restorefile(String deleteBatchNum, String filePath, String sessionUserId);
+    List<RecoveryFileListVo> selectRecoveryFileList(String userId);
+}

+ 13 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IShareFileService.java

@@ -0,0 +1,13 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.Share;
+import vip.xiaonuo.disk.domain.ShareFile;
+import vip.xiaonuo.disk.vo.share.ShareFileListVO;
+
+import java.util.List;
+
+public interface IShareFileService extends IService<ShareFile> {
+
+    List<ShareFileListVO> selectShareFileList(String shareBatchNum, String filePath);
+}

+ 17 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IShareService.java

@@ -0,0 +1,17 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.RecoveryFile;
+import vip.xiaonuo.disk.domain.Share;
+import vip.xiaonuo.disk.domain.ShareFile;
+import vip.xiaonuo.disk.dto.sharefile.ShareListDTO;
+import vip.xiaonuo.disk.vo.share.ShareFileListVO;
+import vip.xiaonuo.disk.vo.share.ShareListVO;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+
+public interface IShareService  extends IService<Share> {
+    List<ShareListVO> selectShareList(ShareListDTO shareListDTO, String userId);
+    int selectShareListTotalCount(ShareListDTO shareListDTO, String userId);
+}

+ 9 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IStorageService.java

@@ -0,0 +1,9 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.StorageBean;
+
+public interface IStorageService extends IService<StorageBean> {
+    Long getTotalStorageSize(String userId);
+    boolean checkStorage(String userId, Long fileSize);
+}

+ 14 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/ISysParamService.java

@@ -0,0 +1,14 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.SysParam;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/30 14:54
+ */
+public interface ISysParamService  extends IService<SysParam> {
+    String getValue(String key);
+}

+ 10 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUploadTaskDetailService.java

@@ -0,0 +1,10 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.UploadTaskDetail;
+
+import java.util.List;
+
+public interface IUploadTaskDetailService  extends IService<UploadTaskDetail> {
+    List<Integer> getUploadedChunkNumList(String identifier);
+}

+ 11 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUploadTaskService.java

@@ -0,0 +1,11 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.UploadTask;
+import vip.xiaonuo.disk.domain.UploadTaskDetail;
+
+import java.util.List;
+
+public interface IUploadTaskService extends IService<UploadTask> {
+
+}

+ 26 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserFileService.java

@@ -0,0 +1,26 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.vo.file.FileListVO;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+
+public interface IUserFileService extends IService<UserFile> {
+    List<UserFile> selectUserFileByNameAndPath(String fileName, String filePath, String userId);
+    List<UserFile> selectSameUserFile(String fileName, String filePath, String extendName, String userId);
+
+    IPage<FileListVO> userFileList(String userId, String filePath, Long beginCount, Long pageCount);
+    void updateFilepathByUserFileId(String userFileId, String newfilePath, String userId);
+    void userFileCopy(String userId, String userFileId, String newfilePath);
+
+    IPage<FileListVO> getFileByFileType(Integer fileTypeId, Long currentPage, Long pageCount, String userId);
+    List<UserFile> selectUserFileListByPath(String filePath, String userId);
+    List<UserFile> selectFilePathTreeByUserId(String userId);
+    void deleteUserFile(String userFileId, String sessionUserId);
+
+    List<UserFile> selectUserFileByLikeRightFilePath(@Param("filePath") String filePath, @Param("userId") String userId);
+
+}

+ 8 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserLoginInfoService.java

@@ -0,0 +1,8 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import vip.xiaonuo.disk.domain.UserLoginInfo;
+
+public interface IUserLoginInfoService extends IService<UserLoginInfo> {
+
+}

+ 37 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/api/IUserService.java

@@ -0,0 +1,37 @@
+package vip.xiaonuo.disk.api;
+
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.qiwenshare.common.result.RestResult;
+import vip.xiaonuo.disk.domain.user.Role;
+import vip.xiaonuo.disk.domain.user.UserBean;
+
+import java.util.List;
+
+public interface IUserService extends IService<UserBean> {
+
+
+    String getUserIdByToken(String token);
+
+
+    /**
+     * 用户注册
+     *
+     * @param userBean 用户信息
+     * @return 结果
+     */
+    RestResult<String> registerUser(UserBean userBean);
+
+
+
+    UserBean findUserInfoByTelephone(String telephone);
+    List<Role> selectRoleListByUserId(String userId);
+    String getSaltByTelephone(String telephone);
+    UserBean selectUserByTelephoneAndPassword(String username, String password);
+
+
+
+
+
+
+
+}

+ 196 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/AsyncTaskComp.java

@@ -0,0 +1,196 @@
+package vip.xiaonuo.disk.component;
+
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.mapper.FileMapper;
+import vip.xiaonuo.disk.mapper.UserFileMapper;
+import com.qiwenshare.ufop.factory.UFOPFactory;
+import com.qiwenshare.ufop.operation.copy.domain.CopyFile;
+import com.qiwenshare.ufop.util.UFOPUtils;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.codec.digest.DigestUtils;
+import org.apache.commons.io.FilenameUtils;
+import org.apache.commons.io.IOUtils;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.scheduling.annotation.Async;
+import org.springframework.scheduling.annotation.AsyncResult;
+import org.springframework.stereotype.Component;
+import vip.xiaonuo.disk.api.IFiletransferService;
+import vip.xiaonuo.disk.api.IRecoveryFileService;
+import vip.xiaonuo.disk.domain.UserFile;
+
+import javax.annotation.Resource;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.UUID;
+import java.util.concurrent.Future;
+
+/**
+ * 功能描述:异步任务业务类(@Async也可添加在方法上)
+ */
+@Slf4j
+@Component
+@Async("asyncTaskExecutor")
+public class AsyncTaskComp {
+
+    @Resource
+    IRecoveryFileService recoveryFileService;
+    @Resource
+    IFiletransferService filetransferService;
+    @Resource
+    UFOPFactory ufopFactory;
+    @Resource
+    UserFileMapper userFileMapper;
+    @Resource
+    FileMapper fileMapper;
+    @Resource
+    vip.xiaonuo.disk.component.FileDealComp fileDealComp;
+
+    @Value("${ufop.storage-type}")
+    private Integer storageType;
+
+    public Long getFilePointCount(String fileId) {
+        LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(UserFile::getFileId, fileId);
+        return userFileMapper.selectCount(lambdaQueryWrapper);
+    }
+
+    public Future<String> deleteUserFile(String userFileId) {
+        UserFile userFile = userFileMapper.selectById(userFileId);
+        if (userFile.getIsDir() == 1) {
+            LambdaQueryWrapper<UserFile> userFileLambdaQueryWrapper = new LambdaQueryWrapper<>();
+            userFileLambdaQueryWrapper.eq(UserFile::getDeleteBatchNum, userFile.getDeleteBatchNum());
+            List<UserFile> list = userFileMapper.selectList(userFileLambdaQueryWrapper);
+            recoveryFileService.deleteUserFileByDeleteBatchNum(userFile.getDeleteBatchNum());
+            for (UserFile userFileItem : list) {
+
+                Long filePointCount = getFilePointCount(userFileItem.getFileId());
+
+                if (filePointCount != null && filePointCount == 0 && userFileItem.getIsDir() == 0) {
+                    FileBean fileBean = fileMapper.selectById(userFileItem.getFileId());
+                    if (fileBean != null) {
+                        try {
+                            filetransferService.deleteFile(fileBean);
+                            fileMapper.deleteById(fileBean.getFileId());
+                        } catch (Exception e) {
+                            log.error("删除本地文件失败:" + JSON.toJSONString(fileBean));
+                        }
+                    }
+
+
+                }
+            }
+        } else {
+
+            recoveryFileService.deleteUserFileByDeleteBatchNum(userFile.getDeleteBatchNum());
+            Long filePointCount = getFilePointCount(userFile.getFileId());
+
+            if (filePointCount != null && filePointCount == 0 && userFile.getIsDir() == 0) {
+                FileBean fileBean = fileMapper.selectById(userFile.getFileId());
+                try {
+                    filetransferService.deleteFile(fileBean);
+                    fileMapper.deleteById(fileBean.getFileId());
+                } catch (Exception e) {
+                    log.error("删除本地文件失败:" + JSON.toJSONString(fileBean));
+                }
+            }
+        }
+
+        return new AsyncResult<>("deleteUserFile");
+    }
+
+    public Future<String> checkESUserFileId(String userFileId) {
+        UserFile userFile = userFileMapper.selectById(userFileId);
+        if (userFile == null) {
+            fileDealComp.deleteESByUserFileId(userFileId);
+        }
+        return new AsyncResult<>("checkUserFileId");
+    }
+
+
+    public Future<String> saveUnzipFile(UserFile userFile, FileBean fileBean, int unzipMode, String entryName, String filePath) {
+        String unzipUrl = UFOPUtils.getTempFile(fileBean.getFileUrl()).getAbsolutePath().replace("." + userFile.getExtendName(), "");
+        String totalFileUrl = unzipUrl + entryName;
+        File currentFile = new File(totalFileUrl);
+
+        String fileId = null;
+        if (!currentFile.isDirectory()) {
+
+            FileInputStream fis = null;
+            String md5Str = UUID.randomUUID().toString();
+            try {
+                fis = new FileInputStream(currentFile);
+                md5Str = DigestUtils.md5Hex(fis);
+            } catch (IOException e) {
+                e.printStackTrace();
+            } finally {
+                IOUtils.closeQuietly(fis);
+            }
+
+            FileInputStream fileInputStream = null;
+            try {
+                Map<String, Object> param = new HashMap<>();
+                param.put("identifier", md5Str);
+                List<FileBean> list = fileMapper.selectByMap(param);
+
+                if (list != null && !list.isEmpty()) { //文件已存在
+                    fileId = list.get(0).getFileId();
+                } else { //文件不存在
+                    fileInputStream = new FileInputStream(currentFile);
+                    CopyFile createFile = new CopyFile();
+                    createFile.setExtendName(FilenameUtils.getExtension(totalFileUrl));
+                    String saveFileUrl = ufopFactory.getCopier().copy(fileInputStream, createFile);
+
+                    FileBean tempFileBean = new FileBean(saveFileUrl, currentFile.length(), storageType, md5Str, userFile.getUserId());
+
+                    fileMapper.insert(tempFileBean);
+                    fileId = tempFileBean.getFileId();
+                }
+            } catch (IOException e) {
+                e.printStackTrace();
+            } finally {
+                IOUtils.closeQuietly(fileInputStream);
+                System.gc();
+                try {
+                    Thread.sleep(100);
+                } catch (InterruptedException e) {
+                    e.printStackTrace();
+                }
+                currentFile.delete();
+            }
+
+
+        }
+
+
+        QiwenFile qiwenFile = null;
+        if (unzipMode == 0) {
+            qiwenFile = new QiwenFile(userFile.getFilePath(), entryName, currentFile.isDirectory());
+        } else if (unzipMode == 1) {
+            qiwenFile = new QiwenFile(userFile.getFilePath() + "/" + userFile.getFileName(), entryName, currentFile.isDirectory());
+        } else if (unzipMode == 2) {
+            qiwenFile = new QiwenFile(filePath, entryName, currentFile.isDirectory());
+        }
+
+        UserFile saveUserFile = new UserFile(qiwenFile, userFile.getUserId(), fileId);
+        String fileName = fileDealComp.getRepeatFileName(saveUserFile, saveUserFile.getFilePath());
+
+        if (saveUserFile.getIsDir() == 1 && !fileName.equals(saveUserFile.getFileName())) {
+            //如果是目录,而且重复,什么也不做
+        } else {
+            saveUserFile.setFileName(fileName);
+            userFileMapper.insert(saveUserFile);
+        }
+        fileDealComp.restoreParentFilePath(qiwenFile, userFile.getUserId());
+
+        return new AsyncResult<>("saveUnzipFile");
+    }
+
+
+}

+ 561 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/FileDealComp.java

@@ -0,0 +1,561 @@
+package vip.xiaonuo.disk.component;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.util.IdUtil;
+import co.elastic.clients.elasticsearch.ElasticsearchClient;
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.common.util.MusicUtils;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IShareFileService;
+import vip.xiaonuo.disk.api.IShareService;
+import vip.xiaonuo.disk.api.IUserService;
+import vip.xiaonuo.disk.config.es.FileSearch;
+import vip.xiaonuo.disk.domain.*;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.mapper.FileMapper;
+import vip.xiaonuo.disk.mapper.MusicMapper;
+import vip.xiaonuo.disk.mapper.UserFileMapper;
+import vip.xiaonuo.disk.util.QiwenFileUtil;
+import vip.xiaonuo.disk.util.TreeNode;
+import com.qiwenshare.ufop.factory.UFOPFactory;
+import com.qiwenshare.ufop.operation.copy.Copier;
+import com.qiwenshare.ufop.operation.copy.domain.CopyFile;
+import com.qiwenshare.ufop.operation.download.Downloader;
+import com.qiwenshare.ufop.operation.download.domain.DownloadFile;
+import com.qiwenshare.ufop.operation.write.Writer;
+import com.qiwenshare.ufop.operation.write.domain.WriteFile;
+import com.qiwenshare.ufop.util.UFOPUtils;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.codec.digest.DigestUtils;
+import org.apache.commons.collections4.CollectionUtils;
+import org.apache.commons.io.IOUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.jaudiotagger.audio.AudioFile;
+import org.jaudiotagger.audio.AudioFileIO;
+import org.jaudiotagger.audio.AudioHeader;
+import org.jaudiotagger.audio.flac.FlacFileReader;
+import org.jaudiotagger.audio.mp3.MP3File;
+import org.jaudiotagger.tag.FieldKey;
+import org.jaudiotagger.tag.Tag;
+import org.jaudiotagger.tag.datatype.Artwork;
+import org.jaudiotagger.tag.id3.AbstractID3v2Frame;
+import org.jaudiotagger.tag.id3.AbstractID3v2Tag;
+import org.jaudiotagger.tag.id3.framebody.FrameBodyAPIC;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Component;
+
+import javax.annotation.Resource;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.*;
+import java.util.concurrent.Executor;
+import java.util.concurrent.Executors;
+
+/**
+ * 文件逻辑处理组件
+ */
+@Slf4j
+@Component
+public class FileDealComp {
+    @Resource
+    private UserFileMapper userFileMapper;
+    @Resource
+    private FileMapper fileMapper;
+    @Resource
+    private IUserService userService;
+    @Resource
+    private IShareService shareService;
+    @Resource
+    private IShareFileService shareFileService;
+    @Resource
+    private UFOPFactory ufopFactory;
+    @Resource
+    private MusicMapper musicMapper;
+    @Autowired
+    private ElasticsearchClient elasticsearchClient;
+
+    public static Executor exec = Executors.newFixedThreadPool(20);
+
+    /**
+     * 获取重复文件名
+     * <p>
+     * 场景1: 文件还原时,在 savefilePath 路径下,保存 测试.txt 文件重名,则会生成 测试(1).txt
+     * 场景2: 上传文件时,在 savefilePath 路径下,保存 测试.txt 文件重名,则会生成 测试(1).txt
+     *
+     * @param userFile
+     * @param savefilePath
+     * @return
+     */
+    public String getRepeatFileName(UserFile userFile, String savefilePath) {
+        String fileName = userFile.getFileName();
+        String extendName = userFile.getExtendName();
+
+        String userId = userFile.getUserId();
+        int isDir = userFile.getIsDir();
+        LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(UserFile::getFilePath, savefilePath)
+                .eq(UserFile::getDeleteFlag, 0)
+                .eq(UserFile::getUserId, userId)
+                .eq(UserFile::getFileName, fileName)
+                .eq(UserFile::getIsDir, isDir);
+        if (userFile.isFile()) {
+            lambdaQueryWrapper.eq(UserFile::getExtendName, extendName);
+        }
+        List<UserFile> list = userFileMapper.selectList(lambdaQueryWrapper);
+        if (CollectionUtils.isEmpty(list)) {
+            return fileName;
+        }
+
+        int i = 0;
+
+        while (!CollectionUtils.isEmpty(list)) {
+            i++;
+            LambdaQueryWrapper<UserFile> lambdaQueryWrapper1 = new LambdaQueryWrapper<>();
+            lambdaQueryWrapper1.eq(UserFile::getFilePath, savefilePath)
+                    .eq(UserFile::getDeleteFlag, 0)
+                    .eq(UserFile::getUserId, userId)
+                    .eq(UserFile::getFileName, fileName + "(" + i + ")")
+                    .eq(UserFile::getIsDir, isDir);
+            if (userFile.isFile()) {
+                lambdaQueryWrapper1.eq(UserFile::getExtendName, extendName);
+            }
+            list = userFileMapper.selectList(lambdaQueryWrapper1);
+
+        }
+
+        return fileName + "(" + i + ")";
+
+    }
+
+    /**
+     * 还原父文件路径
+     * <p>
+     * 1、回收站文件还原操作会将文件恢复到原来的路径下,当还原文件的时候,如果父目录已经不存在了,则需要把父母录给还原
+     * 2、上传目录
+     *
+     * @param sessionUserId
+     */
+    public void restoreParentFilePath(QiwenFile qiwenFile, String sessionUserId) {
+
+        if (qiwenFile.isFile()) {
+            qiwenFile = qiwenFile.getParentFile();
+        }
+        while (qiwenFile.getParent() != null) {
+            String fileName = qiwenFile.getName();
+            String parentFilePath = qiwenFile.getParent();
+
+            LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+            lambdaQueryWrapper.eq(UserFile::getFilePath, parentFilePath)
+                    .eq(UserFile::getFileName, fileName)
+                    .eq(UserFile::getDeleteFlag, 0)
+                    .eq(UserFile::getIsDir, 1)
+                    .eq(UserFile::getUserId, sessionUserId);
+            List<UserFile> userFileList = userFileMapper.selectList(lambdaQueryWrapper);
+            if (userFileList.size() == 0) {
+                UserFile userFile = QiwenFileUtil.getQiwenDir(sessionUserId, parentFilePath, fileName);
+                try {
+                    userFileMapper.insert(userFile);
+                } catch (Exception e) {
+                    //ignore
+                }
+            }
+            qiwenFile = new QiwenFile(parentFilePath, true);
+        }
+    }
+
+
+    /**
+     * 删除重复的子目录文件
+     * <p>
+     * 当还原目录的时候,如果其子目录在文件系统中已存在,则还原之后进行去重操作
+     *
+     * @param filePath
+     * @param sessionUserId
+     */
+    public void deleteRepeatSubDirFile(String filePath, String sessionUserId) {
+        log.debug("删除子目录:" + filePath);
+        LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+
+        lambdaQueryWrapper.select(UserFile::getFileName, UserFile::getFilePath)
+                .likeRight(UserFile::getFilePath, QiwenFileUtil.formatLikePath(filePath))
+                .eq(UserFile::getIsDir, 1)
+                .eq(UserFile::getDeleteFlag, 0)
+                .eq(UserFile::getUserId, sessionUserId)
+                .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);
+            for (int i = 0; i < userFiles.size() - 1; i++) {
+                userFileMapper.deleteById(userFiles.get(i).getUserFileId());
+            }
+        }
+    }
+
+    /**
+     * 组织一个树目录节点,文件移动的时候使用
+     *
+     * @param treeNode
+     * @param id
+     * @param filePath
+     * @param nodeNameQueue
+     * @return
+     */
+    public TreeNode insertTreeNode(TreeNode treeNode, long id, String filePath, Queue<String> nodeNameQueue) {
+
+        List<TreeNode> childrenTreeNodes = treeNode.getChildren();
+        String currentNodeName = nodeNameQueue.peek();
+        if (currentNodeName == null) {
+            return treeNode;
+        }
+
+        QiwenFile qiwenFile = new QiwenFile(filePath, currentNodeName, true);
+        filePath = qiwenFile.getPath();
+
+        if (!isExistPath(childrenTreeNodes, currentNodeName)) {  //1、判断有没有该子节点,如果没有则插入
+            //插入
+            TreeNode resultTreeNode = new TreeNode();
+
+            resultTreeNode.setFilePath(filePath);
+            resultTreeNode.setLabel(nodeNameQueue.poll());
+            resultTreeNode.setId(++id);
+
+            childrenTreeNodes.add(resultTreeNode);
+
+        } else {  //2、如果有,则跳过
+            nodeNameQueue.poll();
+        }
+
+        if (nodeNameQueue.size() != 0) {
+            for (int i = 0; i < childrenTreeNodes.size(); i++) {
+
+                TreeNode childrenTreeNode = childrenTreeNodes.get(i);
+                if (currentNodeName.equals(childrenTreeNode.getLabel())) {
+                    childrenTreeNode = insertTreeNode(childrenTreeNode, id * 10, filePath, nodeNameQueue);
+                    childrenTreeNodes.remove(i);
+                    childrenTreeNodes.add(childrenTreeNode);
+                    treeNode.setChildren(childrenTreeNodes);
+                }
+
+            }
+        } else {
+            treeNode.setChildren(childrenTreeNodes);
+        }
+
+        return treeNode;
+
+    }
+
+    /**
+     * 判断该路径在树节点中是否已经存在
+     *
+     * @param childrenTreeNodes
+     * @param path
+     * @return
+     */
+    public boolean isExistPath(List<TreeNode> childrenTreeNodes, String path) {
+        boolean isExistPath = false;
+
+        try {
+            for (TreeNode childrenTreeNode : childrenTreeNodes) {
+                if (path.equals(childrenTreeNode.getLabel())) {
+                    isExistPath = true;
+                }
+            }
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+
+
+        return isExistPath;
+    }
+
+
+    public void uploadESByUserFileId(String userFileId) {
+        exec.execute(()->{
+            try {
+
+                Map<String, Object> param = new HashMap<>();
+                param.put("userFileId", userFileId);
+                List<UserFile> userfileResult = userFileMapper.selectByMap(param);
+                if (userfileResult != null && userfileResult.size() > 0) {
+                    FileSearch fileSearch = new FileSearch();
+                    BeanUtil.copyProperties(userfileResult.get(0), fileSearch);
+                /*if (fileSearch.getIsDir() == 0) {
+
+                    Reader reader = ufopFactory.getReader(fileSearch.getStorageType());
+                    ReadFile readFile = new ReadFile();
+                    readFile.setFileUrl(fileSearch.getFileUrl());
+                    String content = reader.read(readFile);
+                    //全文搜索
+                    fileSearch.setContent(content);
+
+                }*/
+                    elasticsearchClient.index(i -> i.index("filesearch").id(fileSearch.getUserFileId()).document(fileSearch));
+                }
+            } catch (Exception e) {
+                log.debug("ES更新操作失败,请检查配置");
+            }
+        });
+
+
+    }
+
+    public void deleteESByUserFileId(String userFileId) {
+        exec.execute(() -> {
+            try {
+                elasticsearchClient.delete(d -> d
+                        .index("filesearch")
+                        .id(userFileId));
+            } catch (Exception e) {
+                log.debug("ES删除操作失败,请检查配置");
+            }
+        });
+
+
+    }
+
+    /**
+     * 根据用户传入的参数,判断是否有下载或者预览权限
+     *
+     * @return
+     */
+    public boolean checkAuthDownloadAndPreview(String shareBatchNum,
+                                               String extractionCode,
+                                               String token,
+                                               String userFileIds,
+                                               Integer platform) {
+        log.debug("权限检查开始:shareBatchNum:{}, extractionCode:{}, token:{}, userFileIds{}", shareBatchNum, extractionCode, token, userFileIds);
+        if (platform != null && platform == 2) {
+            return true;
+        }
+        String[] userFileIdArr = userFileIds.split(",");
+        for (String userFileId : userFileIdArr) {
+
+            UserFile userFile = userFileMapper.selectById(userFileId);
+            log.debug(JSON.toJSONString(userFile));
+            if ("undefined".equals(shareBatchNum) || StringUtils.isEmpty(shareBatchNum)) {
+
+//                String userId = userService.getUserIdByToken(token);
+                String userId = StpLoginUserUtil.getLoginUser().getId();
+                log.debug(JSON.toJSONString("当前登录session用户id:" + userId));
+                if (userId == null) {
+                    return false;
+                }
+                log.debug("文件所属用户id:" + userFile.getUserId());
+                log.debug("登录用户id:" + userId);
+                if (!userFile.getUserId().equals(userId)) {
+                    log.info("用户id不一致,权限校验失败");
+                    return false;
+                }
+            } else {
+                Map<String, Object> param = new HashMap<>();
+                param.put("shareBatchNum", shareBatchNum);
+                List<Share> shareList = shareService.listByMap(param);
+                //判断批次号
+                if (shareList.size() <= 0) {
+                    log.info("分享批次号不存在,权限校验失败");
+                    return false;
+                }
+                Integer shareType = shareList.get(0).getShareType();
+                if (1 == shareType) {
+                    //判断提取码
+                    if (!shareList.get(0).getExtractionCode().equals(extractionCode)) {
+                        log.info("提取码错误,权限校验失败");
+                        return false;
+                    }
+                }
+                param.put("userFileId", userFileId);
+                List<ShareFile> shareFileList = shareFileService.listByMap(param);
+                if (shareFileList.size() <= 0) {
+                    log.info("用户id和分享批次号不匹配,权限校验失败");
+                    return false;
+                }
+
+            }
+
+        }
+        return true;
+    }
+
+    /**
+     * 拷贝文件
+     * 场景:修改的文件被多处引用时,需要重新拷贝一份,然后在新的基础上修改
+     *
+     * @param fileBean
+     * @param userFile
+     * @return
+     */
+    public String copyFile(FileBean fileBean, UserFile userFile) {
+        Copier copier = ufopFactory.getCopier();
+        Downloader downloader = ufopFactory.getDownloader(fileBean.getStorageType());
+        DownloadFile downloadFile = new DownloadFile();
+        downloadFile.setFileUrl(fileBean.getFileUrl());
+        CopyFile copyFile = new CopyFile();
+        copyFile.setExtendName(userFile.getExtendName());
+        String fileUrl = copier.copy(downloader.getInputStream(downloadFile), copyFile);
+        if (downloadFile.getOssClient() != null) {
+            downloadFile.getOssClient().shutdown();
+        }
+        fileBean.setFileUrl(fileUrl);
+        fileBean.setFileId(IdUtil.getSnowflakeNextIdStr());
+        fileMapper.insert(fileBean);
+        userFile.setFileId(fileBean.getFileId());
+        userFile.setUploadTime(DateUtil.getCurrentTime());
+        userFile.setModifyTime(DateUtil.getCurrentTime());
+        userFile.setModifyUserId(SessionUtil.getUserId());
+        userFileMapper.updateById(userFile);
+        return fileUrl;
+    }
+
+    public String getIdentifierByFile(String fileUrl, int storageType) throws IOException {
+        DownloadFile downloadFile = new DownloadFile();
+        downloadFile.setFileUrl(fileUrl);
+        InputStream inputStream = ufopFactory.getDownloader(storageType).getInputStream(downloadFile);
+        return DigestUtils.md5Hex(inputStream);
+    }
+
+    public void saveFileInputStream(int storageType, String fileUrl, InputStream inputStream) throws IOException {
+        Writer writer1 = ufopFactory.getWriter(storageType);
+        WriteFile writeFile = new WriteFile();
+        writeFile.setFileUrl(fileUrl);
+        int fileSize = inputStream.available();
+        writeFile.setFileSize(fileSize);
+        writer1.write(inputStream, writeFile);
+    }
+
+    public boolean isDirExist(String fileName, String filePath, String userId) {
+        LambdaQueryWrapper<UserFile> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(UserFile::getFileName, fileName)
+                .eq(UserFile::getFilePath, QiwenFile.formatPath(filePath))
+                .eq(UserFile::getUserId, userId)
+                .eq(UserFile::getDeleteFlag, 0)
+                .eq(UserFile::getIsDir, 1);
+        List<UserFile> list = userFileMapper.selectList(lambdaQueryWrapper);
+        if (list != null && !list.isEmpty()) {
+            return true;
+        }
+        return false;
+    }
+
+
+    public void parseMusicFile(String extendName, int storageType, String fileUrl, String fileId) {
+        File outFile = null;
+        InputStream inputStream = null;
+        FileOutputStream fileOutputStream = null;
+        try {
+            if ("mp3".equalsIgnoreCase(extendName) || "flac".equalsIgnoreCase(extendName)) {
+                Downloader downloader = ufopFactory.getDownloader(storageType);
+                DownloadFile downloadFile = new DownloadFile();
+                downloadFile.setFileUrl(fileUrl);
+                inputStream = downloader.getInputStream(downloadFile);
+                outFile = UFOPUtils.getTempFile(fileUrl);
+                if (!outFile.exists()) {
+                    outFile.createNewFile();
+                }
+                fileOutputStream = new FileOutputStream(outFile);
+                IOUtils.copy(inputStream, fileOutputStream);
+                Music music = new Music();
+                music.setMusicId(IdUtil.getSnowflakeNextIdStr());
+                music.setFileId(fileId);
+
+                Tag tag = null;
+                AudioHeader audioHeader = null;
+                if ("mp3".equalsIgnoreCase(extendName)) {
+                    MP3File f = (MP3File) AudioFileIO.read(outFile);
+                    tag = f.getTag();
+                    audioHeader = f.getAudioHeader();
+                    MP3File mp3file = new MP3File(outFile);
+                    if (mp3file.hasID3v2Tag()) {
+                        AbstractID3v2Tag id3v2Tag = mp3file.getID3v2TagAsv24();
+                        AbstractID3v2Frame frame = (AbstractID3v2Frame) id3v2Tag.getFrame("APIC");
+                        FrameBodyAPIC body;
+                        if (frame != null && !frame.isEmpty()) {
+                            body = (FrameBodyAPIC) frame.getBody();
+                            byte[] imageData = body.getImageData();
+                            music.setAlbumImage(Base64.getEncoder().encodeToString(imageData));
+                        }
+                        if (tag != null) {
+                            music.setArtist(tag.getFirst(FieldKey.ARTIST));
+                            music.setTitle(tag.getFirst(FieldKey.TITLE));
+                            music.setAlbum(tag.getFirst(FieldKey.ALBUM));
+                            music.setYear(tag.getFirst(FieldKey.YEAR));
+                            try {
+                                music.setTrack(tag.getFirst(FieldKey.TRACK));
+                            } catch (Exception e) {
+                                // ignore
+                            }
+
+                            music.setGenre(tag.getFirst(FieldKey.GENRE));
+                            music.setComment(tag.getFirst(FieldKey.COMMENT));
+                            music.setLyrics(tag.getFirst(FieldKey.LYRICS));
+                            music.setComposer(tag.getFirst(FieldKey.COMPOSER));
+                            music.setAlbumArtist(tag.getFirst(FieldKey.ALBUM_ARTIST));
+                            music.setEncoder(tag.getFirst(FieldKey.ENCODER));
+                        }
+                    }
+                } else if ("flac".equalsIgnoreCase(extendName)) {
+                    AudioFile f = new FlacFileReader().read(outFile);
+                    tag = f.getTag();
+                    audioHeader = f.getAudioHeader();
+                    if (tag != null) {
+                        music.setArtist(StringUtils.join(tag.getFields(FieldKey.ARTIST), ","));
+                        music.setTitle(StringUtils.join(tag.getFields(FieldKey.TITLE), ","));
+                        music.setAlbum(StringUtils.join(tag.getFields(FieldKey.ALBUM), ","));
+                        music.setYear(StringUtils.join(tag.getFields(FieldKey.YEAR), ","));
+                        music.setTrack(StringUtils.join(tag.getFields(FieldKey.TRACK), ","));
+                        music.setGenre(StringUtils.join(tag.getFields(FieldKey.GENRE), ","));
+                        music.setComment(StringUtils.join(tag.getFields(FieldKey.COMMENT), ","));
+                        music.setLyrics(StringUtils.join(tag.getFields(FieldKey.LYRICS), ","));
+                        music.setComposer(StringUtils.join(tag.getFields(FieldKey.COMPOSER), ","));
+                        music.setAlbumArtist(StringUtils.join(tag.getFields(FieldKey.ALBUM_ARTIST), ","));
+                        music.setEncoder(StringUtils.join(tag.getFields(FieldKey.ENCODER), ","));
+                        List<Artwork> artworkList = tag.getArtworkList();
+                        if (artworkList != null && !artworkList.isEmpty()) {
+                            Artwork artwork = artworkList.get(0);
+                            byte[] binaryData = artwork.getBinaryData();
+                            music.setAlbumImage(Base64.getEncoder().encodeToString(binaryData));
+                        }
+                    }
+
+                }
+
+                if (audioHeader != null) {
+                    music.setTrackLength(Float.parseFloat(audioHeader.getTrackLength() + ""));
+                }
+
+                if (StringUtils.isEmpty(music.getLyrics())) {
+                    try {
+
+                        String lyc = MusicUtils.getLyc(music.getArtist(), music.getTitle(), music.getAlbum());
+                        music.setLyrics(lyc);
+                    } catch (Exception e) {
+                        log.info(e.getMessage());
+                    }
+                }
+                musicMapper.insert(music);
+            }
+        } catch (Exception e) {
+            log.error("解析音乐信息失败!", e);
+        } finally {
+            IOUtils.closeQuietly(inputStream);
+            IOUtils.closeQuietly(fileOutputStream);
+            if (outFile != null) {
+                if (outFile.exists()) {
+                    outFile.delete();
+                }
+            }
+        }
+    }
+
+}

+ 69 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/JwtComp.java

@@ -0,0 +1,69 @@
+package vip.xiaonuo.disk.component;
+
+import com.alibaba.fastjson2.JSON;
+import com.qiwenshare.common.util.math.CalculatorUtils;
+import vip.xiaonuo.disk.config.jwt.JwtProperties;
+import io.jsonwebtoken.Claims;
+import io.jsonwebtoken.JwtBuilder;
+import io.jsonwebtoken.Jwts;
+import io.jsonwebtoken.SignatureAlgorithm;
+import io.jsonwebtoken.impl.DefaultClaims;
+import org.apache.commons.codec.binary.Base64;
+import org.springframework.stereotype.Component;
+
+import javax.annotation.Resource;
+import javax.crypto.SecretKey;
+import javax.crypto.spec.SecretKeySpec;
+import java.util.Date;
+import java.util.Map;
+
+@Component
+public class JwtComp {
+
+	@Resource
+	JwtProperties jwtProperties;
+
+
+	// 由字符串生成加密key
+	private SecretKey generalKey() {
+		// 本地的密码解码
+		byte[] encodedKey = Base64.decodeBase64(jwtProperties.getSecret());
+		// 根据给定的字节数组使用AES加密算法构造一个密钥
+        return new SecretKeySpec(encodedKey, 0, encodedKey.length, "AES");
+	}
+
+	// 创建jwt
+	public String createJWT(Map<String, Object> param) {
+		String subject = JSON.toJSONString(param);
+		// 生成JWT的时间
+		long nowTime = System.currentTimeMillis();
+		Date nowDate = new Date(nowTime);
+		// 生成签名的时候使用的秘钥secret,切记这个秘钥不能外露,是你服务端的私钥,在任何场景都不应该流露出去,一旦客户端得知这个secret,那就意味着客户端是可以自我签发jwt的
+		SecretKey key = generalKey();
+		Double expireTime = CalculatorUtils.conversion(jwtProperties.getPayload().getRegisterdClaims().getExp());
+
+		// 为payload添加各种标准声明和私有声明
+		DefaultClaims defaultClaims = new DefaultClaims();
+		defaultClaims.setIssuer(jwtProperties.getPayload().getRegisterdClaims().getIss());
+		defaultClaims.setExpiration(new Date(System.currentTimeMillis() + expireTime.longValue()));
+		defaultClaims.setSubject(subject);
+		defaultClaims.setAudience(jwtProperties.getPayload().getRegisterdClaims().getAud());
+
+		JwtBuilder builder = Jwts.builder() // 表示new一个JwtBuilder,设置jwt的body
+				.setClaims(defaultClaims)
+				.setIssuedAt(nowDate) // iat(issuedAt):jwt的签发时间
+				.signWith(SignatureAlgorithm.forName(jwtProperties.getHeader().getAlg()), key); // 设置签名,使用的是签名算法和签名使用的秘钥
+
+		return builder.compact();
+	}
+
+	// 解密jwt
+	public Claims parseJWT(String jwt) throws Exception {
+		SecretKey key = generalKey(); // 签名秘钥,和生成的签名的秘钥一模一样
+        return Jwts.parser() // 得到DefaultJwtParser
+                .setSigningKey(key) // 设置签名的秘钥
+                .parseClaimsJws(jwt).getBody();
+	}
+
+
+}

+ 58 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/component/UserDealComp.java

@@ -0,0 +1,58 @@
+package vip.xiaonuo.disk.component;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.qiwenshare.common.constant.RegexConstant;
+import vip.xiaonuo.disk.domain.user.UserBean;
+import vip.xiaonuo.disk.mapper.UserMapper;
+import org.springframework.stereotype.Component;
+
+import javax.annotation.Resource;
+import java.util.List;
+import java.util.regex.Pattern;
+
+@Component
+public class UserDealComp {
+    @Resource
+    UserMapper userMapper;
+
+
+    /**
+     * 检测用户名是否存在
+     *
+     * @param userBean
+     */
+    public Boolean isUserNameExit(UserBean userBean) {
+        LambdaQueryWrapper<UserBean> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(UserBean::getUsername, userBean.getUsername());
+        List<UserBean> list = userMapper.selectList(lambdaQueryWrapper);
+        if (list != null && !list.isEmpty()) {
+            return true;
+        } else {
+            return false;
+        }
+    }
+
+    /**
+     * 检测手机号是否存在
+     *
+     * @param userBean
+     * @return
+     */
+    public Boolean isPhoneExit(UserBean userBean) {
+
+        LambdaQueryWrapper<UserBean> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(UserBean::getTelephone, userBean.getTelephone());
+        List<UserBean> list = userMapper.selectList(lambdaQueryWrapper);
+        if (list != null && !list.isEmpty()) {
+            return true;
+        } else {
+            return false;
+        }
+
+    }
+
+    public Boolean isPhoneFormatRight(String phone){
+        boolean isRight = Pattern.matches(RegexConstant.PASSWORD_REGEX, phone);
+        return isRight;
+    }
+}

+ 20 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/es/ElasticSearchConfig.java

@@ -0,0 +1,20 @@
+package vip.xiaonuo.disk.config.es;
+
+import co.elastic.clients.elasticsearch.ElasticsearchClient;
+import co.elastic.clients.json.jackson.JacksonJsonpMapper;
+import co.elastic.clients.transport.ElasticsearchTransport;
+import co.elastic.clients.transport.rest_client.RestClientTransport;
+import org.apache.http.HttpHost;
+import org.elasticsearch.client.RestClient;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+@Configuration
+public class ElasticSearchConfig {
+    @Bean
+    public ElasticsearchClient elasticsearchClient(){
+        RestClient client = RestClient.builder(new HttpHost("localhost", 9200,"http")).build();
+        ElasticsearchTransport transport = new RestClientTransport(client,new JacksonJsonpMapper());
+        return new ElasticsearchClient(transport);
+    }
+}

+ 26 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/es/FileSearch.java

@@ -0,0 +1,26 @@
+package vip.xiaonuo.disk.config.es;
+
+import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
+import lombok.Data;
+
+@Data
+@JsonIgnoreProperties(ignoreUnknown = true)
+public class FileSearch {
+    private String indexName;
+    private String userFileId;
+    private String fileId;
+    private String fileName;
+    private String content;
+    private String fileUrl;
+    private Long fileSize;
+    private Integer storageType;
+    private String identifier;
+    private Long userId;
+    private String filePath;
+    private String extendName;
+    private Integer isDir;
+    private String uploadTime;
+    private Integer deleteFlag;
+    private String deleteTime;
+    private String deleteBatchNum;
+}

+ 9 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtHeader.java

@@ -0,0 +1,9 @@
+package vip.xiaonuo.disk.config.jwt;
+
+import lombok.Data;
+
+@Data
+public class JwtHeader {
+    private String alg;
+    private String typ;
+}

+ 10 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtPayload.java

@@ -0,0 +1,10 @@
+package vip.xiaonuo.disk.config.jwt;
+
+import lombok.Data;
+
+@Data
+public class JwtPayload {
+    private RegisterdClaims registerdClaims;
+
+}
+

+ 15 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/JwtProperties.java

@@ -0,0 +1,15 @@
+package vip.xiaonuo.disk.config.jwt;
+
+import lombok.Data;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.stereotype.Component;
+
+@Data
+@Component
+@ConfigurationProperties(prefix = "jwt")
+public class JwtProperties {
+    private String secret;
+    private JwtHeader header;
+    private JwtPayload payload;
+}
+

+ 11 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/jwt/RegisterdClaims.java

@@ -0,0 +1,11 @@
+package vip.xiaonuo.disk.config.jwt;
+
+import lombok.Data;
+
+@Data
+public class RegisterdClaims {
+    private String iss;
+    private String exp;
+    private String sub;
+    private String aud;
+}

+ 85 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/onlyoffice/OnlyofficeConfiguration.java

@@ -0,0 +1,85 @@
+/**
+ *
+ * (c) Copyright Ascensio System SIA 2021
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package vip.xiaonuo.disk.config.onlyoffice;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+import vip.xiaonuo.disk.office.documentserver.storage.FileStoragePathBuilder;
+import vip.xiaonuo.disk.office.documentserver.util.SSLUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.modelmapper.ModelMapper;
+import org.modelmapper.convention.MatchingStrategies;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Configuration;
+
+import javax.annotation.PostConstruct;
+
+@Configuration
+public class OnlyofficeConfiguration {
+
+    @Value("${files.storage}")
+    private String storageAddress;
+
+    @Value("${files.docservice.verify-peer-off}")
+    private String verifyPerrOff;
+
+    @Autowired
+    private FileStoragePathBuilder storagePathBuilder;
+
+    @Autowired
+    private SSLUtils ssl;
+
+    @Bean
+    public ModelMapper mapper(){  // create the model mapper
+        ModelMapper mapper = new ModelMapper();
+        mapper.getConfiguration()  // get the mapper configuration and set new parameters to it
+                .setMatchingStrategy(MatchingStrategies.STRICT)  // specify the STRICT matching strategy
+                .setFieldMatchingEnabled(true)  // define if the field matching is enabled or not
+                .setSkipNullEnabled(true)  // define if null value will be skipped or not
+                .setFieldAccessLevel(org.modelmapper.config.Configuration.AccessLevel.PRIVATE);  // specify the PRIVATE field access level
+        return mapper;
+    }
+
+//    @Bean
+//    public JSONParser jsonParser(){  // create JSON parser
+//        return new JSONParser();
+//    }
+
+    @PostConstruct
+    public void init(){  // initialize the storage path builder
+        storagePathBuilder.configure(StringUtils.isEmpty(storageAddress) ? null : storageAddress);
+        if(!verifyPerrOff.isEmpty()) {
+            try{
+                if(verifyPerrOff.equals("true")) {
+                    ssl.turnOffSslChecking(); //the certificate will be ignored
+                } else {
+                    ssl.turnOnSslChecking(); //the certificate will be verified
+                }
+            } catch(Exception e) {
+                e.printStackTrace();
+            }
+        }
+    }
+
+    @Bean
+    public ObjectMapper objectMapper(){  // create the object mapper
+        return new ObjectMapper();
+    }
+}

+ 85 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/AsyncThreadPoolAutoConfiguration.java

@@ -0,0 +1,85 @@
+package vip.xiaonuo.disk.config.threadpool;
+
+
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.boot.context.properties.EnableConfigurationProperties;
+import org.springframework.context.annotation.Bean;
+import org.springframework.scheduling.annotation.AsyncConfigurer;
+import org.springframework.scheduling.annotation.EnableAsync;
+import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
+import org.springframework.stereotype.Component;
+
+import java.util.Objects;
+import java.util.concurrent.Executor;
+import java.util.concurrent.ThreadPoolExecutor;
+
+/**
+ * 异步线程池配置 AsyncConfigurer在applicationContext早期初始化,如果需要依赖于其它的bean,尽可能的将它们声明为lazy
+ */
+@Slf4j
+@EnableAsync
+@Component
+@EnableConfigurationProperties(AsyncThreadPoolProperties.class)
+public class AsyncThreadPoolAutoConfiguration implements AsyncConfigurer {
+
+    @Autowired
+    private AsyncThreadPoolProperties asyncThreadPoolProperties;
+
+    /**
+     * 定义线程池
+     * 使用{@link java.util.concurrent.LinkedBlockingQueue}(FIFO)队列,是一个用于并发环境下的阻塞队列集合类
+     * ThreadPoolTaskExecutor不是完全被IOC容器管理的bean,可以在方法上加上@Bean注解交给容器管理,这样可以将taskExecutor.initialize()方法调用去掉,容器会自动调用
+     *
+     * @return
+     */
+    @Bean("asyncTaskExecutor")
+    @Override
+    public Executor getAsyncExecutor() {
+        //Java虚拟机可用的处理器数
+        int processors = Runtime.getRuntime().availableProcessors();
+        //定义线程池
+        ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor();
+        //核心线程数
+        taskExecutor.setCorePoolSize(Objects.nonNull(asyncThreadPoolProperties.getCorePoolSize()) ? asyncThreadPoolProperties.getCorePoolSize() : processors);
+        //线程池最大线程数,默认:40000
+        taskExecutor.setMaxPoolSize(Objects.nonNull(asyncThreadPoolProperties.getMaxPoolSize()) ? asyncThreadPoolProperties.getMaxPoolSize() : 40000);
+        //线程队列最大线程数,默认:80000
+        taskExecutor.setQueueCapacity(Objects.nonNull(asyncThreadPoolProperties.getMaxPoolSize()) ? asyncThreadPoolProperties.getMaxPoolSize() : 80000);
+        //线程名称前缀
+        taskExecutor.setThreadNamePrefix(StringUtils.isNotEmpty(asyncThreadPoolProperties.getThreadNamePrefix()) ? asyncThreadPoolProperties.getThreadNamePrefix() : "Async-ThreadPool-");
+        //线程池中线程最大空闲时间,默认:60,单位:秒
+        taskExecutor.setKeepAliveSeconds(asyncThreadPoolProperties.getKeepAliveSeconds());
+        //核心线程是否允许超时,默认:false
+        taskExecutor.setAllowCoreThreadTimeOut(asyncThreadPoolProperties.isAllowCoreThreadTimeOut());
+        //IOC容器关闭时是否阻塞等待剩余的任务执行完成,默认:false(必须设置setAwaitTerminationSeconds)
+        taskExecutor.setWaitForTasksToCompleteOnShutdown(asyncThreadPoolProperties.isWaitForTasksToCompleteOnShutdown());
+        //阻塞IOC容器关闭的时间,默认:10秒(必须设置setWaitForTasksToCompleteOnShutdown)
+        taskExecutor.setAwaitTerminationSeconds(asyncThreadPoolProperties.getAwaitTerminationSeconds());
+        /**
+         * 拒绝策略,默认是AbortPolicy
+         * AbortPolicy:丢弃任务并抛出RejectedExecutionException异常
+         * DiscardPolicy:丢弃任务但不抛出异常
+         * DiscardOldestPolicy:丢弃最旧的处理程序,然后重试,如果执行器关闭,这时丢弃任务
+         * CallerRunsPolicy:执行器执行任务失败,则在策略回调方法中执行任务,如果执行器关闭,这时丢弃任务
+         */
+        taskExecutor.setRejectedExecutionHandler(new ThreadPoolExecutor.AbortPolicy());
+        //初始化
+        //taskExecutor.initialize();
+
+        return taskExecutor;
+    }
+
+    /**
+     * 异步方法执行的过程中抛出的异常捕获
+     *
+     * @return AsyncUncaughtExceptionHandler
+     */
+    @Override
+    public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() {
+        return new BaseAsyncUncaughtExceptionHandler();
+    }
+}
+

+ 51 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/AsyncThreadPoolProperties.java

@@ -0,0 +1,51 @@
+package vip.xiaonuo.disk.config.threadpool;
+
+import lombok.Data;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+
+/**
+ * 异步线程池配置文件
+ */
+@Data
+@ConfigurationProperties(prefix = "spring.async-thread-pool")
+public class AsyncThreadPoolProperties  {
+    /**
+     * 是否启动异步线程池,默认 false
+     */
+    private boolean enable;
+    /**
+     * 核心线程数,默认:Java虚拟机可用线程数
+     */
+    private Integer corePoolSize=8;
+    /**
+     * 线程池最大线程数,默认:40000
+     */
+    private Integer maxPoolSize=500;
+    /**
+     * 线程队列最大线程数,默认:80000
+     */
+    private Integer queueCapacity = 5;
+
+    /**
+     * 线程池中线程最大空闲时间,默认:60,单位:秒
+     */
+    private Integer keepAliveSeconds = 600;
+    /**
+     * 自定义线程名前缀,默认:Async-ThreadPool-
+     */
+    private String threadNamePrefix = "async-threadpool-";
+    /**
+     * 核心线程是否允许超时,默认false
+     */
+    private boolean allowCoreThreadTimeOut;
+    /**
+     * IOC容器关闭时是否阻塞等待剩余的任务执行完成,默认:false(必须设置setAwaitTerminationSeconds)
+     */
+    private boolean waitForTasksToCompleteOnShutdown;
+    /**
+     * 阻塞IOC容器关闭的时间,默认:10秒(必须设置setWaitForTasksToCompleteOnShutdown)
+     */
+    private int awaitTerminationSeconds = 10;
+
+}
+

+ 16 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/config/threadpool/BaseAsyncUncaughtExceptionHandler.java

@@ -0,0 +1,16 @@
+package vip.xiaonuo.disk.config.threadpool;
+
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.aop.interceptor.AsyncUncaughtExceptionHandler;
+
+import java.lang.reflect.Method;
+import java.util.Arrays;
+
+@Slf4j
+public class BaseAsyncUncaughtExceptionHandler implements AsyncUncaughtExceptionHandler {
+    @Override
+    public void handleUncaughtException(Throwable throwable, Method method, Object... objects) {
+        log.error("捕获线程异常method[{}] params{}", method, Arrays.toString(objects));
+        log.error("线程异常");
+    }
+}

+ 22 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/CommonFileTypeEnum.java

@@ -0,0 +1,22 @@
+package vip.xiaonuo.disk.constant;
+
+public enum CommonFileTypeEnum {
+    EVERYONE(0, "所有人"),
+    PERSONAL(1, "个人");
+
+
+    private int type;
+    private String desc;
+    CommonFileTypeEnum(int type, String desc) {
+        this.type = type;
+        this.desc = desc;
+    }
+
+    public int getType() {
+        return type;
+    }
+
+    public String getDesc() {
+        return desc;
+    }
+}

+ 26 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/FileType.java

@@ -0,0 +1,26 @@
+/**
+ *
+ * (c) Copyright Ascensio System SIA 2021
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+package vip.xiaonuo.disk.constant;
+
+public enum FileType
+{
+    Word,
+    Cell,
+    Slide
+}

+ 28 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/constant/FileTypeEnum.java

@@ -0,0 +1,28 @@
+package vip.xiaonuo.disk.constant;
+
+public enum FileTypeEnum {
+    TOTAL(0, "全部"),
+    PICTURE(1, "图片"),
+    DOCUMENT(2, "文档"),
+    VIDEO(3, "视频"),
+    MUSIC(4, "音乐"),
+    OTHER(5, "其他"),
+    SHARE(6, "分享"),
+    RECYCLE(7, "回收站");
+
+
+    private int type;
+    private String desc;
+    FileTypeEnum(int type, String desc) {
+        this.type = type;
+        this.desc = desc;
+    }
+
+    public int getType() {
+        return type;
+    }
+
+    public String getDesc() {
+        return desc;
+    }
+}

+ 113 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/CommonFileController.java

@@ -0,0 +1,113 @@
+package vip.xiaonuo.disk.controller;
+
+import cn.hutool.core.util.IdUtil;
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.ICommonFileService;
+import vip.xiaonuo.disk.api.IFilePermissionService;
+import vip.xiaonuo.disk.api.IUserFileService;
+import vip.xiaonuo.disk.domain.CommonFile;
+import vip.xiaonuo.disk.domain.FilePermission;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.dto.commonfile.CommonFileDTO;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.vo.commonfile.CommonFileListVo;
+import vip.xiaonuo.disk.vo.commonfile.CommonFileUser;
+import vip.xiaonuo.disk.vo.file.FileListVO;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import java.util.ArrayList;
+import java.util.List;
+
+@Tag(name = "common", description = "该接口为文件共享接口")
+@RestController
+@Slf4j
+@RequestMapping("/common")
+public class CommonFileController {
+
+    public static final String CURRENT_MODULE = "文件共享";
+
+    @Resource
+    ICommonFileService commonFileService;
+    @Resource
+    IFilePermissionService filePermissionService;
+    @Resource
+    IUserFileService userFileService;
+
+    @Operation(summary = "将文件共享给他人", description = "共享文件统一接口", tags = {"common"})
+    @PostMapping(value = "/commonfile")
+    @MyLog(operation = "共享文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> commonFile( @RequestBody CommonFileDTO commonFileDTO) {
+        CommonFile commonFile = new CommonFile();
+        commonFile.setUserFileId(commonFileDTO.getUserFileId());
+        commonFile.setCommonFileId(IdUtil.getSnowflakeNextIdStr());
+
+        commonFileService.save(commonFile);
+
+        List<FilePermission> list = JSON.parseArray(commonFileDTO.getCommonUserList(), FilePermission.class);
+
+        List<FilePermission> filePermissionList = new ArrayList<>();
+       for (FilePermission filePermission : list) {
+           filePermission.setFilePermissionId(IdUtil.getSnowflakeNextId());
+            filePermission.setCommonFileId(commonFile.commonFileId);
+            filePermissionList.add(filePermission);
+       }
+        filePermissionService.saveBatch(filePermissionList);
+
+        return RestResult.success();
+    }
+
+    @Operation(summary = "获取共享空间的全量用户列表", description = "共享文件用户接口", tags = {"common"})
+    @GetMapping(value = "/commonfileuser")
+    @MyLog(operation = "共享文件用户", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<List<CommonFileUser>> commonFileUserList() {
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        List<CommonFileUser> list = commonFileService.selectCommonFileUser(userId);
+        return RestResult.success().data(list);
+    }
+
+    @Operation(summary = "获取共享用户文件列表", description = "用来做前台列表展示", tags = {"file"})
+    @RequestMapping(value = "/getCommonFileByUser", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<CommonFileListVo> getCommonFileByUser(
+            @Parameter(description = "用户id", required = true) String userId){
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        List<CommonFileListVo> commonFileVo = commonFileService.selectCommonFileByUser(userId, StpLoginUserUtil.getLoginUser().getId());
+
+        return RestResult.success().data(commonFileVo);
+
+    }
+
+    @Operation(summary = "获取共享空间中某个用户的文件列表", description = "用来做前台列表展示", tags = {"file"})
+    @RequestMapping(value = "/commonFileList", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<FileListVO> commonFileList(
+            @Parameter(description = "用户id", required = true) Long commonFileId,
+            @Parameter(description = "文件路径", required = true) String filePath,
+            @Parameter(description = "当前页", required = true) long currentPage,
+            @Parameter(description = "页面数量", required = true) long pageCount){
+
+        CommonFile commonFile = commonFileService.getById(commonFileId);
+        UserFile userFile = userFileService.getById(commonFile.getUserFileId());
+        QiwenFile qiwenFile = new QiwenFile(userFile.getFilePath(), filePath, true);
+        IPage<FileListVO> fileList = userFileService.userFileList(userFile.getUserId(), qiwenFile.getPath(), currentPage, pageCount);
+
+        return RestResult.success().data(fileList);
+
+    }
+
+}

+ 527 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/FileController.java

@@ -0,0 +1,527 @@
+package vip.xiaonuo.disk.controller;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.util.IdUtil;
+import co.elastic.clients.elasticsearch.ElasticsearchClient;
+import co.elastic.clients.elasticsearch.core.SearchResponse;
+import co.elastic.clients.elasticsearch.core.search.HighlighterEncoder;
+import co.elastic.clients.elasticsearch.core.search.Hit;
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
+import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.exception.QiwenException;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IFileService;
+import vip.xiaonuo.disk.api.IUserFileService;
+import vip.xiaonuo.disk.component.AsyncTaskComp;
+import vip.xiaonuo.disk.component.FileDealComp;
+import vip.xiaonuo.disk.config.es.FileSearch;
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.dto.file.*;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.util.QiwenFileUtil;
+import vip.xiaonuo.disk.util.TreeNode;
+import vip.xiaonuo.disk.vo.file.FileDetailVO;
+import vip.xiaonuo.disk.vo.file.FileListVO;
+import vip.xiaonuo.disk.vo.file.SearchFileVO;
+import com.qiwenshare.ufop.factory.UFOPFactory;
+import com.qiwenshare.ufop.operation.copy.Copier;
+import com.qiwenshare.ufop.operation.copy.domain.CopyFile;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.codec.digest.DigestUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.eclipse.jetty.util.StringUtil;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.util.ClassUtils;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+import java.io.ByteArrayInputStream;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.net.URLDecoder;
+import java.util.*;
+import java.util.concurrent.Executor;
+import java.util.concurrent.Executors;
+import java.util.regex.Pattern;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+
+@Tag(name = "file", description = "该接口为文件接口,主要用来做一些文件的基本操作,如创建目录,删除,移动,复制等。")
+@RestController
+@Slf4j
+@RequestMapping("/file")
+public class FileController {
+
+    @Resource
+    IFileService fileService;
+    @Resource
+    IUserFileService userFileService;
+    @Resource
+    UFOPFactory ufopFactory;
+    @Resource
+    FileDealComp fileDealComp;
+    @Resource
+    AsyncTaskComp asyncTaskComp;
+    @Autowired
+    private ElasticsearchClient elasticsearchClient;
+    @Value("${ufop.storage-type}")
+    private Integer storageType;
+
+    public static Executor executor = Executors.newFixedThreadPool(20);
+
+    public static final String CURRENT_MODULE = "文件接口";
+
+    @Operation(summary = "创建文件", description = "创建文件", tags = {"file"})
+    @ResponseBody
+    @RequestMapping(value = "/createFile", method = RequestMethod.POST)
+    public RestResult<Object> createFile(@Valid @RequestBody CreateFileDTO createFileDTO) {
+
+        try {
+
+            String userId = SessionUtil.getUserId();
+            String filePath = createFileDTO.getFilePath();
+            String fileName = createFileDTO.getFileName();
+            String extendName = createFileDTO.getExtendName();
+            List<UserFile> userFiles = userFileService.selectSameUserFile(fileName, filePath, extendName, userId);
+            if (userFiles != null && !userFiles.isEmpty()) {
+                return RestResult.fail().message("同名文件已存在");
+            }
+            String uuid = UUID.randomUUID().toString().replaceAll("-", "");
+
+            String templateFilePath = "";
+            if ("docx".equals(extendName)) {
+                templateFilePath = "template/Word.docx";
+            } else if ("xlsx".equals(extendName)) {
+                templateFilePath = "template/Excel.xlsx";
+            } else if ("pptx".equals(extendName)) {
+                templateFilePath = "template/PowerPoint.pptx";
+            } else if ("txt".equals(extendName)) {
+                templateFilePath = "template/Text.txt";
+            } else if ("drawio".equals(extendName)) {
+                templateFilePath = "template/Drawio.drawio";
+            }
+            String url2 = ClassUtils.getDefaultClassLoader().getResource("static/" + templateFilePath).getPath();
+            url2 = URLDecoder.decode(url2, "UTF-8");
+            FileInputStream fileInputStream = new FileInputStream(url2);
+            Copier copier = ufopFactory.getCopier();
+            CopyFile copyFile = new CopyFile();
+            copyFile.setExtendName(extendName);
+            String fileUrl = copier.copy(fileInputStream, copyFile);
+
+            FileBean fileBean = new FileBean();
+            fileBean.setFileId(IdUtil.getSnowflakeNextIdStr());
+            fileBean.setFileSize(0L);
+            fileBean.setFileUrl(fileUrl);
+            fileBean.setStorageType(storageType);
+            fileBean.setIdentifier(uuid);
+            fileBean.setCreateTime(DateUtil.getCurrentTime());
+            fileBean.setCreateUserId(StpLoginUserUtil.getLoginUser().getId());
+            fileBean.setFileStatus(1);
+            boolean saveFlag = fileService.save(fileBean);
+            UserFile userFile = new UserFile();
+            if (saveFlag) {
+                userFile.setUserFileId(IdUtil.getSnowflakeNextIdStr());
+                userFile.setUserId(userId);
+                userFile.setFileName(fileName);
+                userFile.setFilePath(filePath);
+                userFile.setDeleteFlag(0);
+                userFile.setIsDir(0);
+                userFile.setExtendName(extendName);
+                userFile.setUploadTime(DateUtil.getCurrentTime());
+                userFile.setFileId(fileBean.getFileId());
+                userFile.setCreateTime(DateUtil.getCurrentTime());
+                userFile.setCreateUserId(SessionUtil.getUserId());
+                userFileService.save(userFile);
+            }
+            return RestResult.success().message("文件创建成功");
+        } catch (Exception e) {
+            log.error(e.getMessage());
+            return RestResult.fail().message(e.getMessage());
+        }
+    }
+
+    @Operation(summary = "创建文件夹", description = "目录(文件夹)的创建", tags = {"file"})
+    @RequestMapping(value = "/createFold", method = RequestMethod.POST)
+    @MyLog(operation = "创建文件夹", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> createFold(@Valid @RequestBody CreateFoldDTO createFoldDto) {
+
+//        String userId = SessionUtil.getSession().getUserId();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        String filePath = createFoldDto.getFilePath();
+
+
+        boolean isDirExist = fileDealComp.isDirExist(createFoldDto.getFileName(), createFoldDto.getFilePath(), userId);
+
+        if (isDirExist) {
+            return RestResult.fail().message("同名文件夹已存在");
+        }
+
+        UserFile userFile = QiwenFileUtil.getQiwenDir(userId, filePath, createFoldDto.getFileName());
+
+        userFileService.save(userFile);
+        fileDealComp.uploadESByUserFileId(userFile.getUserFileId());
+        return RestResult.success();
+    }
+
+    @Operation(summary = "文件搜索", description = "文件搜索", tags = {"file"})
+    @GetMapping(value = "/search")
+    @MyLog(operation = "文件搜索", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<SearchFileVO> searchFile(SearchFileDTO searchFileDTO) {
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        int currentPage = (int)searchFileDTO.getCurrentPage() - 1;
+        int pageCount = (int)(searchFileDTO.getPageCount() == 0 ? 10 : searchFileDTO.getPageCount());
+
+        SearchResponse<FileSearch> search = null;
+        try {
+            search = elasticsearchClient.search(s -> s
+                            .index("filesearch")
+                            .query(_1 -> _1
+                                    .bool(_2 -> _2
+                                            .must(_3 -> _3
+                                                    .bool(_4 -> _4
+                                                            .should(_5 -> _5
+                                                                    .match(_6 -> _6
+                                                                            .field("fileName")
+                                                                            .query(searchFileDTO.getFileName())))
+                                                            .should(_5 -> _5
+                                                                    .wildcard(_6 -> _6
+                                                                            .field("fileName")
+                                                                            .wildcard("*" + searchFileDTO.getFileName() + "*")))
+                                                            .should(_5 -> _5
+                                                                    .match(_6 -> _6
+                                                                            .field("content")
+                                                                            .query(searchFileDTO.getFileName())))
+                                                            .should(_5 -> _5
+                                                                    .wildcard(_6 -> _6
+                                                                            .field("content")
+                                                                            .wildcard("*" + searchFileDTO.getFileName() + "*")))
+                                                    ))
+                                            .must(_3 -> _3
+                                                    .term(_4 -> _4
+                                                            .field("userId")
+                                                            .value(userId)))
+                                    ))
+                            .from(currentPage)
+                            .size(pageCount)
+                            .highlight(h -> h
+                                    .fields("fileName", f -> f.type("plain")
+                                            .preTags("<span class='keyword'>").postTags("</span>"))
+                                    .encoder(HighlighterEncoder.Html))
+                            ,
+                    FileSearch.class);
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+
+        List<SearchFileVO> searchFileVOList = new ArrayList<>();
+        for (Hit<FileSearch> hit : search.hits().hits()) {
+            SearchFileVO searchFileVO = new SearchFileVO();
+            BeanUtil.copyProperties(hit.source(), searchFileVO);
+            searchFileVO.setHighLight(hit.highlight());
+            searchFileVOList.add(searchFileVO);
+            asyncTaskComp.checkESUserFileId(searchFileVO.getUserFileId());
+        }
+        return RestResult.success().dataList(searchFileVOList, searchFileVOList.size());
+    }
+
+
+    @Operation(summary = "文件重命名", description = "文件重命名", tags = {"file"})
+    @RequestMapping(value = "/renamefile", method = RequestMethod.POST)
+    @MyLog(operation = "文件重命名", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> renameFile(@RequestBody RenameFileDTO renameFileDto) {
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        UserFile userFile = userFileService.getById(renameFileDto.getUserFileId());
+
+        List<UserFile> userFiles = userFileService.selectUserFileByNameAndPath(renameFileDto.getFileName(), userFile.getFilePath(), userId);
+        if (userFiles != null && !userFiles.isEmpty()) {
+            return RestResult.fail().message("同名文件已存在");
+        }
+
+        LambdaUpdateWrapper<UserFile> lambdaUpdateWrapper = new LambdaUpdateWrapper<>();
+        lambdaUpdateWrapper.set(UserFile::getFileName, renameFileDto.getFileName())
+                .set(UserFile::getUploadTime, DateUtil.getCurrentTime())
+                .eq(UserFile::getUserFileId, renameFileDto.getUserFileId());
+        userFileService.update(lambdaUpdateWrapper);
+        if (1 == userFile.getIsDir()) {
+            List<UserFile> list = userFileService.selectUserFileByLikeRightFilePath(new QiwenFile(userFile.getFilePath(), userFile.getFileName(), true).getPath(), userId);
+
+            for (UserFile newUserFile : list) {
+                String escapedPattern = Pattern.quote(new QiwenFile(userFile.getFilePath(), userFile.getFileName(), userFile.getIsDir() == 1).getPath());
+                newUserFile.setFilePath(newUserFile.getFilePath().replaceFirst(escapedPattern,
+                        new QiwenFile(userFile.getFilePath(), renameFileDto.getFileName(), userFile.getIsDir() == 1).getPath()));
+                userFileService.updateById(newUserFile);
+            }
+        }
+        fileDealComp.uploadESByUserFileId(renameFileDto.getUserFileId());
+        return RestResult.success();
+    }
+
+    @Operation(summary = "获取文件列表", description = "用来做前台列表展示", tags = {"file"})
+    @RequestMapping(value = "/getfilelist", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<FileListVO> getFileList(
+            @Parameter(description = "文件类型", required = true) String fileType,
+            @Parameter(description = "文件路径", required = true) String filePath,
+            @Parameter(description = "当前页", required = true) long currentPage,
+            @Parameter(description = "页面数量", required = true) long pageCount){
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        if ("0".equals(fileType)) {
+            IPage<FileListVO> fileList = userFileService.userFileList(null, filePath, currentPage, pageCount);
+            return RestResult.success().dataList(fileList.getRecords(), fileList.getTotal());
+        } else {
+            IPage<FileListVO> fileList = userFileService.getFileByFileType(Integer.valueOf(fileType), currentPage, pageCount, userId);
+            return RestResult.success().dataList(fileList.getRecords(), fileList.getTotal());
+        }
+    }
+
+
+    @Operation(summary = "批量删除文件", description = "批量删除文件", tags = {"file"})
+    @RequestMapping(value = "/batchdeletefile", method = RequestMethod.POST)
+    @MyLog(operation = "批量删除文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> deleteImageByIds(@RequestBody BatchDeleteFileDTO batchDeleteFileDto) {
+        String userFileIds = batchDeleteFileDto.getUserFileIds();
+        String[] userFileIdList = userFileIds.split(",");
+        userFileService.update(new UpdateWrapper<UserFile>().lambda().set(UserFile::getDeleteFlag, 1).in(UserFile::getUserFileId, Arrays.asList(userFileIdList)));
+        for (String userFileId : userFileIdList) {
+            executor.execute(()->{
+                    userFileService.deleteUserFile(userFileId, SessionUtil.getUserId());
+            });
+
+            fileDealComp.deleteESByUserFileId(userFileId);
+        }
+
+        return RestResult.success().message("批量删除文件成功");
+    }
+
+    @Operation(summary = "删除文件", description = "可以删除文件或者目录", tags = {"file"})
+    @RequestMapping(value = "/deletefile", method = RequestMethod.POST)
+    @MyLog(operation = "删除文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult deleteFile(@RequestBody DeleteFileDTO deleteFileDto) {
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        userFileService.deleteUserFile(deleteFileDto.getUserFileId(), userId);
+        fileDealComp.deleteESByUserFileId(deleteFileDto.getUserFileId());
+
+        return RestResult.success();
+
+    }
+
+    @Operation(summary = "解压文件", description = "解压文件。", tags = {"file"})
+    @RequestMapping(value = "/unzipfile", method = RequestMethod.POST)
+    @MyLog(operation = "解压文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> unzipFile(@RequestBody UnzipFileDTO unzipFileDto) {
+
+        try {
+            fileService.unzipFile(unzipFileDto.getUserFileId(), unzipFileDto.getUnzipMode(), unzipFileDto.getFilePath());
+        } catch (QiwenException e) {
+            return RestResult.fail().message(e.getMessage());
+        }
+
+        return RestResult.success();
+
+    }
+
+    @Operation(summary = "文件复制", description = "可以复制文件或者目录", tags = {"file"})
+    @RequestMapping(value = "/copyfile", method = RequestMethod.POST)
+    @MyLog(operation = "文件复制", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> copyFile(@RequestBody CopyFileDTO copyFileDTO) {
+        String userId = SessionUtil.getUserId();
+        String filePath = copyFileDTO.getFilePath();
+        String userFileIds = copyFileDTO.getUserFileIds();
+        String[] userFileIdArr = userFileIds.split(",");
+        for (String userFileId : userFileIdArr) {
+            UserFile userFile = userFileService.getById(userFileId);
+            String oldfilePath = userFile.getFilePath();
+            String fileName = userFile.getFileName();
+            if (userFile.isDirectory()) {
+                QiwenFile qiwenFile = new QiwenFile(oldfilePath, fileName, true);
+                if (filePath.startsWith(qiwenFile.getPath() + QiwenFile.separator) || filePath.equals(qiwenFile.getPath())) {
+                    return RestResult.fail().message("原路径与目标路径冲突,不能复制");
+                }
+            }
+
+            userFileService.userFileCopy(SessionUtil.getUserId(), userFileId, filePath);
+            fileDealComp.deleteRepeatSubDirFile(filePath, userId);
+        }
+
+        return RestResult.success();
+
+    }
+
+    @Operation(summary = "文件移动", description = "可以移动文件或者目录", tags = {"file"})
+    @RequestMapping(value = "/movefile", method = RequestMethod.POST)
+    @MyLog(operation = "文件移动", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> moveFile(@RequestBody MoveFileDTO moveFileDto) {
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        UserFile userFile = userFileService.getById(moveFileDto.getUserFileId());
+        String oldfilePath = userFile.getFilePath();
+        String newfilePath = moveFileDto.getFilePath();
+        String fileName = userFile.getFileName();
+        String extendName = userFile.getExtendName();
+        if (StringUtil.isEmpty(extendName)) {
+            QiwenFile qiwenFile = new QiwenFile(oldfilePath, fileName, true);
+            if (newfilePath.startsWith(qiwenFile.getPath() + QiwenFile.separator) || newfilePath.equals(qiwenFile.getPath())) {
+                return RestResult.fail().message("原路径与目标路径冲突,不能移动");
+            }
+        }
+
+        userFileService.updateFilepathByUserFileId(moveFileDto.getUserFileId(), newfilePath, userId);
+
+        fileDealComp.deleteRepeatSubDirFile(newfilePath, userId);
+        return RestResult.success();
+
+    }
+
+    @Operation(summary = "批量移动文件", description = "可以同时选择移动多个文件或者目录", tags = {"file"})
+    @RequestMapping(value = "/batchmovefile", method = RequestMethod.POST)
+    @MyLog(operation = "批量移动文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> batchMoveFile(@RequestBody BatchMoveFileDTO batchMoveFileDto) {
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        String newfilePath = batchMoveFileDto.getFilePath();
+
+        String userFileIds = batchMoveFileDto.getUserFileIds();
+        String[] userFileIdArr = userFileIds.split(",");
+
+        for (String userFileId : userFileIdArr) {
+            UserFile userFile = userFileService.getById(userFileId);
+            if (StringUtil.isEmpty(userFile.getExtendName())) {
+                QiwenFile qiwenFile = new QiwenFile(userFile.getFilePath(), userFile.getFileName(), true);
+                if (newfilePath.startsWith(qiwenFile.getPath() + QiwenFile.separator) || newfilePath.equals(qiwenFile.getPath())) {
+                    return RestResult.fail().message("原路径与目标路径冲突,不能移动");
+                }
+            }
+            userFileService.updateFilepathByUserFileId(userFile.getUserFileId(), newfilePath, userId);
+        }
+
+        return RestResult.success().data("批量移动文件成功");
+
+    }
+
+    @Operation(summary = "获取文件树", description = "文件移动的时候需要用到该接口,用来展示目录树", tags = {"file"})
+    @RequestMapping(value = "/getfiletree", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<TreeNode> getFileTree() {
+        RestResult<TreeNode> result = new RestResult<TreeNode>();
+
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        List<UserFile> userFileList = userFileService.selectFilePathTreeByUserId(userId);
+        TreeNode resultTreeNode = new TreeNode();
+        resultTreeNode.setLabel(QiwenFile.separator);
+        resultTreeNode.setId(0L);
+        long id = 1;
+        for (int i = 0; i < userFileList.size(); i++){
+            UserFile userFile = userFileList.get(i);
+            QiwenFile qiwenFile = new QiwenFile(userFile.getFilePath(), userFile.getFileName(), false);
+            String filePath = qiwenFile.getPath();
+
+            Queue<String> queue = new LinkedList<>();
+
+            String[] strArr = filePath.split(QiwenFile.separator);
+            for (int j = 0; j < strArr.length; j++){
+                if (!"".equals(strArr[j]) && strArr[j] != null){
+                    queue.add(strArr[j]);
+                }
+
+            }
+            if (queue.size() == 0){
+                continue;
+            }
+
+            resultTreeNode = fileDealComp.insertTreeNode(resultTreeNode, id++, QiwenFile.separator, queue);
+
+
+        }
+        List<TreeNode> treeNodeList = resultTreeNode.getChildren();
+        Collections.sort(treeNodeList, (o1, o2) -> {
+            long i = o1.getId() - o2.getId();
+            return (int) i;
+        });
+        result.setSuccess(true);
+        result.setData(resultTreeNode);
+        return result;
+
+    }
+
+    @Operation(summary = "修改文件", description = "支持普通文本类文件的修改", tags = {"file"})
+    @RequestMapping(value = "/update", method = RequestMethod.POST)
+    @ResponseBody
+    public RestResult<String> updateFile(@RequestBody UpdateFileDTO updateFileDTO) {
+//        JwtUser sessionUserBean =  SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        UserFile userFile = userFileService.getById(updateFileDTO.getUserFileId());
+        FileBean fileBean = fileService.getById(userFile.getFileId());
+        Long pointCount = fileService.getFilePointCount(userFile.getFileId());
+        String fileUrl = fileBean.getFileUrl();
+        if (pointCount > 1) {
+            fileUrl = fileDealComp.copyFile(fileBean, userFile);
+        }
+        String content = updateFileDTO.getFileContent();
+        ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(content.getBytes());
+        try {
+            int fileSize = byteArrayInputStream.available();
+            fileDealComp.saveFileInputStream(fileBean.getStorageType(), fileUrl, byteArrayInputStream);
+
+            String md5Str = fileDealComp.getIdentifierByFile(fileUrl, fileBean.getStorageType());
+
+            fileService.updateFileDetail(userFile.getUserFileId(), md5Str, fileSize);
+
+
+        } catch (Exception e) {
+            throw new QiwenException(999999, "修改文件异常");
+        } finally {
+            try {
+                byteArrayInputStream.close();
+            } catch (IOException e) {
+                e.printStackTrace();
+            }
+        }
+        return RestResult.success().message("修改文件成功");
+    }
+
+    @Operation(summary = "查询文件详情", description = "查询文件详情", tags = {"file"})
+    @RequestMapping(value = "/detail", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<FileDetailVO> queryFileDetail(
+            @Parameter(description = "用户文件Id", required = true) String userFileId){
+        FileDetailVO vo = fileService.getFileDetail(userFileId);
+        return RestResult.success().data(vo);
+    }
+
+
+
+
+}

+ 313 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/FiletransferController.java

@@ -0,0 +1,313 @@
+package vip.xiaonuo.disk.controller;
+
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.MimeUtils;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IFileService;
+import vip.xiaonuo.disk.api.IFiletransferService;
+import vip.xiaonuo.disk.api.IUserFileService;
+import vip.xiaonuo.disk.component.FileDealComp;
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.domain.StorageBean;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.dto.file.BatchDownloadFileDTO;
+import vip.xiaonuo.disk.dto.file.DownloadFileDTO;
+import vip.xiaonuo.disk.dto.file.PreviewDTO;
+import vip.xiaonuo.disk.dto.file.UploadFileDTO;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.service.StorageService;
+import vip.xiaonuo.disk.vo.file.UploadFileVo;
+import com.qiwenshare.ufop.factory.UFOPFactory;
+import com.qiwenshare.ufop.operation.download.Downloader;
+import com.qiwenshare.ufop.operation.download.domain.DownloadFile;
+import com.qiwenshare.ufop.operation.download.domain.Range;
+import com.qiwenshare.ufop.util.UFOPUtils;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.io.IOUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.servlet.http.Cookie;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.io.UnsupportedEncodingException;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.stream.Collectors;
+
+@Slf4j
+@Tag(name = "filetransfer", description = "该接口为文件传输接口,主要用来做文件的上传、下载和预览")
+@RestController
+@RequestMapping("/filetransfer")
+public class FiletransferController {
+
+    @Resource
+    IFiletransferService filetransferService;
+
+    @Resource
+    IFileService fileService;
+    @Resource
+    IUserFileService userFileService;
+    @Resource
+    FileDealComp fileDealComp;
+    @Resource
+    StorageService storageService;
+    @Resource
+    UFOPFactory ufopFactory;
+
+
+    public static final String CURRENT_MODULE = "文件传输接口";
+
+    @Operation(summary = "极速上传", description = "校验文件MD5判断文件是否存在,如果存在直接上传成功并返回skipUpload=true,如果不存在返回skipUpload=false需要再次调用该接口的POST方法", tags = {"filetransfer"})
+    @RequestMapping(value = "/uploadfile", method = RequestMethod.GET)
+    @MyLog(operation = "极速上传", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<UploadFileVo> uploadFileSpeed(UploadFileDTO uploadFileDto) {
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        boolean isCheckSuccess = storageService.checkStorage(userId, uploadFileDto.getTotalSize());
+        if (!isCheckSuccess) {
+            return RestResult.fail().message("存储空间不足");
+        }
+        UploadFileVo uploadFileVo = filetransferService.uploadFileSpeed(uploadFileDto);
+        return RestResult.success().data(uploadFileVo);
+
+    }
+
+    @Operation(summary = "上传文件", description = "真正的上传文件接口", tags = {"filetransfer"})
+    @RequestMapping(value = "/uploadfile", method = RequestMethod.POST)
+    @MyLog(operation = "上传文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<UploadFileVo> uploadFile(HttpServletRequest request, UploadFileDTO uploadFileDto) {
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        filetransferService.uploadFile(request, uploadFileDto, userId);
+
+        UploadFileVo uploadFileVo = new UploadFileVo();
+        return RestResult.success().data(uploadFileVo);
+
+    }
+
+
+    @Operation(summary = "下载文件", description = "下载文件接口", tags = {"filetransfer"})
+    @MyLog(operation = "下载文件", module = CURRENT_MODULE)
+    @RequestMapping(value = "/downloadfile", method = RequestMethod.GET)
+    public void downloadFile(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, DownloadFileDTO downloadFileDTO) {
+        Cookie[] cookieArr = httpServletRequest.getCookies();
+        String token = "";
+        if (cookieArr != null) {
+            for (Cookie cookie : cookieArr) {
+                if ("token".equals(cookie.getName())) {
+                    token = cookie.getValue();
+                }
+            }
+        }
+        boolean authResult = fileDealComp.checkAuthDownloadAndPreview(downloadFileDTO.getShareBatchNum(),
+                downloadFileDTO.getExtractionCode(),
+                token,
+                downloadFileDTO.getUserFileId(), null);
+        if (!authResult) {
+            log.error("没有权限下载!!!");
+            return;
+        }
+        httpServletResponse.setContentType("application/force-download");// 设置强制下载不打开
+        UserFile userFile = userFileService.getById(downloadFileDTO.getUserFileId());
+        String fileName = "";
+        if (userFile.getIsDir() == 1) {
+            fileName = userFile.getFileName() + ".zip";
+        } else {
+            fileName = userFile.getFileName() + "." + userFile.getExtendName();
+
+        }
+        try {
+            fileName = new String(fileName.getBytes("utf-8"), "ISO-8859-1");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        }
+
+        httpServletResponse.addHeader("Content-Disposition", "attachment;fileName=" + fileName);// 设置文件名
+
+        filetransferService.downloadFile(httpServletResponse, downloadFileDTO);
+    }
+
+    @Operation(summary = "批量下载文件", description = "批量下载文件", tags = {"filetransfer"})
+    @RequestMapping(value = "/batchDownloadFile", method = RequestMethod.GET)
+    @MyLog(operation = "批量下载文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public void batchDownloadFile(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, BatchDownloadFileDTO batchDownloadFileDTO) {
+        Cookie[] cookieArr = httpServletRequest.getCookies();
+        String token = "";
+        if (cookieArr != null) {
+            for (Cookie cookie : cookieArr) {
+                if ("token".equals(cookie.getName())) {
+                    token = cookie.getValue();
+                }
+            }
+        }
+        boolean authResult = fileDealComp.checkAuthDownloadAndPreview(batchDownloadFileDTO.getShareBatchNum(),
+                batchDownloadFileDTO.getExtractionCode(),
+                token,
+                batchDownloadFileDTO.getUserFileIds(), null);
+        if (!authResult) {
+            log.error("没有权限下载!!!");
+            return;
+        }
+
+        String files = batchDownloadFileDTO.getUserFileIds();
+        String[] userFileIdStrs = files.split(",");
+        List<String> userFileIds = new ArrayList<>();
+        for(String userFileId : userFileIdStrs) {
+            UserFile userFile = userFileService.getById(userFileId);
+            if (userFile.getIsDir() == 0) {
+                userFileIds.add(userFileId);
+            } else {
+                QiwenFile qiwenFile = new QiwenFile(userFile.getFilePath(), userFile.getFileName(), true);
+                List<UserFile> userFileList = userFileService.selectUserFileByLikeRightFilePath(qiwenFile.getPath(), userFile.getUserId());
+                List<String> userFileIds1 = userFileList.stream().map(UserFile::getUserFileId).collect(Collectors.toList());
+                userFileIds.add(userFile.getUserFileId());
+                userFileIds.addAll(userFileIds1);
+            }
+
+        }
+        UserFile userFile = userFileService.getById(userFileIdStrs[0]);
+        httpServletResponse.setContentType("application/force-download");// 设置强制下载不打开
+        Date date = new Date();
+        String fileName = String.valueOf(date.getTime());
+        httpServletResponse.addHeader("Content-Disposition", "attachment;fileName=" + fileName + ".zip");// 设置文件名
+        filetransferService.downloadUserFileList(httpServletResponse, userFile.getFilePath(), fileName, userFileIds);
+    }
+
+    @Operation(summary="预览文件", description="用于文件预览", tags = {"filetransfer"})
+    @GetMapping("/preview")
+    public void preview(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse,  PreviewDTO previewDTO) throws IOException {
+
+        if (previewDTO.getPlatform() != null && previewDTO.getPlatform() == 2) {
+            filetransferService.previewPictureFile(httpServletResponse, previewDTO);
+            return ;
+        }
+        String token = "";
+        if (StringUtils.isNotEmpty(previewDTO.getToken())) {
+            token = previewDTO.getToken();
+        } else {
+            Cookie[] cookieArr = httpServletRequest.getCookies();
+            if (cookieArr != null) {
+                for (Cookie cookie : cookieArr) {
+                    if ("token".equals(cookie.getName())) {
+                        token = cookie.getValue();
+                    }
+                }
+            }
+        }
+
+        UserFile userFile = userFileService.getById(previewDTO.getUserFileId());
+        boolean authResult = fileDealComp.checkAuthDownloadAndPreview(previewDTO.getShareBatchNum(),
+                previewDTO.getExtractionCode(),
+                token,
+                previewDTO.getUserFileId(),
+                previewDTO.getPlatform());
+
+        if (!authResult) {
+            log.error("没有权限预览!!!");
+            return;
+        }
+
+        String fileName = userFile.getFileName() + "." + userFile.getExtendName();
+        try {
+            fileName = new String(fileName.getBytes("utf-8"), "ISO-8859-1");
+        } catch (UnsupportedEncodingException e) {
+            e.printStackTrace();
+        }
+
+        httpServletResponse.addHeader("Content-Disposition", "fileName=" + fileName);// 设置文件名
+        String mime = MimeUtils.getMime(userFile.getExtendName());
+        httpServletResponse.setHeader("Content-Type", mime);
+        if (UFOPUtils.isImageFile(userFile.getExtendName())) {
+            httpServletResponse.setHeader("cache-control", "public");
+        }
+
+        FileBean fileBean = fileService.getById(userFile.getFileId());
+        if (UFOPUtils.isVideoFile(userFile.getExtendName()) || "mp3".equalsIgnoreCase(userFile.getExtendName()) || "flac".equalsIgnoreCase(userFile.getExtendName())) {
+            //获取从那个字节开始读取文件
+            String rangeString = httpServletRequest.getHeader("Range");
+            int start = 0;
+            if (StringUtils.isNotBlank(rangeString)) {
+                start = Integer.parseInt(rangeString.substring(rangeString.indexOf("=") + 1, rangeString.indexOf("-")));
+            }
+
+            Downloader downloader = ufopFactory.getDownloader(fileBean.getStorageType());
+            DownloadFile downloadFile = new DownloadFile();
+            downloadFile.setFileUrl(fileBean.getFileUrl());
+            Range range = new Range();
+            range.setStart(start);
+
+            if (start + 1024 * 1024 * 1 >= fileBean.getFileSize().intValue()) {
+                range.setLength(fileBean.getFileSize().intValue() - start);
+            } else {
+                range.setLength(1024 * 1024 * 1);
+            }
+            downloadFile.setRange(range);
+            InputStream inputStream = downloader.getInputStream(downloadFile);
+
+            OutputStream outputStream = httpServletResponse.getOutputStream();
+            try {
+
+                //返回码需要为206,代表只处理了部分请求,响应了部分数据
+
+                httpServletResponse.setStatus(HttpServletResponse.SC_PARTIAL_CONTENT);
+                // 每次请求只返回1MB的视频流
+
+                httpServletResponse.setHeader("Accept-Ranges", "bytes");
+                //设置此次相应返回的数据范围
+                httpServletResponse.setHeader("Content-Range", "bytes " + start + "-" + (fileBean.getFileSize() - 1) + "/" + fileBean.getFileSize());
+                IOUtils.copy(inputStream, outputStream);
+
+
+            } finally {
+                IOUtils.closeQuietly(inputStream);
+                IOUtils.closeQuietly(outputStream);
+                if (downloadFile.getOssClient() != null) {
+                    downloadFile.getOssClient().shutdown();
+                }
+            }
+
+        } else {
+            filetransferService.previewFile(httpServletResponse, previewDTO);
+        }
+
+    }
+
+    @Operation(summary = "获取存储信息", description = "获取存储信息", tags = {"filetransfer"})
+    @RequestMapping(value = "/getstorage", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<StorageBean> getStorage() {
+
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        StorageBean storageBean = new StorageBean();
+
+        storageBean.setUserId(userId);
+
+
+        Long storageSize = filetransferService.selectStorageSizeByUserId(userId);
+        StorageBean storage = new StorageBean();
+        storage.setUserId(userId);
+        storage.setStorageSize(storageSize);
+        Long totalStorageSize = storageService.getTotalStorageSize(userId);
+        storage.setTotalStorageSize(totalStorageSize);
+        return RestResult.success().data(storage);
+
+    }
+
+
+}

+ 64 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/NoticeController.java

@@ -0,0 +1,64 @@
+package vip.xiaonuo.disk.controller;
+
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.qiwenshare.common.result.RestResult;
+import vip.xiaonuo.disk.api.INoticeService;
+import vip.xiaonuo.disk.domain.Notice;
+import vip.xiaonuo.disk.dto.notice.NoticeListDTO;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+
+@Tag(name = "公告管理")
+@RestController
+@RequestMapping("/notice")
+public class NoticeController {
+    public static final String CURRENT_MODULE = "公告管理";
+    @Resource
+    INoticeService noticeService;
+
+    /**
+     * 得到所有的公告
+     *
+     * @return
+     */
+    @Operation(summary = "得到所有的公告列表", tags = {"公告管理"})
+    @RequestMapping(value = "/list", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<NoticeListDTO> selectUserList(@Parameter(description = "当前页,从1开始")  @RequestParam(defaultValue = "1") int page,
+                                          @Parameter(description = "页大小")  @RequestParam(defaultValue = "10") int pageSize,
+                                          @Parameter(description = "标题") @RequestParam(required = false) String title,
+                                          @Parameter(description = "发布者")  @RequestParam(required = false) Long publisher,
+                                          @Parameter(description = "开始发布时间")  @RequestParam(required = false) String beginTime,
+                                          @Parameter(description = "开始发布时间")  @RequestParam(required = false) String endTime) {
+        NoticeListDTO noticeListDTO = new NoticeListDTO();
+        noticeListDTO.setPage(page);
+        noticeListDTO.setPageSize(pageSize);
+        noticeListDTO.setTitle(title);
+        noticeListDTO.setPlatform(3);
+        noticeListDTO.setPublisher(publisher);
+        noticeListDTO.setBeginTime(beginTime);
+        noticeListDTO.setEndTime(endTime);
+        IPage<Notice> noticeIPage = noticeService.selectUserPage(noticeListDTO);
+
+        return RestResult.success().dataList(noticeIPage.getRecords(), noticeIPage.getTotal());
+    }
+
+    @Operation(summary = "查询公告详情", tags = {"公告管理"})
+    @RequestMapping(value = "/detail", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<Notice> getNoticeDetail(@Parameter(description = "公告id", required = true) long noticeId) {
+        RestResult<Notice> result = new RestResult<Notice>();
+
+        Notice notice = noticeService.getById(noticeId);
+
+        return RestResult.success().data(notice);
+    }
+
+
+
+
+}

+ 252 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/OfficeController.java

@@ -0,0 +1,252 @@
+package vip.xiaonuo.disk.controller;
+
+import cn.hutool.core.util.IdUtil;
+import com.alibaba.fastjson2.JSON;
+import com.alibaba.fastjson2.JSONObject;
+import com.baomidou.mybatisplus.core.toolkit.ClassUtils;
+import com.qiwenshare.common.exception.NotLoginException;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IFileService;
+import vip.xiaonuo.disk.api.IUserFileService;
+import vip.xiaonuo.disk.api.IUserService;
+import vip.xiaonuo.disk.component.FileDealComp;
+import vip.xiaonuo.disk.domain.FileBean;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.domain.user.UserBean;
+import vip.xiaonuo.disk.dto.file.CreateOfficeFileDTO;
+import vip.xiaonuo.disk.dto.file.EditOfficeFileDTO;
+import vip.xiaonuo.disk.dto.file.PreviewOfficeFileDTO;
+import vip.xiaonuo.disk.office.documentserver.managers.history.HistoryManager;
+import vip.xiaonuo.disk.office.documentserver.models.enums.Action;
+import vip.xiaonuo.disk.office.documentserver.models.enums.Type;
+import vip.xiaonuo.disk.office.documentserver.models.filemodel.FileModel;
+import vip.xiaonuo.disk.office.entities.User;
+import vip.xiaonuo.disk.office.services.configurers.FileConfigurer;
+import vip.xiaonuo.disk.office.services.configurers.wrappers.DefaultFileWrapper;
+import com.qiwenshare.ufop.factory.UFOPFactory;
+import com.qiwenshare.ufop.operation.copy.Copier;
+import com.qiwenshare.ufop.operation.copy.domain.CopyFile;
+import com.qiwenshare.ufop.operation.download.domain.DownloadFile;
+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.apache.commons.lang3.StringUtils;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.PrintWriter;
+import java.net.HttpURLConnection;
+import java.net.URL;
+import java.net.URLDecoder;
+import java.util.List;
+import java.util.Locale;
+import java.util.Scanner;
+import java.util.UUID;
+
+@Tag(name = "office", description = "该接口为Onlyoffice文件操作接口,主要用来做一些文档的编辑,浏览等。")
+@RestController
+@Slf4j
+@RequestMapping({"/office"})
+public class OfficeController {
+    public static final String CURRENT_MODULE = "Onlyoffice文件操作接口";
+    @Resource
+    IUserService userService;
+    @Resource
+    UFOPFactory ufopFactory;
+    @Resource
+    FileDealComp fileDealComp;
+    @Value("${deployment.host}")
+    private String deploymentHost;
+    @Value("${server.port}")
+    private String port;
+    @Value("${ufop.storage-type}")
+    private Integer storageType;
+
+    @Value("${files.docservice.url.site}")
+    private String docserviceSite;
+
+    @Value("${files.docservice.url.api}")
+    private String docserviceApiUrl;
+    @Autowired
+    private FileConfigurer<DefaultFileWrapper> fileConfigurer;
+
+    @Resource
+    IFileService fileService;
+    @Resource
+    IUserFileService userFileService;
+    @Autowired
+    private HistoryManager historyManager;
+
+    @Operation(summary = "预览office文件", description = "预览office文件", tags = {"office"})
+    @RequestMapping(value = "/previewofficefile", method = RequestMethod.POST)
+    @ResponseBody
+    public RestResult<Object> previewOfficeFile(HttpServletRequest request, @RequestBody PreviewOfficeFileDTO previewOfficeFileDTO) {
+        RestResult<Object> result = new RestResult<>();
+        try {
+            String token = request.getHeader("token");
+            String previewUrl = request.getScheme() + "://" + deploymentHost + ":" + port + "/filetransfer/preview?userFileId=" + previewOfficeFileDTO.getUserFileId() + "&isMin=false&shareBatchNum=undefined&extractionCode=undefined&token=" + token;
+//            JwtUser loginUser = SessionUtil.getSession();
+            String userId = StpLoginUserUtil.getLoginUser().getId();
+            UserFile userFile = userFileService.getById(previewOfficeFileDTO.getUserFileId());
+
+
+
+            UserBean userBean = userService.getById(userId);
+            User user = new User(userBean);
+
+            Action action = Action.view;
+            Type type = Type.desktop;
+            Locale locale = new Locale("zh");
+            FileModel fileModel = fileConfigurer.getFileModel(
+                    DefaultFileWrapper
+                            .builder()
+                            .userFile(userFile)
+                            .type(type)
+                            .lang(locale.toLanguageTag())
+                            .action(action)
+                            .user(user)
+                            .actionData(previewUrl)
+                            .build()
+            );
+
+            JSONObject jsonObject = new JSONObject();
+            jsonObject.put("file",fileModel);
+//            jsonObject.put("fileHistory", historyManager.getHistory(fileModel.getDocument()));  // get file history and add it to the model
+            jsonObject.put("docserviceApiUrl", docserviceSite + docserviceApiUrl);
+            jsonObject.put("reportName",userFile.getFileName());
+            result.setData(jsonObject);
+            result.setCode(200);
+            result.setMessage("获取报告成功!");
+        } catch (Exception e) {
+            log.error(e.getMessage());
+            result.setCode(500);
+            result.setMessage("服务器错误!");
+        }
+        return result;
+    }
+    @Operation(summary = "编辑office文件", description = "编辑office文件", tags = {"office"})
+    @ResponseBody
+    @RequestMapping(value = "/editofficefile", method = RequestMethod.POST)
+    public RestResult<Object> editOfficeFile(HttpServletRequest request, @RequestBody EditOfficeFileDTO editOfficeFileDTO) {
+        RestResult<Object> result = new RestResult<>();
+        String token = request.getHeader("token");
+        String previewUrl = request.getScheme() + "://" + deploymentHost + ":" + port + "/filetransfer/preview?userFileId=" + editOfficeFileDTO.getUserFileId() + "&isMin=false&shareBatchNum=undefined&extractionCode=undefined&token=" + token;
+        log.info("editOfficeFile");
+        try {
+//            JwtUser loginUser = SessionUtil.getSession();
+            String userId = StpLoginUserUtil.getLoginUser().getId();
+            UserFile userFile = userFileService.getById(editOfficeFileDTO.getUserFileId());
+
+
+            UserBean userBean = userService.getById(userId);
+            User user = new User(userBean);
+
+            Action action = Action.edit;
+            Type type = Type.desktop;
+            Locale locale = new Locale("zh");
+            FileModel fileModel = fileConfigurer.getFileModel(
+                    DefaultFileWrapper
+                            .builder()
+                            .userFile(userFile)
+                            .type(type)
+                            .lang(locale.toLanguageTag())
+                            .action(action)
+                            .user(user)
+                            .actionData(previewUrl)
+                            .build()
+            );
+            JSONObject jsonObject = new JSONObject();
+            jsonObject.put("file",fileModel);
+            jsonObject.put("docserviceApiUrl", docserviceSite + docserviceApiUrl);
+            jsonObject.put("reportName",userFile.getFileName());
+            result.setData(jsonObject);
+            result.setCode(200);
+            result.setMessage("编辑报告成功!");
+        } catch (Exception e) {
+            log.error(e.getMessage());
+            result.setCode(500);
+            result.setMessage("服务器错误!");
+        }
+        return result;
+    }
+
+
+    @RequestMapping(value = "/IndexServlet", method = RequestMethod.POST)
+    @ResponseBody
+    public void IndexServlet(HttpServletResponse response, HttpServletRequest request) throws IOException {
+        String token = request.getParameter("token");
+//        String userId = userService.getUserIdByToken(token);
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        if (StringUtils.isEmpty(userId)) {
+            throw new NotLoginException();
+        }
+
+        PrintWriter writer = response.getWriter();
+        Scanner scanner = new Scanner(request.getInputStream()).useDelimiter("\\A");
+        String body = scanner.hasNext() ? scanner.next() : "";
+
+        JSONObject jsonObj = JSON.parseObject(body);
+        log.info("===saveeditedfile:" + jsonObj.get("status")); ;
+        String status = jsonObj != null ? jsonObj.get("status").toString() : "";
+        if ("2".equals(status) || "6".equals(status)) {
+            String type = request.getParameter("type");
+            String downloadUri = (String) jsonObj.get("url");
+
+            if("edit".equals(type)){ //修改报告
+                String userFileId = request.getParameter("userFileId");
+                UserFile userFile = userFileService.getById(userFileId);
+                FileBean fileBean = fileService.getById(userFile.getFileId());
+                Long pointCount = fileService.getFilePointCount(userFile.getFileId());
+                String fileUrl = fileBean.getFileUrl();
+                if (pointCount > 1) {
+                    fileUrl = fileDealComp.copyFile(fileBean, userFile);
+                }
+
+                URL url = new URL(downloadUri);
+                HttpURLConnection connection = (HttpURLConnection) url.openConnection();
+
+                try {
+                    InputStream stream = connection.getInputStream();
+                    fileDealComp.saveFileInputStream(fileBean.getStorageType(), fileUrl, stream);
+
+                } catch (Exception e) {
+                    log.error(e.getMessage());
+                } finally {
+
+                    int fileLength = connection.getContentLength();
+                    log.info("当前修改文件大小为:" + (long) fileLength);
+
+                    DownloadFile downloadFile = new DownloadFile();
+                    downloadFile.setFileUrl(fileBean.getFileUrl());
+                    InputStream inputStream = ufopFactory.getDownloader(fileBean.getStorageType()).getInputStream(downloadFile);
+                    String md5Str = DigestUtils.md5Hex(inputStream);
+
+                    fileService.updateFileDetail(userFile.getUserFileId(), md5Str, fileLength);
+                    connection.disconnect();
+                }
+            }
+        }
+
+        if("3".equals(status)||"7".equals(status)) {//不强制手动保存时为6,"6".equals(status)
+            log.debug("====保存失败:");
+            writer.write("{\"error\":1}");
+        }else {
+            log.debug("状态为:0") ;
+            writer.write("{\"error\":" + "0" + "}");
+
+        }
+    }
+
+}

+ 109 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/RecoveryFileController.java

@@ -0,0 +1,109 @@
+package vip.xiaonuo.disk.controller;
+
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.*;
+import vip.xiaonuo.disk.component.AsyncTaskComp;
+import vip.xiaonuo.disk.domain.RecoveryFile;
+import vip.xiaonuo.disk.dto.file.DeleteRecoveryFileDTO;
+import vip.xiaonuo.disk.dto.recoveryfile.BatchDeleteRecoveryFileDTO;
+import vip.xiaonuo.disk.dto.recoveryfile.RestoreFileDTO;
+import vip.xiaonuo.disk.vo.file.RecoveryFileListVo;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import java.util.List;
+
+@Tag(name = "recoveryfile", description = "文件删除后会进入回收站,该接口主要是对回收站文件进行管理")
+@RestController
+@Slf4j
+@RequestMapping("/recoveryfile")
+public class RecoveryFileController {
+    @Resource
+    IRecoveryFileService recoveryFileService;
+    @Resource
+    IUserFileService userFileService;
+    @Resource
+    IUserService userService;
+    @Resource
+    IFileService fileService;
+    @Resource
+    IFiletransferService filetransferService;
+    @Resource
+    AsyncTaskComp asyncTaskComp;
+
+
+    public static final String CURRENT_MODULE = "回收站文件接口";
+
+    @Operation(summary = "删除回收文件", description = "删除回收文件", tags = {"recoveryfile"})
+    @MyLog(operation = "删除回收文件", module = CURRENT_MODULE)
+    @RequestMapping(value = "/deleterecoveryfile", method = RequestMethod.POST)
+    @ResponseBody
+    public RestResult<String> deleteRecoveryFile(@RequestBody DeleteRecoveryFileDTO deleteRecoveryFileDTO) {
+        RecoveryFile recoveryFile = recoveryFileService.getOne(new QueryWrapper<RecoveryFile>().lambda().eq(RecoveryFile::getUserFileId, deleteRecoveryFileDTO.getUserFileId()));
+
+        asyncTaskComp.deleteUserFile(recoveryFile.getUserFileId());
+
+        recoveryFileService.removeById(recoveryFile.getRecoveryFileId());
+        return RestResult.success().data("删除成功");
+    }
+
+    @Operation(summary = "批量删除回收文件", description = "批量删除回收文件", tags = {"recoveryfile"})
+    @RequestMapping(value = "/batchdelete", method = RequestMethod.POST)
+    @MyLog(operation = "批量删除回收文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> batchDeleteRecoveryFile(@RequestBody BatchDeleteRecoveryFileDTO batchDeleteRecoveryFileDTO) {
+        String userFileIds = batchDeleteRecoveryFileDTO.getUserFileIds();
+        String[] userFileIdList = userFileIds.split(",");
+        for (String userFileId : userFileIdList) {
+            RecoveryFile recoveryFile = recoveryFileService.getOne(new QueryWrapper<RecoveryFile>().lambda().eq(RecoveryFile::getUserFileId, userFileId));
+
+            if (recoveryFile != null) {
+                asyncTaskComp.deleteUserFile(recoveryFile.getUserFileId());
+
+                recoveryFileService.removeById(recoveryFile.getRecoveryFileId());
+            }
+
+        }
+        return RestResult.success().data("批量删除成功");
+    }
+
+    @Operation(summary = "回收文件列表", description = "回收文件列表", tags = {"recoveryfile"})
+    @RequestMapping(value = "/list", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<RecoveryFileListVo> getRecoveryFileList() {
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        List<RecoveryFileListVo> recoveryFileList = recoveryFileService.selectRecoveryFileList(userId);
+        return RestResult.success().dataList(recoveryFileList, recoveryFileList.size());
+    }
+
+    @Operation(summary = "还原文件", description = "还原文件", tags = {"recoveryfile"})
+    @RequestMapping(value = "/restorefile", method = RequestMethod.POST)
+    @MyLog(operation = "还原文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult restoreFile(@RequestBody RestoreFileDTO restoreFileDto) {
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        recoveryFileService.restorefile(restoreFileDto.getDeleteBatchNum(), restoreFileDto.getFilePath(), userId);
+        return RestResult.success().message("还原成功!");
+    }
+
+}
+
+
+
+
+
+
+
+
+

+ 246 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/ShareController.java

@@ -0,0 +1,246 @@
+package vip.xiaonuo.disk.controller;
+
+import cn.hutool.core.bean.BeanUtil;
+import cn.hutool.core.util.IdUtil;
+import cn.hutool.core.util.RandomUtil;
+import com.alibaba.fastjson2.JSON;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IShareFileService;
+import vip.xiaonuo.disk.api.IShareService;
+import vip.xiaonuo.disk.api.IUserFileService;
+import vip.xiaonuo.disk.component.FileDealComp;
+import vip.xiaonuo.disk.domain.Share;
+import vip.xiaonuo.disk.domain.ShareFile;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.dto.sharefile.*;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.vo.share.ShareFileListVO;
+import vip.xiaonuo.disk.vo.share.ShareFileVO;
+import vip.xiaonuo.disk.vo.share.ShareListVO;
+import vip.xiaonuo.disk.vo.share.ShareTypeVO;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import java.text.ParseException;
+import java.util.*;
+
+@Tag(name = "share", description = "该接口为文件分享接口")
+@RestController
+@Slf4j
+@RequestMapping("/share")
+public class ShareController {
+
+    public static final String CURRENT_MODULE = "文件分享";
+
+    @Resource
+    IShareFileService shareFileService;
+    @Resource
+    IShareService shareService;
+    @Resource
+    IUserFileService userFileService;
+    @Resource
+    FileDealComp fileDealComp;
+
+    @Operation(summary = "分享文件", description = "分享文件统一接口", tags = {"share"})
+    @PostMapping(value = "/sharefile")
+    @MyLog(operation = "分享文件", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<ShareFileVO> shareFile( @RequestBody ShareFileDTO shareFileDTO) {
+        ShareFileVO shareSecretVO = new ShareFileVO();
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        String uuid = UUID.randomUUID().toString().replace("-", "");
+        Share share = new Share();
+        share.setShareId(IdUtil.getSnowflakeNextIdStr());
+        BeanUtil.copyProperties(shareFileDTO, share);
+        share.setShareTime(DateUtil.getCurrentTime());
+        share.setUserId(userId);
+        share.setShareStatus(0);
+        if (shareFileDTO.getShareType() == 1) {
+            String extractionCode = RandomUtil.randomNumbers(6);
+            share.setExtractionCode(extractionCode);
+            shareSecretVO.setExtractionCode(share.getExtractionCode());
+        }
+
+        share.setShareBatchNum(uuid);
+        shareService.save(share);
+
+        List<ShareFile> saveFileList = new ArrayList<>();
+        String userFileIds = shareFileDTO.getUserFileIds();
+        String[] userFileIdList = userFileIds.split(",");
+        for (String userFileId : userFileIdList) {
+            UserFile userFile = userFileService.getById(userFileId);
+            if (userFile.getUserId().compareTo(userId) != 0) {
+                return RestResult.fail().message("您只能分享自己的文件");
+            }
+            if (userFile.getIsDir() == 1) {
+                QiwenFile qiwenFile = new QiwenFile(userFile.getFilePath(), userFile.getFileName(), true);
+                List<UserFile> userfileList = userFileService.selectUserFileByLikeRightFilePath(qiwenFile.getPath(), userId);
+                for (UserFile userFile1 : userfileList) {
+                    ShareFile shareFile1 = new ShareFile();
+                    shareFile1.setShareFileId(IdUtil.getSnowflakeNextIdStr());
+                    shareFile1.setUserFileId(userFile1.getUserFileId());
+                    shareFile1.setShareBatchNum(uuid);
+                    shareFile1.setShareFilePath(userFile1.getFilePath().replaceFirst(userFile.getFilePath().equals("/") ? "" : userFile.getFilePath(), ""));
+                    saveFileList.add(shareFile1);
+                }
+            }
+            ShareFile shareFile = new ShareFile();
+            shareFile.setShareFileId(IdUtil.getSnowflakeNextIdStr());
+            shareFile.setUserFileId(userFileId);
+            shareFile.setShareFilePath("/");
+            shareFile.setShareBatchNum(uuid);
+            saveFileList.add(shareFile);
+
+
+        }
+        shareFileService.saveBatch(saveFileList);
+        shareSecretVO.setShareBatchNum(uuid);
+
+        return RestResult.success().data(shareSecretVO);
+    }
+
+    @Operation(summary = "保存分享文件", description = "用来将别人分享的文件保存到自己的网盘中", tags = {"share"})
+    @PostMapping(value = "/savesharefile")
+    @MyLog(operation = "保存分享文件", module = CURRENT_MODULE)
+    @Transactional(rollbackFor=Exception.class)
+    @ResponseBody
+    public RestResult saveShareFile(@RequestBody SaveShareFileDTO saveShareFileDTO) {
+
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+//        List<ShareFile> fileList = JSON.parseArray(saveShareFileDTO.getFiles(), ShareFile.class);
+        String savefilePath = saveShareFileDTO.getFilePath();
+//        String userId = sessionUserBean.getUserId();
+        String[] userFileIdArr = saveShareFileDTO.getUserFileIds().split(",");
+        List<UserFile> saveUserFileList = new ArrayList<>();
+        for (String userFileId : userFileIdArr) {
+
+
+            UserFile userFile = userFileService.getById(userFileId);
+            String fileName = userFile.getFileName();
+            String filePath = userFile.getFilePath();
+
+            UserFile userFile2 = new UserFile();
+            BeanUtil.copyProperties(userFile, userFile2);
+
+            String savefileName = fileDealComp.getRepeatFileName(userFile, savefilePath);
+
+            if (userFile.getIsDir() == 1) {
+                ShareFile shareFile = shareFileService.getOne(new QueryWrapper<ShareFile>().lambda().eq(ShareFile::getUserFileId, userFileId).eq(ShareFile::getShareBatchNum, saveShareFileDTO.getShareBatchNum()));
+                List<ShareFile> shareFileList = shareFileService.list(new QueryWrapper<ShareFile>().lambda().eq(ShareFile::getShareBatchNum, saveShareFileDTO.getShareBatchNum()).likeRight(ShareFile::getShareFilePath, QiwenFile.formatPath(shareFile.getShareFilePath() +"/"+ fileName)));
+
+
+
+                for (ShareFile shareFile1 : shareFileList) {
+                    UserFile userFile1 = userFileService.getById(shareFile1.getUserFileId());
+                    userFile1.setUserFileId(IdUtil.getSnowflakeNextIdStr());
+                    userFile1.setUserId(userId);
+                    userFile1.setFilePath(userFile1.getFilePath().replaceFirst(QiwenFile.formatPath(filePath + "/" + fileName), QiwenFile.formatPath(savefilePath + "/" + savefileName)));
+                    saveUserFileList.add(userFile1);
+                    log.info("当前文件:" + JSON.toJSONString(userFile1));
+                }
+            }
+            userFile2.setUserFileId(IdUtil.getSnowflakeNextIdStr());
+            userFile2.setUserId(userId);
+            userFile2.setFilePath(savefilePath);
+            userFile2.setFileName(savefileName);
+            saveUserFileList.add(userFile2);
+
+        }
+        log.info("----------" + JSON.toJSONString(saveUserFileList));
+        userFileService.saveBatch(saveUserFileList);
+
+        return RestResult.success();
+    }
+
+    @Operation(summary = "查看已分享列表", description = "查看已分享列表", tags = {"share"})
+    @GetMapping(value = "/shareList")
+    @ResponseBody
+    public RestResult<ShareListVO> shareList(ShareListDTO shareListDTO) {
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+        List<ShareListVO> shareList = shareService.selectShareList(shareListDTO, userId);
+
+        int total = shareService.selectShareListTotalCount(shareListDTO, userId);
+
+        return RestResult.success().dataList(shareList, total);
+    }
+
+
+    @Operation(summary = "分享文件列表", description = "分享列表", tags = {"share"})
+    @GetMapping(value = "/sharefileList")
+    @ResponseBody
+    public RestResult<ShareFileListVO> shareFileList(ShareFileListDTO shareFileListBySecretDTO) {
+        String shareBatchNum = shareFileListBySecretDTO.getShareBatchNum();
+        String shareFilePath = shareFileListBySecretDTO.getShareFilePath();
+        List<ShareFileListVO> list = shareFileService.selectShareFileList(shareBatchNum, shareFilePath);
+        for (ShareFileListVO shareFileListVO : list) {
+            shareFileListVO.setShareFilePath(shareFilePath);
+        }
+        return RestResult.success().dataList(list, list.size());
+    }
+
+    @Operation(summary = "分享类型", description = "可用此接口判断是否需要提取码", tags = {"share"})
+    @GetMapping(value = "/sharetype")
+    @ResponseBody
+    public RestResult<ShareTypeVO> shareType(ShareTypeDTO shareTypeDTO) {
+        LambdaQueryWrapper<Share> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(Share::getShareBatchNum, shareTypeDTO.getShareBatchNum());
+        Share share = shareService.getOne(lambdaQueryWrapper);
+        ShareTypeVO shareTypeVO = new ShareTypeVO();
+        shareTypeVO.setShareType(share.getShareType());
+        return RestResult.success().data(shareTypeVO);
+    }
+
+    @Operation(summary = "校验提取码", description = "校验提取码", tags = {"share"})
+    @GetMapping(value = "/checkextractioncode")
+    @ResponseBody
+    public RestResult<String> checkExtractionCode(CheckExtractionCodeDTO checkExtractionCodeDTO) {
+        LambdaQueryWrapper<Share> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(Share::getShareBatchNum, checkExtractionCodeDTO.getShareBatchNum())
+                .eq(Share::getExtractionCode, checkExtractionCodeDTO.getExtractionCode());
+        List<Share> list = shareService.list(lambdaQueryWrapper);
+        if (list.isEmpty()) {
+            return RestResult.fail().message("校验失败");
+        } else {
+            return RestResult.success();
+        }
+    }
+
+    @Operation(summary = "校验过期时间", description = "校验过期时间", tags = {"share"})
+    @GetMapping(value = "/checkendtime")
+    @ResponseBody
+    public RestResult<String> checkEndTime(CheckEndTimeDTO checkEndTimeDTO) {
+        LambdaQueryWrapper<Share> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+        lambdaQueryWrapper.eq(Share::getShareBatchNum, checkEndTimeDTO.getShareBatchNum());
+        Share share = shareService.getOne(lambdaQueryWrapper);
+        if (share == null) {
+            return RestResult.fail().message("文件不存在!");
+        }
+        String endTime = share.getEndTime();
+        Date endTimeDate = null;
+        try {
+            endTimeDate = DateUtil.getDateByFormatString(endTime, "yyyy-MM-dd HH:mm:ss");
+        } catch (ParseException e) {
+            log.error("日期解析失败:{}" , e);
+        }
+        if (new Date().after(endTimeDate))  {
+            return RestResult.fail().message("分享已过期");
+        } else {
+            return RestResult.success();
+        }
+    }
+}

+ 47 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/SysParamController.java

@@ -0,0 +1,47 @@
+package vip.xiaonuo.disk.controller;
+
+
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import com.qiwenshare.common.result.RestResult;
+import vip.xiaonuo.disk.api.ISysParamService;
+import vip.xiaonuo.disk.domain.SysParam;
+import vip.xiaonuo.disk.dto.param.QueryGroupParamDTO;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import org.springframework.web.bind.annotation.RequestMapping;
+import org.springframework.web.bind.annotation.RequestMethod;
+import org.springframework.web.bind.annotation.ResponseBody;
+import org.springframework.web.bind.annotation.RestController;
+
+import javax.annotation.Resource;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+@Tag(name = "系统参数管理")
+@RestController
+@RequestMapping("/param")
+public class SysParamController {
+    @Resource
+    ISysParamService sysParamService;
+
+    @Operation(summary = "查询系统参数组", tags = {"系统参数管理"})
+    @RequestMapping(value = "/grouplist", method = RequestMethod.GET)
+    @ResponseBody
+    public RestResult<Map> groupList(
+            @Parameter(description = "查询参数dto", required = false)
+                    QueryGroupParamDTO queryGroupParamDTO
+    ) {
+        List<SysParam> list = sysParamService.list(new QueryWrapper<SysParam>().lambda().eq(SysParam::getGroupName, queryGroupParamDTO.getGroupName()));
+        Map<String, Object> result = new HashMap<>();
+
+        for (SysParam sysParam : list) {
+            result.put(sysParam.getSysParamKey(), sysParam.getSysParamValue());
+        }
+
+        return RestResult.success().data(result);
+    }
+
+
+}

+ 85 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/TaskController.java

@@ -0,0 +1,85 @@
+package vip.xiaonuo.disk.controller;
+
+import co.elastic.clients.elasticsearch.ElasticsearchClient;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
+import vip.xiaonuo.disk.api.IShareFileService;
+import vip.xiaonuo.disk.component.FileDealComp;
+import vip.xiaonuo.disk.domain.ShareFile;
+import vip.xiaonuo.disk.domain.UserFile;
+import vip.xiaonuo.disk.io.QiwenFile;
+import vip.xiaonuo.disk.service.UserFileService;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.scheduling.annotation.Scheduled;
+import org.springframework.stereotype.Controller;
+
+import javax.annotation.Resource;
+import java.util.List;
+
+@Slf4j
+@Controller
+public class TaskController {
+
+    @Resource
+    UserFileService userFileService;
+    @Resource
+    FileDealComp fileDealComp;
+    @Resource
+    IShareFileService shareFileService;
+    @Autowired
+    private ElasticsearchClient elasticsearchClient;
+
+
+    @Scheduled(fixedRate = 1000 * 60 * 60 * 24)
+    public void updateElasticSearch() {
+        List<UserFile> userfileList = userFileService.list(new QueryWrapper<UserFile>().eq("deleteFlag", 0));
+        for (int i = 0; i < userfileList.size(); i++) {
+            try {
+
+                QiwenFile ufopFile = new QiwenFile(userfileList.get(i).getFilePath(), userfileList.get(i).getFileName(), userfileList.get(i).getIsDir() == 1);
+                fileDealComp.restoreParentFilePath(ufopFile, userfileList.get(i).getUserId());
+                if (i % 1000 == 0 || i == userfileList.size() - 1) {
+                    log.info("目录健康检查进度:" + (i + 1) + "/" + userfileList.size());
+                }
+
+            } catch (Exception e) {
+                log.error(e.getMessage());
+            }
+        }
+        userfileList = userFileService.list(new QueryWrapper<UserFile>().eq("deleteFlag", 0));
+        for (UserFile userFile : userfileList) {
+            fileDealComp.uploadESByUserFileId(userFile.getUserFileId());
+        }
+
+    }
+
+    @Scheduled(fixedRate = Long.MAX_VALUE)
+    public void updateFilePath() {
+        List<UserFile> list = userFileService.list();
+        for (UserFile userFile : list) {
+            try {
+                String path = QiwenFile.formatPath(userFile.getFilePath());
+                if (!userFile.getFilePath().equals(path)) {
+                    userFile.setFilePath(path);
+                    userFileService.updateById(userFile);
+                }
+            } catch (Exception e) {
+                // ignore
+            }
+        }
+    }
+
+    @Scheduled(fixedRate = Long.MAX_VALUE)
+    public void updateShareFilePath() {
+        List<ShareFile> list = shareFileService.list();
+        for (ShareFile shareFile : list) {
+            try {
+                String path = QiwenFile.formatPath(shareFile.getShareFilePath());
+                shareFile.setShareFilePath(path);
+                shareFileService.updateById(shareFile);
+            } catch (Exception e) {
+                //ignore
+            }
+        }
+    }
+}

+ 156 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/controller/UserController.java

@@ -0,0 +1,156 @@
+package vip.xiaonuo.disk.controller;
+
+import cn.hutool.core.bean.BeanUtil;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.qiwenshare.common.anno.MyLog;
+import com.qiwenshare.common.result.RestResult;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.common.util.HashUtils;
+import com.qiwenshare.common.util.security.JwtUser;
+import com.qiwenshare.common.util.security.SessionUtil;
+import vip.xiaonuo.auth.core.pojo.SaBaseLoginUser;
+import vip.xiaonuo.auth.core.util.StpLoginUserUtil;
+import vip.xiaonuo.disk.api.IUserLoginInfoService;
+import vip.xiaonuo.disk.api.IUserService;
+import vip.xiaonuo.disk.component.JwtComp;
+import vip.xiaonuo.disk.domain.UserLoginInfo;
+import vip.xiaonuo.disk.domain.user.UserBean;
+import vip.xiaonuo.disk.dto.user.RegisterDTO;
+import vip.xiaonuo.disk.vo.user.UserLoginVo;
+import io.swagger.v3.oas.annotations.Operation;
+import io.swagger.v3.oas.annotations.Parameter;
+import io.swagger.v3.oas.annotations.tags.Tag;
+import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.lang3.StringUtils;
+import org.springframework.web.bind.annotation.*;
+
+import javax.annotation.Resource;
+import javax.validation.Valid;
+import java.util.HashMap;
+import java.util.Map;
+
+
+@Tag(name = "user", description = "该接口为用户接口,主要做用户登录,注册和校验token")
+@RestController
+@Slf4j
+@RequestMapping("/user")
+public class UserController {
+
+    @Resource
+    IUserService userService;
+    @Resource
+    IUserLoginInfoService userLoginInfoService;
+    @Resource
+    JwtComp jwtComp;
+
+    public static Map<String, String> verificationCodeMap = new HashMap<>();
+
+
+    public static final String CURRENT_MODULE = "用户管理";
+
+    @Operation(summary = "用户注册", description = "注册账号", tags = {"user"})
+    @PostMapping(value = "/register")
+    @MyLog(operation = "用户注册", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<String> addUser(@Valid @RequestBody RegisterDTO registerDTO) {
+        RestResult<String> restResult = null;
+        UserBean userBean = new UserBean();
+        BeanUtil.copyProperties(registerDTO, userBean);
+        restResult = userService.registerUser(userBean);
+
+        return restResult;
+    }
+
+    @Operation(summary = "用户登录", description = "用户登录认证后才能进入系统", tags = {"user"})
+    @GetMapping("/login")
+    @MyLog(operation = "用户登录", module = CURRENT_MODULE)
+    @ResponseBody
+    public RestResult<UserLoginVo> userLogin(
+            @Parameter(description = "登录手机号") String telephone,
+            @Parameter(description = "登录密码") String password){
+        RestResult<UserLoginVo> restResult = new RestResult<UserLoginVo>();
+        String salt = userService.getSaltByTelephone(telephone);
+        String hashPassword = HashUtils.hashHex("MD5", password, salt, 1024);
+        UserBean result = userService.selectUserByTelephoneAndPassword(telephone, hashPassword);
+        if (result == null) {
+            return RestResult.fail().message("手机号或密码错误!");
+        }
+
+        Map<String, Object> param = new HashMap<>();
+        param.put("userId", result.getUserId());
+        String token = "";
+        try {
+            token = jwtComp.createJWT(param);
+        } catch (Exception e) {
+            log.info("登录失败:{}", e);
+            return RestResult.fail().message("创建token失败!");
+        }
+        UserBean sessionUserBean = userService.findUserInfoByTelephone(telephone);
+        if (sessionUserBean.getAvailable() != null && sessionUserBean.getAvailable() == 0) {
+            return RestResult.fail().message("用户已被禁用");
+        }
+        UserLoginVo userLoginVo = new UserLoginVo();
+        BeanUtil.copyProperties(sessionUserBean, userLoginVo);
+        userLoginVo.setToken("Bearer " + token);
+        restResult.setData(userLoginVo);
+        restResult.setSuccess(true);
+        restResult.setCode(200001);
+        return restResult;
+
+    }
+
+    @Operation(summary = "检查用户登录信息", description = "验证token的有效性", tags = {"user"})
+    @GetMapping("/checkuserlogininfo")
+    @ResponseBody
+    public RestResult<UserLoginVo> checkUserLoginInfo(@RequestHeader("token") String token) {
+        UserLoginVo userLoginVo = new UserLoginVo();
+//        String userId = userService.getUserIdByToken(token);
+        String userId = StpLoginUserUtil.getLoginUser().getId();
+
+        if (StringUtils.isNotEmpty(userId)) {
+            LambdaQueryWrapper<UserLoginInfo> lambdaQueryWrapper = new LambdaQueryWrapper<>();
+            lambdaQueryWrapper.eq(UserLoginInfo::getUserId, userId);
+            lambdaQueryWrapper.likeRight(UserLoginInfo::getUserloginDate, DateUtil.getCurrentTime().substring(0, 10));
+            userLoginInfoService.remove(lambdaQueryWrapper);
+            UserLoginInfo userLoginInfo = new UserLoginInfo();
+            userLoginInfo.setUserId(userId);
+            userLoginInfo.setUserloginDate(DateUtil.getCurrentTime());
+            userLoginInfoService.save(userLoginInfo);
+            UserBean user = userService.getById(userId);
+            BeanUtil.copyProperties(user, userLoginVo);
+            if (StringUtils.isEmpty(user.getWxOpenId())) {
+                userLoginVo.setHasWxAuth(false);
+            } else {
+                userLoginVo.setHasWxAuth(true);
+            }
+            return RestResult.success().data(userLoginVo);
+
+        } else {
+            return RestResult.fail().message("用户暂未登录");
+        }
+
+    }
+
+    @Operation(summary = "检查微信认证", description = "检查微信认证", tags = {"user"})
+    @GetMapping("/checkWxAuth")
+    @ResponseBody
+    public RestResult<Boolean> checkWxAuth() {
+//        JwtUser sessionUserBean = SessionUtil.getSession();
+        SaBaseLoginUser loginUser = StpLoginUserUtil.getLoginUser();
+
+        if (loginUser != null && !"anonymousUser".equals(loginUser.getAccount())) {
+            UserBean user = userService.getById(loginUser.getId());
+
+            if (StringUtils.isEmpty(user.getWxOpenId())) {
+                return RestResult.success().data(false);
+            } else {
+                return RestResult.success().data(true);
+            }
+
+        } else {
+            return RestResult.fail().message("用户暂未登录");
+        }
+
+    }
+
+}

+ 30 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/CommonFile.java

@@ -0,0 +1,30 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2022/1/12 14:41
+ */
+@Data
+@Table(name = "commonfile")
+@Entity
+@TableName("commonfile")
+public class CommonFile {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="varchar(20)")
+    public String commonFileId;
+    @Column(columnDefinition="varchar(20) comment '用户文件id'")
+    public String userFileId;
+//    @Column(columnDefinition="int(2) comment '文件权限'")
+//    public Integer filePermission;
+}

+ 84 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileBean.java

@@ -0,0 +1,84 @@
+package vip.xiaonuo.disk.domain;
+
+import cn.hutool.core.util.IdUtil;
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.qiwenshare.common.util.DateUtil;
+import com.qiwenshare.ufop.operation.upload.domain.UploadFileResult;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * 文件实体类
+ *
+ * @author ma116
+ */
+@Data
+@Table(name = "file")
+@Entity
+@TableName("file")
+public class FileBean {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="varchar(20)")
+    private String fileId;
+
+    @Column(columnDefinition="varchar(500) comment '文件url'")
+    private String fileUrl;
+
+    @Column(columnDefinition="bigint(10) comment '文件大小'")
+    private Long fileSize;
+
+    @Column(columnDefinition="int(1) comment '文件状态(0-失效,1-生效)'")
+    private Integer fileStatus;
+
+    @Column(columnDefinition="int(1) comment '存储类型'")
+    private Integer storageType;
+
+    @Column(columnDefinition="varchar(200) comment 'md5唯一标识'")
+    private String identifier;
+
+    @Column(columnDefinition="varchar(25) comment '创建时间'")
+    private String createTime;
+
+    @Column(columnDefinition="varchar(20) comment '创建用户id'")
+    private String createUserId;
+
+    @Column(columnDefinition="varchar(25) comment '修改时间'")
+    private String modifyTime;
+
+    @Column(columnDefinition="varchar(20) comment '修改用户id'")
+    private String modifyUserId;
+
+    public FileBean(){
+
+    }
+
+    public FileBean(UploadFileResult uploadFileResult) {
+        this.fileId = IdUtil.getSnowflakeNextIdStr();
+        this.fileUrl = uploadFileResult.getFileUrl();
+        this.fileSize = uploadFileResult.getFileSize();
+        this.fileStatus = 1;
+        this.storageType = uploadFileResult.getStorageType().getCode();
+        this.identifier = uploadFileResult.getIdentifier();
+        this.createTime = DateUtil.getCurrentTime();
+
+    }
+
+    public FileBean(String fileUrl, Long fileSize, Integer storageType, String identifier, String userId) {
+        this.fileId = IdUtil.getSnowflakeNextIdStr();
+        this.fileUrl = fileUrl;
+        this.fileSize = fileSize;
+        this.fileStatus = 1;
+        this.storageType = storageType;
+        this.identifier = identifier;
+        this.createTime = DateUtil.getCurrentTime();
+        this.createUserId = userId;
+
+    }
+
+}

+ 30 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileClassification.java

@@ -0,0 +1,30 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/23 19:48
+ */
+@Data
+@Table(name = "fileclassification")
+@Entity
+@TableName("fileclassification")
+public class FileClassification {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private Long fileClassificationId;
+    @Column(columnDefinition="bigint(20) comment '文件类型id'")
+    private Integer fileTypeId;
+    @Column(columnDefinition="varchar(25) comment '文件扩展名'")
+    private String fileExtendName;
+}

+ 30 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileExtend.java

@@ -0,0 +1,30 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/20 20:16
+ */
+@Data
+@Table(name = "fileextend")
+@Entity
+@TableName("fileextend")
+public class FileExtend {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="varchar(25)")
+    private String fileExtendName;
+    @Column(columnDefinition="varchar(25) comment '文件扩展名描述'")
+    private String fileExtendDesc;
+    @Column(columnDefinition="varchar(100) comment '文件扩展名预览图'")
+    private String fileExtendImgUrl;
+}

+ 33 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FilePermission.java

@@ -0,0 +1,33 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2022/1/12 14:44
+ */
+@Data
+@Table(name = "filepermission")
+@Entity
+@TableName("filepermission")
+public class FilePermission {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    public Long filePermissionId;
+    @Column(columnDefinition="varchar(20)  comment '共享文件id'")
+    public String commonFileId;
+    @Column(columnDefinition="bigint(20) comment '用户id'")
+    public Long userId;
+    @Column(columnDefinition="int(2) comment '用户对文件的权限码'")
+    public Integer filePermissionCode;
+
+}

+ 29 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/FileType.java

@@ -0,0 +1,29 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/23 22:11
+ */
+@Data
+@Table(name = "filetype")
+@Entity
+@TableName("filetype")
+public class FileType {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    private Integer fileTypeId;
+    @Column(columnDefinition="varchar(50) comment '文件类型名'")
+    private String fileTypeName;
+    @Column(columnDefinition="int(2) comment '次序'")
+    private Integer orderNum;
+}

+ 32 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Image.java

@@ -0,0 +1,32 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/7 22:05
+ */
+@Data
+@Table(name = "image")
+@Entity
+@TableName("image")
+public class Image {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private Long imageId;
+    @Column(columnDefinition = "varchar(20) comment '文件id'")
+    private String fileId;
+    @Column(columnDefinition="int(5) comment '图像的宽'")
+    private Integer imageWidth;
+    @Column(columnDefinition="int(5) comment '图像的高'")
+    private Integer imageHeight;
+}

+ 62 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Music.java

@@ -0,0 +1,62 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2022/4/27 23:44
+ */
+@Data
+@Table(name = "music")
+@Entity
+@TableName("music")
+public class Music {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private String musicId;
+    @Column(columnDefinition = "bigint(20) comment '文件id'")
+    private String fileId;
+    private String track;
+    @Column
+    private String artist;
+    @Column
+    private String title;
+    @Column
+    private String album;
+    @Column
+    private String year;
+    @Column
+    private String genre;
+    @Column
+    private String comment;
+    @Column(columnDefinition="varchar(10000) comment '歌词'")
+    private String lyrics;
+    @Column
+    private String composer;
+    @Column
+    private String publicer;
+    @Column
+    private String originalArtist;
+    @Column
+    private String albumArtist;
+    @Column
+    private String copyright;
+    @Column
+    private String url;
+    @Column
+    private String encoder;
+    @Column(columnDefinition = "mediumblob")
+    private String albumImage;
+
+    @Column
+    private Float trackLength;
+}

+ 49 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Notice.java

@@ -0,0 +1,49 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: 公告
+ * @date 2021/11/22 22:16
+ */
+@Data
+@Table(name = "notice")
+@Entity
+@TableName("notice")
+public class Notice {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)", unique = true)
+    private Long noticeId;
+
+    @Column(columnDefinition="varchar(100) comment '标题'", nullable = false)
+    private String title;
+    @Column(columnDefinition="int(2) comment '平台(1-社区,2-管理端,3-网盘,4-股票)'")
+    private Integer platform;
+
+    @Column(columnDefinition = "longtext comment 'markdown原文'")
+    private String markdownContent;
+    @Column(columnDefinition = "longtext comment 'html内容'")
+    private String content;
+    @Column(columnDefinition="varchar(25) comment '有效时间'")
+    private String validDateTime;
+    @Column(columnDefinition="int(1) comment '是否长期有效(0-否,1-是)'")
+    private int isLongValidData;
+
+    @Column(columnDefinition="varchar(25) comment '创建时间'")
+    private String createTime;
+    @Column(columnDefinition="bigint(20) comment '创建用户id'")
+    private Long createUserId;
+    @Column(columnDefinition="varchar(25) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition="bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+}

+ 85 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/OperationLogBean.java

@@ -0,0 +1,85 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * 操作日志基础信息类
+ *
+ * @author ma116
+ */
+@Data
+@Table(name = "operationlog")
+@Entity
+@TableName("operationlog")
+public class OperationLogBean {
+    /**
+     * 操作日志id
+     */
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long operationLogId;
+
+    /**
+     * 用户id
+     */
+    @Column(columnDefinition="varchar(20) comment '用户id'")
+    private String userId;
+
+    /**
+     * 操作
+     */
+    @Column(columnDefinition="varchar(50) comment '操作'")
+    private String operation;
+
+    /**
+     * 操作对象
+     */
+    private String operationObj;
+
+    /**
+     * 终端IP
+     */
+    @Column(columnDefinition="varchar(20) comment '终端ip地址'")
+    private String terminal;
+
+    /**
+     * 操作结果
+     */
+    @Column(columnDefinition="varchar(20) comment '操作结果'")
+    private String result;
+
+    /**
+     * 操作详情
+     */
+    @Column(columnDefinition="varchar(100) comment '操作详情'")
+    private String detail;
+
+    /**
+     * 操作源
+     */
+    private String source;
+
+    /**
+     * 时间
+     */
+    @Column(columnDefinition="varchar(25) comment '操作时间'")
+    private String time;
+
+    /**
+     * 日志级别 1-正常 2-警告 3-错误
+     */
+    private Integer logLevel;
+
+    @Column(columnDefinition="int(2) comment '平台(1-社区,2-管理端,3-网盘,4-股票)'")
+    private Integer platform;
+
+    private String requestURI;
+    private String requestMethod;
+
+}

+ 60 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/PictureFile.java

@@ -0,0 +1,60 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2022/1/1 19:06
+ */
+@Data
+@Table(name = "picturefile")
+@Entity
+@TableName("picturefile")
+public class PictureFile {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private Long pictureFileId;
+
+    @Column(columnDefinition="varchar(500) comment '文件url'")
+    private String fileUrl;
+
+    @Column(columnDefinition="bigint(10) comment '文件大小'")
+    private Long fileSize;
+
+    @Column(columnDefinition="int(1) comment '存储类型'")
+    private Integer storageType;
+
+    @Column(columnDefinition = "bigint(20) comment '用户id'")
+    private Long userId;
+
+    @Column(columnDefinition="varchar(100) comment '文件名'")
+    private String fileName;
+
+    @Column(columnDefinition="varchar(100) comment '扩展名'")
+    private String extendName;
+
+    @Column(columnDefinition="varchar(25) comment '创建时间'")
+    private String createTime;
+
+    @Column(columnDefinition="bigint(20) comment '创建用户id'")
+    private Long createUserId;
+
+    @Column(columnDefinition="varchar(25) comment '修改时间'")
+    private String modifyTime;
+
+    @Column(columnDefinition="bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+
+
+
+}

+ 29 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/RecoveryFile.java

@@ -0,0 +1,29 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "recoveryfile", uniqueConstraints = {
+        @UniqueConstraint(name = "user_file_id_index3", columnNames = {"userFileId"})
+})
+@Entity
+@TableName("recoveryfile")
+public class RecoveryFile {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private Long recoveryFileId;
+    @Column(columnDefinition = "varchar(20) comment '用户文件id'")
+    private String userFileId;
+    @Column(columnDefinition="varchar(25) comment '删除时间'")
+    private String deleteTime;
+    @Column(columnDefinition = "varchar(50) comment '删除批次号'")
+    private String deleteBatchNum;
+}

+ 35 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/Share.java

@@ -0,0 +1,35 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+import java.util.UUID;
+
+@Data
+@Table(name = "share")
+@Entity
+@TableName("share")
+public class Share {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    private String shareId;
+    @Column(columnDefinition="varchar(20) comment '用户id'")
+    private String userId;
+    @Column(columnDefinition="varchar(30) comment '分享时间'")
+    private String shareTime;
+    @Column(columnDefinition="varchar(30) comment '失效时间'")
+    private String endTime;
+    @Column(columnDefinition="varchar(10) comment '提取码'")
+    private String extractionCode;
+    @Column(columnDefinition="varchar(40) comment '分享批次号'")
+    private String shareBatchNum;
+    @Column(columnDefinition="int(2) comment '分享类型(0公共,1私密,2好友)'")
+    private Integer shareType;
+    @Column(columnDefinition="int(2) comment '分享状态(0正常,1已失效,2已撤销)'")
+    private Integer shareStatus;
+
+}

+ 27 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/ShareFile.java

@@ -0,0 +1,27 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "sharefile")
+@Entity
+@TableName("sharefile")
+public class ShareFile {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    private String shareFileId;
+
+    @Column(columnDefinition="varchar(50) comment '分享批次号'")
+    private String shareBatchNum;
+    @Column(columnDefinition="varchar(20) comment '用户文件id'")
+    private String userFileId;
+    @Column(columnDefinition="varchar(100) comment '分享文件路径'")
+    private String shareFilePath;
+
+}

+ 49 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/StorageBean.java

@@ -0,0 +1,49 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * 存储信息类
+ */
+@Data
+@Table(name = "storage", uniqueConstraints = {
+        @UniqueConstraint(name = "userid_index", columnNames = {"userId"})
+})
+@Entity
+@TableName("storage")
+public class StorageBean {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(columnDefinition="bigint(20)")
+    @TableId(type = IdType.AUTO)
+    private Long storageId;
+
+    @Column(columnDefinition="varchar(20)")
+    private String userId;
+
+    @Column(columnDefinition="bigint(20) comment '占用存储大小'")
+    private Long storageSize;
+
+    @Column(columnDefinition="bigint(20) comment '总存储大小'")
+    private Long totalStorageSize;
+
+    @Column(columnDefinition="varchar(25) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition="bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+
+    public StorageBean() {
+
+    }
+
+    public StorageBean(String userId) {
+        this.userId = userId;
+    }
+
+}

+ 28 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/SysParam.java

@@ -0,0 +1,28 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "sysparam")
+@Entity
+@TableName("sysparam")
+public class SysParam {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(columnDefinition = "bigint(20)")
+    @TableId(type = IdType.AUTO)
+    private Long sysParamId;
+    @Column(columnDefinition = "varchar(50)")
+    private String groupName;
+    @Column(columnDefinition = "varchar(50)")
+    private String sysParamKey;
+    @Column(columnDefinition = "varchar(50)")
+    private String sysParamValue;
+    @Column(columnDefinition = "varchar(50)")
+    private String sysParamDesc;
+}

+ 42 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UploadTask.java

@@ -0,0 +1,42 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "uploadtask")
+@Entity
+@TableName("uploadtask")
+public class UploadTask {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition = "bigint(20)")
+    private Long uploadTaskId;
+
+    @Column(columnDefinition = "bigint(20) comment '用户id'")
+    private String userId;
+
+    @Column(columnDefinition="varchar(200) comment 'md5唯一标识'")
+    private String identifier;
+
+    @Column(columnDefinition="varchar(100) comment '文件名称'")
+    private String fileName;
+
+    @Column(columnDefinition="varchar(500) comment '文件路径'")
+    private String filePath;
+
+    @Column(columnDefinition="varchar(100) comment '扩展名'")
+    private String extendName;
+
+    @Column(columnDefinition="varchar(25) comment '上传时间'")
+    private String uploadTime;
+
+    @Column(columnDefinition="int(1) comment '上传状态(1-成功,0-失败或未完成)'")
+    private Integer uploadStatus;
+}

+ 42 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UploadTaskDetail.java

@@ -0,0 +1,42 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "uploadtaskdetail")
+@Entity
+@TableName("uploadtaskdetail")
+public class UploadTaskDetail {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    @Column(columnDefinition="bigint(20)")
+    private Long uploadTaskDetailId;
+
+    @Column(columnDefinition="varchar(500) comment '文件路径'")
+    private String filePath;
+
+    @Column(columnDefinition="varchar(100) comment '文件名称'")
+    private String filename;
+
+    @Column(columnDefinition="int(5) comment '当前分片数'")
+    private int chunkNumber;
+
+    @Column(columnDefinition="bigint(10) comment '当前分片大小'")
+    private Integer chunkSize;
+    @Column(columnDefinition="varchar(500) comment '文件相对路径'")
+    private String relativePath;
+
+    @Column(columnDefinition="int(5) comment '文件总分片数'")
+    private Integer totalChunks;
+    @Column(columnDefinition="bigint(10) comment '文件总大小'")
+    private Integer totalSize;
+
+    @Column(columnDefinition="varchar(200) comment '文件md5唯一标识'")
+    private String identifier;
+}

+ 90 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UserFile.java

@@ -0,0 +1,90 @@
+package vip.xiaonuo.disk.domain;
+
+import cn.hutool.core.util.IdUtil;
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.qiwenshare.common.util.DateUtil;
+import vip.xiaonuo.disk.io.QiwenFile;
+import lombok.Data;
+import lombok.Getter;
+
+import javax.persistence.*;
+import javax.validation.constraints.NotNull;
+
+@Data
+@Table(name = "userfile", uniqueConstraints = {
+        @UniqueConstraint(name = "fileindex", columnNames = {"userId", "filePath", "fileName", "extendName", "deleteFlag", "isDir"})
+})
+@Entity
+@TableName("userfile")
+public class UserFile {
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @TableId(type = IdType.AUTO)
+    @Column(nullable = false, columnDefinition = "varchar(20)")
+    private String userFileId;
+
+    @Column(columnDefinition = "bigint(20) comment '用户id'")
+    private String userId;
+
+    @Column(columnDefinition="varchar(20) comment '文件id'")
+    private String fileId;
+
+    @Column(columnDefinition="varchar(100) comment '文件名'")
+    private String fileName;
+
+    @Column(columnDefinition="varchar(500) comment '文件路径'")
+    private String filePath;
+
+    @Column(columnDefinition="varchar(100) NULL DEFAULT '' comment '扩展名'")
+    private String extendName;
+
+    @Column(columnDefinition="int(1) comment '是否是目录(0-否,1-是)'")
+    private Integer isDir;
+
+    @Column(columnDefinition="varchar(25) comment '修改时间'")
+    private String uploadTime;
+
+    @Column(columnDefinition="int(11) comment '删除标识(0-未删除,1-已删除)'")
+    private Integer deleteFlag;
+
+    @Column(columnDefinition="varchar(25) comment '删除时间'")
+    private String deleteTime;
+
+    @Column(columnDefinition = "varchar(50) comment '删除批次号'")
+    private String deleteBatchNum;
+    @Column(columnDefinition="varchar(30) comment '创建时间'")
+    private String createTime;
+    @Column(columnDefinition="varchar(20) comment '创建用户id'")
+    private String createUserId;
+    @Column(columnDefinition="varchar(30) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition="varchar(20) comment '修改用户id'")
+    private String modifyUserId;
+
+    public UserFile() {};
+    public UserFile(QiwenFile qiwenFile, String userId, String fileId) {
+        this.userFileId = IdUtil.getSnowflakeNextIdStr();
+        this.userId = userId;
+        this.fileId = fileId;
+        this.filePath = qiwenFile.getParent();
+        this.fileName = qiwenFile.getNameNotExtend();
+        this.extendName = qiwenFile.getExtendName();
+        this.isDir = qiwenFile.isDirectory() ? 1 : 0;
+        String currentTime = DateUtil.getCurrentTime();
+        this.setUploadTime(currentTime);
+        this.setCreateUserId(userId);
+        this.setCreateTime(currentTime);
+        this.deleteFlag = 0;
+    }
+
+    public boolean isDirectory() {
+        return this.isDir == 1;
+    }
+
+    public boolean isFile() {
+        return this.isDir == 0;
+    }
+
+}

+ 29 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/UserLoginInfo.java

@@ -0,0 +1,29 @@
+package vip.xiaonuo.disk.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/11/18 22:36
+ */
+@Data
+@Table(name = "userlogininfo")
+@Entity
+@TableName("userlogininfo")
+public class UserLoginInfo {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long userLoginId;
+    @Column(columnDefinition = "varchar(30) comment '用户登录日期'")
+    private String userloginDate;
+    @Column(columnDefinition = "varchar(20) comment '用户id'")
+    private String userId;
+}

+ 50 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/Permission.java

@@ -0,0 +1,50 @@
+package vip.xiaonuo.disk.domain.user;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * 权限实体类
+ */
+@Data
+@Table(name = "permission")
+@Entity
+@TableName("permission")
+public class Permission {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long permissionId;//主键
+
+    @Column(columnDefinition="bigint(20) comment '父编号'")
+    private Long parentId;
+
+    @Column(columnDefinition="varchar(30) comment '权限名称'")
+    private String permissionName;//名称.
+
+    @Column(columnDefinition="int(2) comment '资源类型'")
+    private Integer resourceType;//资源类型
+
+    @Column(columnDefinition="varchar(30) comment '权限标识码'")
+    private String permissionCode;
+
+    @Column(columnDefinition="int(2) comment '次序'")
+    private Integer orderNum;
+
+    @Column(columnDefinition="varchar(30) comment '创建时间'")
+    private String createTime;
+    @Column(columnDefinition="bigint(20) comment '创建用户id'")
+    private Long createUserId;
+    @Column(columnDefinition="varchar(30) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition="bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+
+
+
+}

+ 54 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/Role.java

@@ -0,0 +1,54 @@
+package vip.xiaonuo.disk.domain.user;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableField;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+import java.util.List;
+
+/**
+ * 角色实体信息类
+ */
+@Data
+@Table(name = "role")
+@Entity
+@TableName("role")
+public class Role {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long roleId; // 编号
+
+    @Column(columnDefinition="varchar(20) comment '角色名'")
+    private String roleName;
+
+    @Column(columnDefinition="varchar(100) comment '角色描述'")
+    private String description;
+
+    @Column(columnDefinition="int(2) comment '是否可用(0-不可用,1-可用)'")
+    private Integer available; // 是否可用,如果不可用将不会添加给用户
+
+    @Column(columnDefinition="varchar(30) comment '创建时间'")
+    private String createTime;
+    @Column(columnDefinition="bigint(20) comment '创建用户id'")
+    private Long createUserId;
+    @Column(columnDefinition="varchar(30) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition="bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+
+//    /**
+//     * 权限列表
+//     */
+//    @ManyToMany(fetch = FetchType.EAGER)//立即从数据库中进行加载数据
+//    @JoinTable(name = "role_permission",
+//            joinColumns = {@JoinColumn(name = "roleid")},
+//            inverseJoinColumns = {@JoinColumn(name = "permissionid")})
+//    @TableField(exist = false)
+//    private List<Permission> permissions;
+
+}

+ 29 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/RolePermission.java

@@ -0,0 +1,29 @@
+package vip.xiaonuo.disk.domain.user;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/30 16:14
+ */
+@Data
+@Table(name = "role_permission")
+@Entity
+@TableName("role_permission")
+public class RolePermission {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long id;
+    @Column(columnDefinition="bigint(20) comment '角色id'")
+    private Long roleId;
+    @Column(columnDefinition="bigint(20) comment '权限id'")
+    private Long permissionId;
+}

+ 85 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/UserBean.java

@@ -0,0 +1,85 @@
+package vip.xiaonuo.disk.domain.user;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+/**
+ * 用户基础信息类
+ *
+ * @author ma116
+ */
+@Data
+@Table(name = "user")
+@Entity
+@TableName("user")
+public class UserBean {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.AUTO)
+    @Column(columnDefinition = "varchar(20)")
+    @TableId(type = IdType.AUTO)
+    private String userId;
+
+    @Column(columnDefinition = "varchar(30) comment '用户名'")
+    private String username;
+
+    @Column(columnDefinition = "varchar(35) comment '密码'")
+    private String password;
+
+    @Column(columnDefinition = "varchar(15) comment '手机号'")
+    private String telephone;
+
+    @Column(columnDefinition = "varchar(100) comment '邮箱'")
+    private String email;
+
+    @Column(columnDefinition = "varchar(3) comment '性别'")
+    private String sex;
+
+    @Column(columnDefinition = "varchar(30) comment '生日'")
+    private String birthday;
+
+    @Column(columnDefinition = "varchar(10) comment '省'")
+    private String addrProvince;
+
+    @Column(columnDefinition = "varchar(10) comment '市'")
+    private String addrCity;
+
+    @Column(columnDefinition = "varchar(10) comment '区'")
+    private String addrArea;
+
+    @Column(columnDefinition = "varchar(50) comment '行业'")
+    private String industry;
+
+    @Column(columnDefinition = "varchar(50) comment '地区'")
+    private String position;
+
+    @Column(columnDefinition = "varchar(5000) comment '个人简介'")
+    private String intro;
+
+    @Column(columnDefinition = "varchar(20) comment '盐'")
+    private String salt;
+
+    @Column(columnDefinition = "varchar(100) comment '头像'")
+    private String imageUrl;
+
+    @Column(columnDefinition = "varchar(30) comment '注册时间'")
+    private String registerTime;
+
+    @Column(columnDefinition = "varchar(30) comment '最后登录时间'")
+    private String lastLoginTime;
+
+    @Column(columnDefinition = "int(2) comment '是否可用(0-不可用,1-可用)'")
+    private Integer available;
+    @Column(columnDefinition = "varchar(30) comment '修改时间'")
+    private String modifyTime;
+    @Column(columnDefinition = "bigint(20) comment '修改用户id'")
+    private Long modifyUserId;
+    @Column(columnDefinition = "varchar(28) comment 'open id'")
+    private String wxOpenId;
+
+
+}

+ 21 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/domain/user/UserRole.java

@@ -0,0 +1,21 @@
+package vip.xiaonuo.disk.domain.user;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import javax.persistence.*;
+
+@Data
+@Table(name = "user_role")
+@Entity
+@TableName("user_role")
+public class UserRole {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @TableId(type = IdType.AUTO)
+    private Long userRoleId;
+    private String userId;
+    private Long roleId;
+}

+ 19 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/commonfile/CommonFileDTO.java

@@ -0,0 +1,19 @@
+package vip.xiaonuo.disk.dto.commonfile;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+/**
+ * @author MAC
+ * @version 1.0
+ * @description: TODO
+ * @date 2022/1/12 15:03
+ */
+@Data
+@Schema(name = "共享文件DTO",required = true)
+public class CommonFileDTO {
+    @Schema(name = "用户文件id")
+    private String userFileId;
+    @Schema(name = "共享用户id集合")
+    private String commonUserList;
+}

+ 16 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchDeleteFileDTO.java

@@ -0,0 +1,16 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import javax.validation.constraints.NotEmpty;
+import java.util.regex.Pattern;
+
+@Data
+@Schema(name = "批量删除文件DTO",required = true)
+public class BatchDeleteFileDTO {
+    @Schema(description="文件Id集合", required = true)
+    @NotEmpty
+    private String userFileIds;
+
+}

+ 16 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchDownloadFileDTO.java

@@ -0,0 +1,16 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "批量下载文件DTO",required = true)
+public class BatchDownloadFileDTO {
+    @Schema(description="文件集合", required = true)
+    private String userFileIds;
+    @Schema(description="批次号")
+    private String shareBatchNum;
+    @Schema(description="提取码")
+    private String extractionCode;
+
+}

+ 15 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/BatchMoveFileDTO.java

@@ -0,0 +1,15 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "批量移动文件DTO",required = true)
+public class BatchMoveFileDTO {
+    @Schema(description="用户文件Id集合", required = true)
+    private String userFileIds;
+    @Schema(description="目的文件路径", required = true)
+    private String filePath;
+
+
+}

+ 15 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CopyFileDTO.java

@@ -0,0 +1,15 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "复制文件DTO",required = true)
+public class CopyFileDTO {
+    @Schema(description = "用户文件id集合", required = true)
+    private String userFileIds;
+
+    @Schema(description = "文件路径", required = true)
+    private String filePath;
+
+}

+ 24 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateFileDTO.java

@@ -0,0 +1,24 @@
+package vip.xiaonuo.disk.dto.file;
+
+import com.qiwenshare.common.constant.RegexConstant;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.Pattern;
+
+@Data
+public class CreateFileDTO {
+
+    @Schema(description = "文件路径", required = true)
+    private String filePath;
+
+    @Schema(description = "文件名", required = true)
+    @NotBlank(message = "文件名不能为空")
+    @Pattern(regexp = RegexConstant.FILE_NAME_REGEX, message = "文件名不合法!", flags = {Pattern.Flag.CASE_INSENSITIVE})
+    private String fileName;
+
+    @Schema(description = "扩展名", required = true)
+    private String extendName;
+
+}

+ 20 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateFoldDTO.java

@@ -0,0 +1,20 @@
+package vip.xiaonuo.disk.dto.file;
+
+import com.qiwenshare.common.constant.RegexConstant;
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+import javax.validation.constraints.NotBlank;
+import javax.validation.constraints.Pattern;
+
+@Data
+@Schema(name = "创建文件DTO",required = true)
+public class CreateFoldDTO {
+    @Schema(description="文件名", required=true)
+    @NotBlank(message = "文件名不能为空")
+    @Pattern(regexp = RegexConstant.FILE_NAME_REGEX, message = "文件名不合法!")
+    private String fileName;
+    @Schema(description="文件路径", required=true)
+    private String filePath;
+
+}

+ 10 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/CreateOfficeFileDTO.java

@@ -0,0 +1,10 @@
+package vip.xiaonuo.disk.dto.file;
+
+import lombok.Data;
+
+@Data
+public class CreateOfficeFileDTO {
+   private String filePath;
+   private String fileName;
+   private String extendName;
+}

+ 13 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DeleteFileDTO.java

@@ -0,0 +1,13 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "删除文件DTO",required = true)
+public class DeleteFileDTO {
+    @Schema(description = "用户文件id", required = true)
+    private String userFileId;
+
+
+}

+ 12 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DeleteRecoveryFileDTO.java

@@ -0,0 +1,12 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "删除回收文件DTO",required = true)
+public class DeleteRecoveryFileDTO {
+    @Schema(description = "用户文件id", required = true)
+    private String userFileId;
+
+}

+ 14 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/DownloadFileDTO.java

@@ -0,0 +1,14 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "下载文件DTO",required = true)
+public class DownloadFileDTO {
+    private String userFileId;
+    @Schema(description="批次号")
+    private String shareBatchNum;
+    @Schema(description="提取码")
+    private String extractionCode;
+}

+ 12 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/EditOfficeFileDTO.java

@@ -0,0 +1,12 @@
+package vip.xiaonuo.disk.dto.file;
+
+import lombok.Data;
+
+@Data
+public class EditOfficeFileDTO {
+   private String userFileId;
+//   private String previewUrl;
+//   private String filePath;
+//   private String fileName;
+//   private String extendName;
+}

+ 15 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/FileListDTO.java

@@ -0,0 +1,15 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "文件列表DTO",required = true)
+public class FileListDTO {
+    @Schema(description = "文件路径", required = true)
+    private String filePath;
+    @Schema(description = "当前页码", required = true)
+    private Long currentPage;
+    @Schema(description = "一页显示数量", required = true)
+    private Long pageCount;
+}

+ 22 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/MoveFileDTO.java

@@ -0,0 +1,22 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "移动文件DTO",required = true)
+public class MoveFileDTO {
+    @Schema(description = "用户文件id", required = true)
+    private String userFileId;
+    @Schema(description = "文件路径", required = true)
+    private String filePath;
+//
+//    @Schema(description = "文件名", required = true)
+//    private String fileName;
+//
+//    @Schema(description = "旧文件名", required = true)
+//    private String oldFilePath;
+//    @Schema(description = "扩展名", required = true)
+//    private String extendName;
+
+}

+ 15 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/OnlyofficeDTO.java

@@ -0,0 +1,15 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+public class OnlyofficeDTO {
+    private String fileId;
+
+    private String fileName;
+
+    private String fileUrl;
+
+    private String extendName;
+}

+ 18 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/PreviewDTO.java

@@ -0,0 +1,18 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "预览文件DTO",required = true)
+public class PreviewDTO {
+    private String userFileId;
+    @Schema(description="批次号")
+    private String shareBatchNum;
+    @Schema(description="提取码")
+    private String extractionCode;
+    private String isMin;
+    private Integer platform;
+    private String url;
+    private String token;
+}

+ 12 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/PreviewOfficeFileDTO.java

@@ -0,0 +1,12 @@
+package vip.xiaonuo.disk.dto.file;
+
+import lombok.Data;
+
+@Data
+public class PreviewOfficeFileDTO {
+   private String userFileId;
+   private String previewUrl;
+//   private String filePath;
+//   private String fileName;
+//   private String extendName;
+}

+ 14 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/RenameFileDTO.java

@@ -0,0 +1,14 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "重命名文件DTO",required = true)
+public class RenameFileDTO {
+    @Schema(description = "用户文件id", required = true)
+    private String userFileId;
+
+    @Schema(description = "文件名", required = true)
+    private String fileName;
+}

+ 14 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/SearchFileDTO.java

@@ -0,0 +1,14 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+public class SearchFileDTO {
+    @Schema(description="文件名", required=true)
+    private String fileName;
+    @Schema(description="当前页", required=true)
+    private long currentPage;
+    @Schema(description="每页数量", required=true)
+    private long pageCount;
+}

+ 17 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/UnzipFileDTO.java

@@ -0,0 +1,17 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+@Data
+@Schema(name = "解压缩文件DTO",required = true)
+public class UnzipFileDTO {
+    @Schema(description = "文件url", required = true)
+    private String userFileId;
+
+    @Schema(description = "解压模式 0-解压到当前文件夹, 1-自动创建该文件名目录,并解压到目录里, 2-手动选择解压目录", required = true)
+    private int unzipMode;
+
+    @Schema(description = "解压目的文件目录,仅当 unzipMode 为 2 时必传")
+    private String filePath;
+}

+ 19 - 0
snowy-plugin/snowy-plugin-disk/snowy-plugin-disk-func/src/main/java/vip/xiaonuo/disk/dto/file/UpdateFileDTO.java

@@ -0,0 +1,19 @@
+package vip.xiaonuo.disk.dto.file;
+
+import io.swagger.v3.oas.annotations.media.Schema;
+import lombok.Data;
+
+/**
+ * @author 马超
+ * @version 1.0
+ * @description: TODO
+ * @date 2021/12/8 19:23
+ */
+@Data
+@Schema(name = "修改文件DTO",required = true)
+public class UpdateFileDTO {
+    @Schema(description = "用户文件id")
+    private String userFileId;
+    @Schema(description = "文件内容")
+    private String fileContent;
+}

Some files were not shown because too many files changed in this diff