Article directory
- Preface
- Controller
- IService
- ServiceImpl
- FileUtil
Foreword
There is a function to upload files on the page. You can create a new directory and upload files under the directory, as shown in the figure:
Tips: Select the directory and click Package Download to export the folders and files in the directory into zips according to the hierarchy. If no task directory or file is selected, all directories and files will be compressed into zips according to the hierarchy
Controller
@ApiOperation(value = "Package download") @GetMapping(value = "/downloadZip") public void downloadZip(@ApiParam(name = "id", value= "project id/directory id/file id", required = true) @RequestParam(value = "id") Long id, HttpServletResponse response) throws Exception {<! -- --> projectMaterialsCatalogService.downloadZip(id, response); }
IService
/** * Download package * * @param id directory id or file id * @param response * @throwsException */ void downloadZip(Long id, HttpServletResponse response) throws Exception;
ServiceImpl
/** * Download package * * @param id directory id or file id * @param response * @throwsException */ @Override public void downloadZip(Long id, HttpServletResponse response) throws Exception {<!-- --> // First determine whether it is a project, and directly check the directory based on the project ID. LambdaQueryWrapper<ProjectMaterialsCatalog> queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(ProjectMaterialsCatalog::getBusinessId, id); queryWrapper.eq(ProjectMaterialsCatalog::getIsDeleted, "0"); List<ProjectMaterialsCatalog> projectMaterialsCatalogs = baseMapper.selectList(queryWrapper); //Generated ZIP file path String zipFilePath = ""; //Generated temporary folder hierarchy String temFolderPath = ""; // If it is a project ID, all directory data needs to be packaged and downloaded. if (CollectionUtils.isNotEmpty(projectMaterialsCatalogs)) {<!-- --> //Multiple level 1 folders are placed under the temporary folder, with the current project ID as the folder temFolderPath = filesPath + File.separator + id; for (ProjectMaterialsCatalog catalog : projectMaterialsCatalogs) {<!-- --> //Create the directory first and then create the file String catalogName = catalog.getCatalogName(); // First generate the folder containing hierarchical structure based on the directory genCatalog(catalog, temFolderPath + File.separator + catalogName); } zipFilePath = temFolderPath + ".zip"; //Compress the generated folder FileUtil.folderToZip(zipFilePath, temFolderPath, true); } else {<!-- --> // Then determine whether it is a directory or a file ProjectMaterialsCatalog catalog = baseMapper.selectById(id); if (catalog != null) {<!-- --> //Create the directory first and then create the file String catalogName = catalog.getCatalogName(); temFolderPath = filesPath + File.separator + catalogName; zipFilePath = temFolderPath + ".zip"; // First generate the folder containing hierarchical structure based on the directory genCatalog(catalog, temFolderPath); //Compress the generated folder FileUtil.folderToZip(zipFilePath, temFolderPath, true); } else {<!-- --> // The description is a file, package this file into zip ProjectMaterialsFiles fileInfo = projectMaterialsFilesMapper.selectById(id); // Get file path String filePath = filesPath + File.separator + fileInfo.getFilePath(); // Get the file name prefix String prefix = cn.hutool.core.io.FileUtil.getPrefix(fileInfo.getFileName()); //Generated ZIP file path zipFilePath = filesPath + File.separator + prefix + ".zip"; //Compress the file List<File> fileList = new ArrayList<>(); fileList.add(new File(filePath)); FileUtil.fileToZip(zipFilePath, fileList); } } try {<!-- --> // Download the generated file zip File zipFile = new File(zipFilePath); response.setCharacterEncoding("UTF-8"); response.setContentType("application/zip"); response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode(zipFile.getName(), "UTF-8")); InputStream in = new FileInputStream(zipFile); // Obtain the output stream - the output stream obtained through response is used to write content to the client ServletOutputStream out = response.getOutputStream(); //File copy code int len = 0; byte[] buffer = new byte[1024]; while ((len = in.read(buffer)) != -1) {<!-- --> out.write(buffer, 0, len); } out.flush(); out.close(); in.close(); response.flushBuffer(); } catch (IOException e) {<!-- --> throw new RuntimeException(e); } finally {<!-- --> // Delete compressed package cn.hutool.core.io.FileUtil.del(zipFilePath); //Delete the created folder if (StringUtils.isNotBlank(temFolderPath)) {<!-- --> cn.hutool.core.io.FileUtil.del(temFolderPath); } } } /** * Recursively generate folders and files * * @param rootCatalog * @param catalogPath */ public void genCatalog(ProjectMaterialsCatalog rootCatalog, String catalogPath) throws Exception {<!-- --> File file = new File(catalogPath); if (!file.exists()) {<!-- --> file.mkdirs(); } // Determine whether there are files in the directory List<ProjectMaterialsFiles> filesList = projectMaterialsFilesMapper.getFileByCatalogId(rootCatalog.getId()); if (CollectionUtils.isNotEmpty(filesList)) {<!-- --> // Loop to create files in this directory for (ProjectMaterialsFiles f : filesList) {<!-- --> File sourceFile = new File(filesPath + File.separator + f.getFilePath()); //The source file does not exist if (!sourceFile.exists()) {<!-- --> continue; } File destFile = new File(catalogPath + File.separator + f.getFileName()); Files.copy(sourceFile, destFile); } } LambdaQueryWrapper<ProjectMaterialsCatalog> queryWrapper = new LambdaQueryWrapper<>(); queryWrapper.eq(ProjectMaterialsCatalog::getIsDeleted, "0"); queryWrapper.eq(ProjectMaterialsCatalog::getParentId, rootCatalog.getId()); List<ProjectMaterialsCatalog> catalogList = baseMapper.selectList(queryWrapper); if (CollectionUtils.isNotEmpty(catalogList)) {<!-- --> for (ProjectMaterialsCatalog catalog : catalogList) {<!-- --> catalogPath + = File.separator + catalog.getCatalogName(); genCatalog(catalog, catalogPath); } } }
FileUtil
/** * Compress the folder into ZIP * * @param zipFileName Generate compressed folder path * @param sourceFileName The file path to be compressed * @param KeepDirStructure Whether to retain the original directory structure, true: retain the directory structure; * false: All files run to the root directory of the compressed package (note: files with the same name may appear if the directory structure is not retained, and the compression will fail) * @throws RuntimeException If compression fails, a runtime exception will be thrown */ public static Boolean folderToZip(String zipFileName, String sourceFileName, boolean KeepDirStructure) {<!-- --> Boolean result = true; long start = System.currentTimeMillis();//Start ZipOutputStream zos = null; try {<!-- --> FileOutputStream fileOutputStream = new FileOutputStream(zipFileName); zos = new ZipOutputStream(fileOutputStream); File sourceFile = new File(sourceFileName); compress(sourceFile, zos, sourceFile.getName(), KeepDirStructure); long end = System.currentTimeMillis();//End System.out.println("Compression completed, time taken: " + (end - start) + " milliseconds"); } catch (Exception e) {<!-- --> result = false; e.printStackTrace(); } finally {<!-- --> if (zos != null) {<!-- --> try {<!-- --> zos.close(); } catch (IOException e) {<!-- --> e.getStackTrace(); } } } return result; } /** * Compress files into ZIP to compress multiple files at once * * @param srcFiles list of files to be compressed * @param zipFileName compressed file output * @throws RuntimeException If compression fails, a runtime exception will be thrown */ public static void fileToZip(String zipFileName, List<File> srcFiles) throws Exception {<!-- --> long start = System.currentTimeMillis(); ZipOutputStream zos = null; try {<!-- --> FileOutputStream fileOutputStream = new FileOutputStream(zipFileName); zos = new ZipOutputStream(fileOutputStream); for (File srcFile : srcFiles) {<!-- --> compress(srcFile, zos, srcFile.getName(), true); } long end = System.currentTimeMillis(); System.out.println("Compression completed, time taken: " + (end - start) + " milliseconds"); } catch (Exception e) {<!-- --> throw new RuntimeException("zip error from ZipUtils", e); } finally {<!-- --> if (zos != null) {<!-- --> try {<!-- --> zos.close(); } catch (IOException e) {<!-- --> e.printStackTrace(); } } } } /** * Recursive compression method * * @param sourceFile source file * @param zos zip output stream * @param name compressed name * @param KeepDirStructure Whether to retain the original directory structure, true: retain the directory structure; * false: All files run to the root directory of the compressed package (note: files with the same name may appear if the directory structure is not retained, and the compression will fail) * @throwsException */ public static void compress(File sourceFile, ZipOutputStream zos, String name, boolean KeepDirStructure) throws Exception {<!-- --> if (sourceFile.isFile()) {<!-- --> //Add a zip entity to the zip output stream. The name in the constructor is the name of the file of the zip entity. zos.putNextEntry(new ZipEntry(name)); // copy the file to the zip output stream int len; byte[] buf = new byte[1024]; FileInputStream in = new FileInputStream(sourceFile); while ((len = in.read(buf)) != -1) {<!-- --> zos.write(buf, 0, len); } // Complete the entry zos.closeEntry(); in.close(); } else {<!-- --> File[] listFiles = sourceFile.listFiles(); if (listFiles == null || listFiles.length == 0) {<!-- --> // When you need to retain the original file structure, you need to process the empty folder if (KeepDirStructure) {<!-- --> //Handling of empty folders zos.putNextEntry(new ZipEntry(name + "/")); // There is no file, no copy of the file is required zos.closeEntry(); } } else {<!-- --> for (File file : listFiles) {<!-- --> // Determine whether the original file structure needs to be retained if (KeepDirStructure) {<!-- --> // Note: file.getName() needs to be preceded by the name of the parent folder plus a slash. // Otherwise, the original file structure cannot be retained in the final compressed package, that is: all files will go to the root directory of the compressed package. compress(file, zos, name + "/" + file.getName(), KeepDirStructure); } else {<!-- --> compress(file, zos, file.getName(), KeepDirStructure); } } } } }