wangliang 3 weeks ago
parent
commit
db7f1e31d9

+ 98 - 25
sop-api/src/main/java/com/qmth/sop/server/api/TBDeviceDeliveryController.java

@@ -1,8 +1,9 @@
 package com.qmth.sop.server.api;
 
-
+import com.alibaba.excel.EasyExcel;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.qmth.boot.api.constant.ApiConstant;
+import com.qmth.sop.business.bean.dto.SysMessageExportDto;
 import com.qmth.sop.business.bean.params.DeviceDeliveryParam;
 import com.qmth.sop.business.bean.params.DeviceInOutForm;
 import com.qmth.sop.business.bean.result.ProjectExchangeResult;
@@ -12,6 +13,7 @@ import com.qmth.sop.business.service.TBDeviceDeliveryService;
 import com.qmth.sop.common.annotation.OperationLog;
 import com.qmth.sop.common.contant.SystemConstant;
 import com.qmth.sop.common.enums.*;
+import com.qmth.sop.common.util.FileUtil;
 import com.qmth.sop.common.util.Result;
 import com.qmth.sop.common.util.ResultUtil;
 import com.qmth.sop.common.util.ServletUtil;
@@ -26,8 +28,11 @@ import javax.annotation.Resource;
 import javax.validation.Valid;
 import javax.validation.constraints.Max;
 import javax.validation.constraints.Min;
+import java.io.File;
+import java.text.SimpleDateFormat;
 import java.util.ArrayList;
 import java.util.List;
+import java.util.Objects;
 import java.util.Optional;
 import java.util.stream.Collectors;
 
@@ -50,12 +55,18 @@ public class TBDeviceDeliveryController {
     @ApiOperation(value = "设备发货列表分页查询")
     @RequestMapping(value = "/page", method = RequestMethod.POST)
     @ApiResponses({ @ApiResponse(code = 200, message = "返回信息", response = ProjectExchangeResult.class) })
-    public Result list(@ApiParam(value = "服务单元id") @RequestParam(required = false) String serviceId, @ApiParam(value = "用途类型") @RequestParam(required = false) DeviceUsageTypeEnum usageType,
-            @ApiParam(value = "项目单号") @RequestParam(required = false) String crmNo, @ApiParam(value = "发货状态") @RequestParam(required = false) DeviceDeliveryStatusEnum status,
-            @ApiParam(value = "发货人id") @RequestParam(required = false) String deliverUserId, @ApiParam(value = "发货开始时间") @RequestParam(required = false) Long deliverStartTime,
-            @ApiParam(value = "发货结束时间") @RequestParam(required = false) Long deliverEndTime, @ApiParam(value = "设备序列号") @RequestParam(required = false) String serialNo,
-            @ApiParam(value = "设备编号") @RequestParam(required = false) String deviceNo, @ApiParam(value = "供应商id") @RequestParam(required = false) String supplierId,
-            @ApiParam(value = "签收开始时间") @RequestParam(required = false) Long receiveStartTime, @ApiParam(value = "签收结束时间") @RequestParam(required = false) Long receiveEndTime,
+    public Result list(@ApiParam(value = "服务单元id") @RequestParam(required = false) String serviceId,
+            @ApiParam(value = "用途类型") @RequestParam(required = false) DeviceUsageTypeEnum usageType,
+            @ApiParam(value = "项目单号") @RequestParam(required = false) String crmNo,
+            @ApiParam(value = "发货状态") @RequestParam(required = false) DeviceDeliveryStatusEnum status,
+            @ApiParam(value = "发货人id") @RequestParam(required = false) String deliverUserId,
+            @ApiParam(value = "发货开始时间") @RequestParam(required = false) Long deliverStartTime,
+            @ApiParam(value = "发货结束时间") @RequestParam(required = false) Long deliverEndTime,
+            @ApiParam(value = "设备序列号") @RequestParam(required = false) String serialNo,
+            @ApiParam(value = "设备编号") @RequestParam(required = false) String deviceNo,
+            @ApiParam(value = "供应商id") @RequestParam(required = false) String supplierId,
+            @ApiParam(value = "签收开始时间") @RequestParam(required = false) Long receiveStartTime,
+            @ApiParam(value = "签收结束时间") @RequestParam(required = false) Long receiveEndTime,
             @ApiParam(value = "收件人") @RequestParam(required = false) String consignee,
             @ApiParam(value = "邮寄地址") @RequestParam(required = false) String mailingAddress,
             @ApiParam(value = "出入库状态") @RequestParam(required = false) InOutTypeEnum deliveryType,
@@ -65,10 +76,11 @@ public class TBDeviceDeliveryController {
             @ApiParam(value = "页码", required = true) @RequestParam @Min(SystemConstant.PAGE_NUMBER_MIN) Integer pageNumber,
             @ApiParam(value = "页数", required = true) @RequestParam @Min(SystemConstant.PAGE_SIZE_MIN) @Max(SystemConstant.PAGE_SIZE_MAX) Integer pageSize)
             throws Exception {
-        return ResultUtil.ok(tbDeviceDeliveryService.page(new Page<>(pageNumber, pageSize), SystemConstant.convertIdToLong(serviceId),
-                usageType, crmNo, status, SystemConstant.convertIdToLong(deliverUserId), deliverStartTime, deliverEndTime,
-                serialNo, deviceNo, SystemConstant.convertIdToLong(supplierId), receiveStartTime, receiveEndTime,
-                consignee, mailingAddress, deliveryType, brand, model, expressNo));
+        return ResultUtil.ok(tbDeviceDeliveryService.page(new Page<>(pageNumber, pageSize),
+                SystemConstant.convertIdToLong(serviceId), usageType, crmNo, status,
+                SystemConstant.convertIdToLong(deliverUserId), deliverStartTime, deliverEndTime, serialNo, deviceNo,
+                SystemConstant.convertIdToLong(supplierId), receiveStartTime, receiveEndTime, consignee, mailingAddress,
+                deliveryType, brand, model, expressNo));
     }
 
     @ApiOperation(value = "设备发货保存接口")
@@ -76,7 +88,8 @@ public class TBDeviceDeliveryController {
     @ApiResponses({ @ApiResponse(code = 200, message = "返回信息", response = Object.class) })
     @OperationLog(logType = LogTypeEnum.UPDATE)
     @Transactional
-    public Result save(@Valid @ApiParam(value = "设备发货修改信息", required = true) @RequestBody DeviceDeliveryParam deviceDeliveryParam,
+    public Result save(
+            @Valid @ApiParam(value = "设备发货修改信息", required = true) @RequestBody DeviceDeliveryParam deviceDeliveryParam,
             BindingResult bindingResult) throws Exception {
         if (bindingResult.hasErrors()) {
             return ResultUtil.error(bindingResult.getAllErrors().get(0).getDefaultMessage());
@@ -99,7 +112,8 @@ public class TBDeviceDeliveryController {
     @ApiResponses({ @ApiResponse(code = 200, message = "返回信息", response = Object.class) })
     @OperationLog(logType = LogTypeEnum.UPDATE)
     @Transactional
-    public Result statusUpdate(@ApiParam(value = "设备发货id", required = true) @RequestParam List<String> idList, @ApiParam(value = "设备发货状态", required = true) @RequestParam DeviceDeliveryStatusEnum status) {
+    public Result statusUpdate(@ApiParam(value = "设备发货id", required = true) @RequestParam List<String> idList,
+            @ApiParam(value = "设备发货状态", required = true) @RequestParam DeviceDeliveryStatusEnum status) {
         SysUser requestUser = (SysUser) ServletUtil.getRequestUser();
         if (CollectionUtils.isNotEmpty(idList)) {
             tbDeviceDeliveryService.updateStatus(
@@ -123,20 +137,77 @@ public class TBDeviceDeliveryController {
     @RequestMapping(value = "/export", method = RequestMethod.POST)
     @ApiResponses({ @ApiResponse(code = 200, message = "返回信息", response = ProjectExchangeResult.class) })
     @OperationLog(logType = LogTypeEnum.EXPORT)
-    public void export(@ApiParam(value = "服务单元id") @RequestParam(required = false) Long serviceId, @ApiParam(value = "用途类型") @RequestParam(required = false) DeviceUsageTypeEnum usageType,
-            @ApiParam(value = "项目单号") @RequestParam(required = false) String crmNo, @ApiParam(value = "发货状态") @RequestParam(required = false) DeviceDeliveryStatusEnum status,
-            @ApiParam(value = "发货人id") @RequestParam(required = false) Long deliverUserId, @ApiParam(value = "发货开始时间") @RequestParam(required = false) Long deliverStartTime,
-            @ApiParam(value = "发货结束时间") @RequestParam(required = false) Long deliverEndTime, @ApiParam(value = "设备序列号") @RequestParam(required = false) String serialNo,
-            @ApiParam(value = "设备编号") @RequestParam(required = false) String deviceNo, @ApiParam(value = "供应商id") @RequestParam(required = false) Long supplierId,
-            @ApiParam(value = "签收开始时间") @RequestParam(required = false) Long receiveStartTime, @ApiParam(value = "签收结束时间") @RequestParam(required = false) Long receiveEndTime,
+    public void export(@ApiParam(value = "服务单元id") @RequestParam(required = false) Long serviceId,
+            @ApiParam(value = "用途类型") @RequestParam(required = false) DeviceUsageTypeEnum usageType,
+            @ApiParam(value = "项目单号") @RequestParam(required = false) String crmNo,
+            @ApiParam(value = "发货状态") @RequestParam(required = false) DeviceDeliveryStatusEnum status,
+            @ApiParam(value = "发货人id") @RequestParam(required = false) Long deliverUserId,
+            @ApiParam(value = "发货开始时间") @RequestParam(required = false) Long deliverStartTime,
+            @ApiParam(value = "发货结束时间") @RequestParam(required = false) Long deliverEndTime,
+            @ApiParam(value = "设备序列号") @RequestParam(required = false) String serialNo,
+            @ApiParam(value = "设备编号") @RequestParam(required = false) String deviceNo,
+            @ApiParam(value = "供应商id") @RequestParam(required = false) Long supplierId,
+            @ApiParam(value = "签收开始时间") @RequestParam(required = false) Long receiveStartTime,
+            @ApiParam(value = "签收结束时间") @RequestParam(required = false) Long receiveEndTime,
             @ApiParam(value = "收件人") @RequestParam(required = false) String consignee,
-            @ApiParam(value = "邮寄地址") @RequestParam(required = false) String mailingAddress, @ApiParam(value = "出入库状态") @RequestParam(required = false) InOutTypeEnum deliveryType,
+            @ApiParam(value = "邮寄地址") @RequestParam(required = false) String mailingAddress,
+            @ApiParam(value = "出入库状态") @RequestParam(required = false) InOutTypeEnum deliveryType,
             @ApiParam(value = "品牌") @RequestParam(required = false) String brand,
             @ApiParam(value = "型号") @RequestParam(required = false) String model,
             @ApiParam(value = "快递单号") @RequestParam(required = false) String expressNo) throws Exception {
-        tbDeviceDeliveryService.dataExport(serviceId, usageType, crmNo, status, deliverUserId, deliverStartTime,
-                deliverEndTime, serialNo, deviceNo, supplierId, receiveStartTime, receiveEndTime, consignee,
-                mailingAddress, deliveryType, brand, model, expressNo);
+        //        tbDeviceDeliveryService.dataExport(serviceId, usageType, crmNo, status, deliverUserId, deliverStartTime,
+        //                deliverEndTime, serialNo, deviceNo, supplierId, receiveStartTime, receiveEndTime, consignee,
+        //                mailingAddress, deliveryType, brand, model, expressNo);
+        String rootPath = null;
+        List<File> fileTempList = new ArrayList<>();
+        try {
+            String title = "测试zip";
+            rootPath = FileUtil.getFileTempDirPath(true);
+            String downloadFilePath = rootPath + File.separator + title;
+            File downloadPathFile = new File(downloadFilePath);
+            if (!downloadPathFile.exists()) {
+                downloadPathFile.mkdirs();
+            }
+
+            for (int y = 0; y < 3; y++) {
+                File fileTemp = new File(downloadFilePath, title + (y + 1) + SystemConstant.XLSX_PREFIX);
+                if (!fileTemp.exists()) {
+                    fileTemp.createNewFile();
+                }
+                List<SysMessageExportDto> sysMessageExportDtoList = new ArrayList<>();
+                for (int i = 0; i < 5; i++) {
+                    SysMessageExportDto dto = new SysMessageExportDto();
+                    dto.setCity("武汉");
+                    dto.setCode("code" + (i + 1));
+                    dto.setCountry("湖北");
+                    dto.setCustom("自定义" + (i + 1));
+                    dto.setMobileNumber("1800865900" + (i + 1));
+                    dto.setName("name" + (i + 1));
+                    dto.setProvince("中国");
+                    dto.setService("service" + (i + 1));
+                    dto.setStatus("已阅");
+                    dto.setSupplier("supplier" + (i + 1));
+                    //时间戳转化为日期字符串
+                    dto.setTime(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(System.currentTimeMillis()));
+                    dto.setType("type" + (i + 1));
+                    sysMessageExportDtoList.add(dto);
+                }
+                EasyExcel.write(fileTemp, SysMessageExportDto.class).sheet("回执明细导出").doWrite(sysMessageExportDtoList);
+                fileTempList.add(fileTemp);
+            }
+            String zipFileName = title + SystemConstant.ZIP_PREFIX;
+            FileUtil.downloadEncryptZip(ServletUtil.getResponse(), downloadPathFile, zipFileName,
+                    SystemConstant.ZIP_ENCRYPT_PWD);
+        } catch (Exception e) {
+            e.printStackTrace();
+        } finally {
+            if (Objects.nonNull(rootPath)) {
+                FileUtil.deleteDirectory(rootPath);
+            }
+            for (File file : fileTempList) {
+                file.delete();
+            }
+        }
     }
 
     @ApiOperation(value = "设备发货人列表查询")
@@ -149,10 +220,12 @@ public class TBDeviceDeliveryController {
     @ApiOperation(value = "设备发货可返还设备列表查询")
     @RequestMapping(value = "/can_return_info", method = RequestMethod.POST)
     @ApiResponses({ @ApiResponse(code = 200, message = "返回信息", response = SysUser.class) })
-    public Result findDeviceReturnList(@ApiParam(value = "设备发货id集合") @RequestParam(required = false) List<String> idList) {
+    public Result findDeviceReturnList(
+            @ApiParam(value = "设备发货id集合") @RequestParam(required = false) List<String> idList) {
         List<Long> deviceDeliveryIdList = new ArrayList<>();
         if (CollectionUtils.isNotEmpty(idList)) {
-            deviceDeliveryIdList = idList.stream().map(SystemConstant::convertIdToLong).distinct().collect(Collectors.toList());
+            deviceDeliveryIdList = idList.stream().map(SystemConstant::convertIdToLong).distinct()
+                    .collect(Collectors.toList());
 
         }
         List<DeviceInOutForm> deviceInOutFormList = tbDeviceDeliveryService.findDeviceReturnList(deviceDeliveryIdList);

+ 2 - 0
sop-common/src/main/java/com/qmth/sop/common/contant/SystemConstant.java

@@ -36,6 +36,8 @@ public class SystemConstant {
     /**
      * 系统常量
      */
+    public static final String ZIP_PREFIX = ".zip";
+    public static final String ZIP_ENCRYPT_PWD = "qmthzip";
     public static final String CHARSET_NAME = "UTF-8";
 
     //    public static final String CHARSET_GB2312 = "gb2312";

+ 681 - 0
sop-common/src/main/java/com/qmth/sop/common/util/FileUtil.java

@@ -1,14 +1,30 @@
 package com.qmth.sop.common.util;
 
 import com.qmth.sop.common.contant.SystemConstant;
+import com.qmth.sop.common.enums.ExceptionResultEnum;
 import org.apache.commons.codec.binary.Base64;
+import org.apache.commons.codec.digest.DigestUtils;
+import org.apache.commons.io.FileUtils;
 import org.apache.commons.io.IOUtils;
+import org.apache.commons.lang3.StringUtils;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
+import org.springframework.web.multipart.MultipartFile;
 
 import javax.servlet.http.HttpServletResponse;
 import java.io.*;
+import java.net.HttpURLConnection;
+import java.net.URL;
 import java.net.URLEncoder;
+import java.nio.charset.Charset;
+import java.nio.charset.StandardCharsets;
+import java.util.Enumeration;
+import java.util.LinkedList;
+import java.util.List;
+import java.util.Objects;
+import java.util.zip.ZipEntry;
+import java.util.zip.ZipFile;
+import java.util.zip.ZipOutputStream;
 
 /**
  * @Description:
@@ -47,12 +63,494 @@ public class FileUtil {
         deleteFile(file);
     }
 
+//    public static void deleteFile(File file) {
+//        if (file.isFile() && file.exists()) {
+//            file.delete();
+//        }
+//    }
+//
+//    public static void outputFile(HttpServletResponse response, File file, String fileName) {
+//        try {
+//            if (!file.exists()) {
+//                response.sendError(404, "File not found!");
+//            }
+//
+//            BufferedInputStream br = new BufferedInputStream(new FileInputStream(file));
+//            String fName = URLEncoder.encode(fileName, SystemConstant.CHARSET_NAME);
+//
+//            response.reset();
+//            response.setContentType("application/x-msdownload");
+//            response.setHeader("Content-Disposition", "attachment; filename=" + fName);
+//            IOUtils.copy(br, response.getOutputStream());
+//            br.close();
+////            outStream.close();
+//        } catch (IOException e) {
+//            log.error(SystemConstant.LOG_ERROR, e);
+//        }
+//    }
+
+    /**
+     * 将网络文件保存到本地
+     *
+     * @param fileUrl       网络文件URL
+     * @param localFilePath 例如D:/123.txt
+     * @throws IOException
+     */
+    public static void saveUrlAsFile(String fileUrl, String localFilePath) {
+        HttpURLConnection connection = null;
+        DataOutputStream dataOutputStream = null;
+        DataInputStream dataInputStream = null;
+        try {
+            URL url = new URL(fileUrl);
+
+            connection = (HttpURLConnection) url.openConnection();
+
+            dataInputStream = new DataInputStream(connection.getInputStream());
+            FileOutputStream fileOutputStream = new FileOutputStream(localFilePath);
+            dataOutputStream = new DataOutputStream(fileOutputStream);
+
+            byte[] buffer = new byte[4096];
+            int count;
+            while ((count = dataInputStream.read(buffer)) > 0) {
+                dataOutputStream.write(buffer, 0, count);
+            }
+            fileOutputStream.flush();
+            dataOutputStream.flush();
+        } catch (IOException e) {
+            throw ExceptionResultEnum.ERROR.exception("下载文件出错" + e.getMessage());
+        } finally {
+            if (connection != null) {
+                connection.disconnect();
+            }
+            if (dataOutputStream != null) {
+                try {
+                    dataOutputStream.close();
+                } catch (IOException e) {
+                }
+            }
+            if (dataInputStream != null) {
+                try {
+                    dataInputStream.close();
+                } catch (IOException e) {
+                }
+            }
+        }
+    }
+
+    /**
+     * 将网络文件保存到本地
+     *
+     * @param fileUrl   网络文件URL
+     * @param localFile 本地文件对象
+     * @throws IOException
+     */
+    public static void saveUrlAsFile(String fileUrl, File localFile) {
+        saveUrlAsFile(fileUrl, localFile.getAbsolutePath());
+    }
+
+    /**
+     * 读取文件内容
+     *
+     * @param file
+     * @return
+     * @throws IOException
+     */
+    public static String readFileContent(File file) {
+        StringBuilder content = new StringBuilder();
+        InputStreamReader streamReader = null;
+        BufferedReader bufferedReader = null;
+        try {
+            String encoding = SystemConstant.CHARSET_NAME;
+            if (file.exists() && file.isFile()) {
+                streamReader = new InputStreamReader(new FileInputStream(file), encoding);
+                bufferedReader = new BufferedReader(streamReader);
+                String line;
+                while ((line = bufferedReader.readLine()) != null) {
+                    content.append(line);
+                }
+            }
+        } catch (IOException e) {
+            throw ExceptionResultEnum.ERROR.exception("读取文件出错" + e.getMessage());
+        } finally {
+            if (streamReader != null) {
+                try {
+                    streamReader.close();
+                } catch (IOException e) {
+                }
+            }
+            if (bufferedReader != null) {
+                try {
+                    bufferedReader.close();
+                } catch (IOException e) {
+                }
+            }
+        }
+        return content.toString();
+    }
+
+    /**
+     * 创建文件目录
+     */
+    public static boolean makeDirs(String path) {
+        if (path == null || "".equals(path)) {
+            return false;
+        }
+        File folder = new File(path);
+        if (!folder.exists()) {
+            return folder.mkdirs();
+        }
+        return true;
+    }
+
+
+    public static void saveAsFile(String path, String content, Charset encoding) {
+        if (path == null || content == null) {
+            return;
+        }
+
+        if (encoding == null) {
+            encoding = StandardCharsets.UTF_8;
+        }
+        BufferedWriter bw = null;
+        try {
+            File file = new File(path);
+            if (!file.exists()) {
+                if (makeDirs(file.getParent())) {
+                    boolean ok = file.createNewFile();
+                    if (!ok) {
+                        throw ExceptionResultEnum.ERROR.exception("文件创建失败!");
+                    }
+                }
+            }
+            IOUtils.write(content.getBytes(encoding), new FileOutputStream(file));
+        } catch (IOException e) {
+            throw ExceptionResultEnum.ERROR.exception("保存文件出错" + e.getMessage());
+        } finally {
+            if (bw != null) {
+                try {
+                    bw.close();
+                } catch (IOException e) {
+                }
+            }
+        }
+    }
+
+    /**
+     * 解压文件
+     *
+     * @param targetDir 解压目录
+     * @param zipFile   待解压的ZIP文件
+     * @throws IOException
+     */
+    public static List<File> unZip(File targetDir, File zipFile) throws IOException {
+        if (targetDir == null) {
+            throw ExceptionResultEnum.ERROR.exception("解压目录不能为空!");
+        }
+
+        if (zipFile == null) {
+            throw ExceptionResultEnum.ERROR.exception("待解压的文件不能为空!");
+        }
+
+        if (!zipFile.exists()) {
+            throw ExceptionResultEnum.ERROR.exception("待解压的文件不存在!" + zipFile.getAbsolutePath());
+        }
+
+        String zipName = zipFile.getName().toLowerCase();
+        if (zipFile.isDirectory() || zipName.indexOf(SystemConstant.ZIP_PREFIX) < 0) {
+            throw ExceptionResultEnum.ERROR.exception("待解压的文件格式错误!");
+        }
+
+        if (!targetDir.exists()) {
+            targetDir.mkdir();
+        }
+
+        List<File> result = new LinkedList<>();
+
+        try (ZipFile zip = new ZipFile(zipFile, StandardCharsets.UTF_8);) {
+
+            Enumeration entries = zip.entries();
+            while (entries.hasMoreElements()) {
+                ZipEntry entry = (ZipEntry) entries.nextElement();
+
+                // Linux中需要替换掉路径的反斜杠
+                String entryName = replaceSplit((File.separator + entry.getName()));
+
+                String filePath = targetDir.getAbsolutePath() + entryName;
+                File target = new File(filePath);
+                if (entry.isDirectory()) {
+                    target.mkdirs();
+                } else {
+                    File dir = target.getParentFile();
+                    if (!dir.exists()) {
+                        dir.mkdirs();
+                    }
+
+                    try (OutputStream os = new FileOutputStream(target); InputStream is = zip.getInputStream(entry);) {
+                        IOUtils.copy(is, os);
+                        os.flush();
+                    }
+                    result.add(target);
+                }
+            }
+
+        }
+
+        return result;
+    }
+
+    /**
+     * 文件压缩
+     *
+     * @param target 目录或文件 @param zipFile 压缩后的ZIP文件 @throws IOException @throws
+     */
+    public static boolean doZip(File target, File zipFile) throws IOException {
+        if (target == null || !target.exists()) {
+            throw ExceptionResultEnum.ERROR.exception("目录或文件不能为空!");
+        }
+
+        if (zipFile == null) {
+            throw ExceptionResultEnum.ERROR.exception("待压缩的文件不能为空!");
+        }
+
+        try (OutputStream outStream = new FileOutputStream(zipFile);
+                ZipOutputStream zipOutStream = new ZipOutputStream(outStream, StandardCharsets.UTF_8);) {
+            if (!zipFile.exists()) {
+                boolean ok = zipFile.createNewFile();
+                if (!ok) {
+                    throw ExceptionResultEnum.ERROR.exception("压缩的文件创建失败!");
+                }
+            }
+
+            if (target.isDirectory()) {
+                File[] files = target.listFiles();
+                if (files.length == 0) {
+                    throw ExceptionResultEnum.ERROR.exception("文件夹内未找到任何文件!");
+                }
+
+                for (File file : files) {
+                    doZip(zipOutStream, file, null);
+                }
+            } else {
+                doZip(zipOutStream, target, null);
+            }
+        }
+
+        return true;
+    }
+
+    /**
+     * @param resultFile
+     * @param sourseFiles
+     * @return
+     * @throws IOException
+     */
+    public static boolean doZip(File resultFile, List<File> sourseFiles) {
+        if (sourseFiles == null || sourseFiles.size() == 0) {
+            throw ExceptionResultEnum.ERROR.exception("待压缩的文件不能为空!");
+        }
+
+        if (resultFile == null) {
+            throw ExceptionResultEnum.ERROR.exception("压缩后的文件不能为空!");
+        }
+        ZipOutputStream zipOutStream = null;
+        try {
+            OutputStream outStream = new FileOutputStream(resultFile);
+            zipOutStream = new ZipOutputStream(outStream, StandardCharsets.UTF_8);
+            if (!resultFile.exists()) {
+                boolean ok = resultFile.createNewFile();
+                if (!ok) {
+                    throw ExceptionResultEnum.ERROR.exception("压缩的文件创建失败!");
+                }
+            }
+
+            for (File file : sourseFiles) {
+                doZip(zipOutStream, file, null);
+            }
+        } catch (IOException e) {
+            throw ExceptionResultEnum.ERROR.exception("压缩的文件创建失败!" + e.getMessage());
+        } finally {
+            if (zipOutStream != null) {
+                try {
+                    zipOutStream.close();
+                } catch (IOException e) {
+                }
+            }
+        }
+
+        return true;
+    }
+
+    private static void doZip(ZipOutputStream zipOutStream, File target, String parentDir) throws IOException {
+        if (parentDir == null) {
+            parentDir = "";
+        }
+
+        if (!"".equals(parentDir) && !parentDir.endsWith(File.separator)) {
+            parentDir += File.separator;
+        }
+
+        if (target.isDirectory()) {
+            File[] files = target.listFiles();
+            if (files.length > 0) {
+                for (File file : files) {
+                    doZip(zipOutStream, file, parentDir + target.getName());
+                }
+            } else {
+                zipOutStream.putNextEntry(new ZipEntry(parentDir + target.getName()));
+                zipOutStream.closeEntry();
+            }
+        } else {
+            try (InputStream is = new FileInputStream(target);) {
+                zipOutStream.putNextEntry(new ZipEntry(parentDir + target.getName()));
+                int len;
+                byte[] bytes = new byte[1024];
+                while ((len = is.read(bytes)) > 0) {
+                    zipOutStream.write(bytes, 0, len);
+                }
+            }
+            zipOutStream.closeEntry();
+        }
+    }
+
+    public static void deleteFolder(String path) {
+
+        File file = new File(path);
+        if (file.exists()) {
+            if (file.isFile()) {
+                deleteFile(path);
+            } else {
+                deleteDirectory(path);
+            }
+        }
+    }
+
+//    public static void deleteFile(String path) {
+//        File file = new File(path);
+//        deleteFile(file);
+//    }
+
     public static void deleteFile(File file) {
         if (file.isFile() && file.exists()) {
             file.delete();
         }
     }
 
+    public static void deleteDirectory(File dirFile) {
+        if (!dirFile.exists() || !dirFile.isDirectory()) {
+            return;
+        }
+        File[] files = dirFile.listFiles();
+        if (files != null) {
+            for (int i = 0; i < files.length; i++) {
+                if (files[i].isFile()) {
+                    deleteFile(files[i]);
+                } else {
+                    deleteDirectory(files[i]);
+                }
+            }
+        }
+
+        dirFile.delete();
+    }
+
+    public static void deleteDirectory(String path) {
+        if (!path.endsWith(File.separator)) {
+            path = path + File.separator;
+        }
+        File dirFile = new File(path);
+        deleteDirectory(dirFile);
+    }
+
+    /**
+     * 文件转数组
+     *
+     * @param file
+     * @return
+     * @throws IOException
+     */
+    public static byte[] fileConvertToByteArray(File file) throws IOException {
+        byte[] data = null;
+        FileInputStream fis = null;
+        ByteArrayOutputStream baos = null;
+        try {
+            fis = new FileInputStream(file);
+            baos = new ByteArrayOutputStream();
+            int len;
+            byte[] buffer = new byte[1024];
+            while ((len = fis.read(buffer)) != -1) {
+                baos.write(buffer, 0, len);
+            }
+            data = baos.toByteArray();
+        } catch (Exception e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+        } finally {
+            if (Objects.nonNull(fis)) {
+                fis.close();
+            }
+            if (Objects.nonNull(baos)) {
+                baos.flush();
+                baos.close();
+            }
+        }
+        return data;
+    }
+
+    public static File multipartFileToFile(MultipartFile file) throws Exception {
+
+        File toFile = null;
+        if (file.equals("") || file.getSize() <= 0) {
+            file = null;
+        } else {
+            InputStream ins = null;
+            ins = file.getInputStream();
+            toFile = new File(file.getOriginalFilename());
+            inputStreamToFile(ins, toFile);
+            ins.close();
+        }
+        return toFile;
+    }
+
+    //获取流文件
+    private static void inputStreamToFile(InputStream ins, File file) {
+        try {
+            OutputStream os = new FileOutputStream(file);
+            int bytesRead = 0;
+            byte[] buffer = new byte[8192];
+            while ((bytesRead = ins.read(buffer, 0, 8192)) != -1) {
+                os.write(buffer, 0, bytesRead);
+            }
+            os.close();
+            ins.close();
+        } catch (Exception e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+        }
+    }
+
+    /**
+     * 复制文件
+     *
+     * @param sourceFileName 源文件
+     * @param destFileName   目标文件
+     */
+    public static void copyFile(String sourceFileName, String destFileName) {
+        try {
+            File sourceFile = new File(sourceFileName);
+            if (!sourceFile.exists()) {
+                throw ExceptionResultEnum.ERROR.exception("源文件" + sourceFileName + "不存在");
+            }
+
+            File desFile = new File(destFileName);
+            if (!desFile.exists()) {
+                desFile.getParentFile().mkdirs(); //目标文件目录不存在的话需要创建目录
+                desFile.createNewFile();
+            }
+
+            FileUtils.copyFile(sourceFile, desFile);
+        } catch (IOException e) {
+            throw ExceptionResultEnum.ERROR.exception(e.getMessage());
+        }
+    }
+
     public static void outputFile(HttpServletResponse response, File file, String fileName) {
         try {
             if (!file.exists()) {
@@ -72,4 +570,187 @@ public class FileUtil {
             log.error(SystemConstant.LOG_ERROR, e);
         }
     }
+
+    public static void outputFile(HttpServletResponse response, InputStream inputStream, String fileName) {
+        try {
+            BufferedInputStream br = new BufferedInputStream(inputStream);
+            fileName = fileName.replaceAll("/", "\\\\");
+            String fName = URLEncoder.encode(fileName, SystemConstant.CHARSET_NAME);
+
+            response.reset();
+            response.setContentType("application/x-msdownload");
+            response.setHeader("Content-Disposition", "attachment; filename=" + fName);
+            IOUtils.copy(br, response.getOutputStream());
+            br.close();
+            //            outStream.close();
+        } catch (IOException e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+        }
+    }
+
+    public static InputStream getStream(String path) {
+        try {
+            ClassLoader classLoader = FileUtil.class.getClassLoader();
+            URL url = classLoader.getResource(path);
+            return url.openStream();
+        } catch (Exception e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    /**
+     * 将路径中的双"//"替换成单"/"
+     *
+     * @param path 文件路径
+     * @return string
+     */
+    public static String replaceSplit(String path) {
+        return path.replaceAll("\\\\", SystemConstant.ORG_SPLIT);
+    }
+
+    public static String md5File(File file) {
+        try {
+            return md5File(new FileInputStream(file));
+        } catch (IOException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    public static String md5File(InputStream inputStream) {
+        try {
+            return DigestUtils.md5Hex(inputStream);
+        } catch (IOException e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    /**
+     * 获取临时文件根目录
+     *
+     * @param containNanoId 是否使用NanoId创建子目录
+     * @return 文件路径
+     */
+    public static String getFileTempDirPath(Boolean containNanoId) {
+        File fileTmpDir;
+        try {
+            if (containNanoId) {
+                fileTmpDir = new File(System.getProperty(SystemConstant.TMP_DIR), SystemConstant.getNanoId());
+            } else {
+                fileTmpDir = new File(System.getProperty(SystemConstant.TMP_DIR));
+            }
+            if (!fileTmpDir.exists()) {
+                fileTmpDir.mkdirs();
+            }
+            log.info("getFileTempDirPath_path:{}", fileTmpDir.getPath());
+            return fileTmpDir.getPath();
+        } catch (Exception e) {
+            throw new RuntimeException(e);
+        }
+    }
+
+    /**
+     * 生成文本文件
+     *
+     * @param file    目标文件
+     * @param content 文件内容
+     */
+    public static File writeContent(File file, String content) {
+        try {
+            if (!file.exists()) {
+                file.getParentFile().mkdirs();
+                file.createNewFile();
+            }
+            IOUtils.write(content.getBytes(StandardCharsets.UTF_8), new FileOutputStream(file));
+        } catch (Exception e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+        }
+        return file;
+    }
+
+    /**
+     * 下载加密zip文件
+     *
+     * @param response         response
+     * @param downloadPathFile 压缩文件所在文件夹路径
+     * @param zipFileName      压缩zip文件路径+文件名
+     */
+    public static void downloadEncryptZip(HttpServletResponse response, File downloadPathFile, String zipFileName, String password) {
+        if (StringUtils.isBlank(password)) {
+            password = SystemConstant.ZIP_ENCRYPT_PWD;
+        }
+        // 压缩zip文件和图片保存文件夹放在同一级
+        File zipFile = new File(downloadPathFile.getParent(), zipFileName);
+        try {
+            // 压缩zip文件路径+文件名
+            String zipFilePath = zipFile.getPath();
+            // 待压缩文件所在文件夹
+            String zipFilesPath = downloadPathFile.getPath();
+            Zip4jUtil.zipEncryptFile(zipFilePath, zipFilesPath, password);
+            FileUtil.outputFile(response, zipFile, zipFile.getName());
+        } catch (Exception e) {
+            throw ExceptionResultEnum.ERROR.exception("下载失败");
+        }
+    }
+
+    /**
+     * 下载加密zip文件
+     *
+     * @param downloadPathFile 压缩文件所在文件夹路径
+     * @param zipFileName      压缩zip文件路径+文件名
+     */
+    public static void downloadEncryptZip(File downloadPathFile, String zipFileName, String password) {
+        if (StringUtils.isBlank(password)) {
+            password = SystemConstant.ZIP_ENCRYPT_PWD;
+        }
+        // 压缩zip文件和图片保存文件夹放在同一级
+        File zipFile = new File(downloadPathFile.getParent(), zipFileName);
+        try {
+            // 压缩zip文件路径+文件名
+            String zipFilePath = zipFile.getPath();
+            // 待压缩文件所在文件夹
+            String zipFilesPath = downloadPathFile.getPath();
+            Zip4jUtil.zipEncryptFile(zipFilePath, zipFilesPath, password);
+        } catch (Exception e) {
+            throw ExceptionResultEnum.ERROR.exception("下载失败");
+        }
+    }
+
+//    /**
+//     * @param zipLocalRootPath
+//     * @param zipDirName
+//     * @param password
+//     * @return
+//     * @throws Exception
+//     */
+//    public static JSONObject uploadEncryptZip(String zipLocalRootPath, String zipDirName, String password) throws Exception {
+//        if (StringUtils.isBlank(password)) {
+//            password = SystemConstant.ZIP_ENCRYPT_PWD;
+//        }
+//
+//        File zipFile = SystemConstant.getFileTempDirVar(SystemConstant.ZIP_PREFIX);
+//
+//        try {
+//            FileStoreUtil fileStoreUtil = SpringContextHolder.getBean(FileStoreUtil.class);
+//            DictionaryConfig dictionaryConfig = SpringContextHolder.getBean(DictionaryConfig.class);
+//            Zip4jUtil.zipEncryptFile(zipFile.getPath(), zipLocalRootPath, password);
+//
+//            boolean oss = dictionaryConfig.sysDomain().isOss();
+//            JSONObject jsonObject = new JSONObject();
+//            jsonObject.put(SystemConstant.PATH, zipDirName);
+//            String zipFileMd5 = DigestUtils.md5Hex(new FileInputStream(zipFile));
+//            if (oss || (!oss && dictionaryConfig.fssPrivateDomain().getConfig().startsWith(SystemConstant.START_PARENT))) {//上传至oss
+//                fileStoreUtil.ossUpload(zipDirName, zipFile, zipFileMd5, fileStoreUtil.getUploadEnumByPath(zipDirName).getFssType());
+//                jsonObject.put(SystemConstant.TYPE, oss ? SystemConstant.OSS : SystemConstant.LOCAL);
+//            } else {
+//                fileStoreUtil.localUpload(zipDirName, new FileInputStream(zipFile), zipFileMd5, LocalCatalogEnum.LOCAL_FILE);
+//                jsonObject.put(SystemConstant.TYPE, SystemConstant.LOCAL);
+//            }
+//            jsonObject.put(SystemConstant.UPLOAD_TYPE, UploadFileEnum.FILE);
+//            return jsonObject;
+//        } catch (Exception e) {
+//            throw new RuntimeException(e);
+//        } finally {
+//            FileUtil.deleteFile(zipFile);
+//        }
+//    }
 }

+ 208 - 0
sop-common/src/main/java/com/qmth/sop/common/util/Zip4jUtil.java

@@ -0,0 +1,208 @@
+package com.qmth.sop.common.util;
+
+import cn.hutool.core.collection.CollectionUtil;
+import com.qmth.sop.common.contant.SystemConstant;
+import com.qmth.sop.common.enums.ExceptionResultEnum;
+import net.lingala.zip4j.core.ZipFile;
+import net.lingala.zip4j.exception.ZipException;
+import net.lingala.zip4j.model.ZipParameters;
+import net.lingala.zip4j.util.Zip4jConstants;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.springframework.util.CollectionUtils;
+
+import java.io.File;
+import java.util.List;
+import java.util.Objects;
+import java.util.Optional;
+
+/**
+ * @Description: zip4j工具
+ * @Param:
+ * @return:
+ * @Author: wangliang
+ * @Date: 2022/8/12
+ */
+public class Zip4jUtil {
+
+    private final static Logger log = LoggerFactory.getLogger(Zip4jUtil.class);
+
+    /**
+     * 压缩zip
+     *
+     * @param scrPath
+     * @param files
+     */
+    public static void zipFile(String scrPath, List<File> files) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        if (!scrPath.endsWith(SystemConstant.ZIP_PREFIX)) {
+            throw ExceptionResultEnum.ERROR.exception("压缩文件必须为zip");
+        }
+        if (CollectionUtils.isEmpty(files)) {
+            throw ExceptionResultEnum.ERROR.exception("没有待压缩的文件");
+        }
+        commonZipFile(scrPath, null, files, null);
+    }
+
+    /**
+     * 压缩zip
+     *
+     * @param scrPath
+     * @param destPath
+     */
+    public static void zipFile(String scrPath, String destPath) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        if (!scrPath.endsWith(SystemConstant.ZIP_PREFIX)) {
+            throw ExceptionResultEnum.ERROR.exception("压缩文件必须为zip");
+        }
+        Optional.ofNullable(destPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("压缩路径不能为空"));
+        commonZipFile(scrPath, destPath, null, null);
+    }
+
+    /**
+     * 压缩zip带密码
+     *
+     * @param scrPath
+     * @param files
+     * @param password
+     * @throws ZipException
+     */
+    public static void zipEncryptFile(String scrPath, List<File> files, String password) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        if (!scrPath.endsWith(SystemConstant.ZIP_PREFIX)) {
+            throw ExceptionResultEnum.ERROR.exception("压缩文件必须为zip");
+        }
+        if (CollectionUtils.isEmpty(files)) {
+            throw ExceptionResultEnum.ERROR.exception("没有待压缩的文件");
+        }
+        Optional.ofNullable(password).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("压缩密码不能为空"));
+        commonZipFile(scrPath, null, files, password);
+    }
+
+    /**
+     * 压缩zip带密码
+     *
+     * @param scrPath
+     * @param destPath
+     * @param password
+     */
+    public static void zipEncryptFile(String scrPath, String destPath, String password) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        if (!scrPath.endsWith(SystemConstant.ZIP_PREFIX)) {
+            throw ExceptionResultEnum.ERROR.exception("压缩文件必须为zip");
+        }
+        Optional.ofNullable(destPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("压缩路径不能为空"));
+        Optional.ofNullable(password).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("压缩密码不能为空"));
+        commonZipFile(scrPath, destPath, null, password);
+    }
+
+    /**
+     * 解压zip
+     *
+     * @param scrPath
+     * @param destPath
+     */
+    public static void unzip(String scrPath, String destPath) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        Optional.ofNullable(destPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("解压路径不能为空"));
+        commonUnZipFile(scrPath, destPath, null);
+    }
+
+    /**
+     * 解压zip带密码
+     *
+     * @param scrPath
+     * @param destPath
+     * @param password
+     */
+    public static void unzipEncryptFile(String scrPath, String destPath, String password) {
+        Optional.ofNullable(scrPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("原始路径不能为空"));
+        Optional.ofNullable(destPath).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("解压路径不能为空"));
+        Optional.ofNullable(password).orElseThrow(() -> ExceptionResultEnum.ERROR.exception("解压密码不能为空"));
+        commonUnZipFile(scrPath, destPath, password);
+    }
+
+    /**
+     * 解压zip包
+     *
+     * @param scrPath
+     * @param destPath
+     * @param password
+     */
+    private static void commonUnZipFile(String scrPath, String destPath, String password) {
+        try {
+            File file = new File(scrPath);
+            if (!file.exists()) {
+                file.getParentFile().mkdirs();
+            }
+            ZipFile zipFile = new ZipFile(scrPath);
+            if (Objects.nonNull(password) && zipFile.isEncrypted()) {
+                zipFile.setPassword(password);
+            }
+            File currentFile = new File(destPath);
+            if (!currentFile.exists()) {
+                currentFile.getParentFile().mkdirs();
+                //                throw ExceptionResultEnum.ERROR.exception("待解压的路径不存在");
+            }
+            zipFile.extractAll(destPath);
+        } catch (ZipException e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+            throw ExceptionResultEnum.ERROR.exception(e.getMessage());
+        }
+    }
+
+    /**
+     * 压缩zip包
+     *
+     * @param scrPath
+     * @param destPath
+     * @param files
+     * @param password
+     */
+    private static void commonZipFile(String scrPath, String destPath, List<File> files, String password) {
+        try {
+            File file = new File(scrPath);
+            if (!file.exists()) {
+                file.getParentFile().mkdirs();
+            }
+            // 生成的压缩文件
+            ZipFile zipFile = new ZipFile(scrPath);
+            //            zipFile.setFileNameCharset("UTF-8");
+            ZipParameters parameters = new ZipParameters();
+            // 压缩级别
+            parameters.setCompressionMethod(Zip4jConstants.COMP_DEFLATE);
+            // 压缩级别
+            parameters.setCompressionLevel(Zip4jConstants.DEFLATE_LEVEL_NORMAL);
+            if (Objects.nonNull(password)) {
+                parameters.setEncryptFiles(true);
+                parameters.setEncryptionMethod(Zip4jConstants.ENC_METHOD_AES);
+                parameters.setAesKeyStrength(Zip4jConstants.AES_STRENGTH_256);
+                parameters.setPassword(password);
+            }
+
+            File[] fs = null;
+            if (!CollectionUtil.isEmpty(files)) {
+                // 要打包的文件夹
+                fs = files.toArray(new File[files.size()]);
+            } else if (Objects.nonNull(destPath)) {
+                File currentFile = new File(destPath);
+                if (!currentFile.exists()) {
+                    throw ExceptionResultEnum.ERROR.exception("待压缩的路径不存在");
+                }
+                fs = currentFile.listFiles();
+            }
+
+            // 遍历test文件夹下所有的文件、文件夹
+            for (File f : fs) {
+                if (f.isDirectory()) {
+                    zipFile.addFolder(f.getPath(), parameters);
+                } else {
+                    zipFile.addFile(f, parameters);
+                }
+            }
+        } catch (Exception e) {
+            log.error(SystemConstant.LOG_ERROR, e);
+            throw ExceptionResultEnum.ERROR.exception(e.getMessage());
+        }
+    }
+}