Java文件上传解压

目录结构

在这里插入图片描述

工具类

枚举

定义文件类型

public enum FileType {// 未知UNKNOWN,// 压缩文件ZIP, RAR, _7Z, TAR, GZ, TAR_GZ, BZ2, TAR_BZ2,// 位图文件BMP, PNG, JPG, JPEG,// 矢量图文件SVG,// 影音文件AVI, MP4, MP3, AAR, OGG, WAV, WAVE}

为了避免文件被修改后缀,所以这里创建了一个获取文件的真实类型工具类

import com.zipfile.zipenum.FileType;
import org.springframework.stereotype.Component;import java.io.File;
import java.io.IOException;
import java.io.InputStream;@Component
public class fileTypes {public static FileType getFileType(InputStream inputStream){
//        FileInputStream inputStream =null;try{
//            inputStream = new FileInputStream(file);byte[] head = new byte[4];if (-1 == inputStream.read(head)) {return FileType.UNKNOWN;}int headHex = 0;for (byte b : head) {headHex <<= 8;headHex |= b;}switch (headHex) {case 0x504B0304:return FileType.ZIP;case 0x776f7264:return FileType.TAR;case -0x51:return FileType._7Z;case 0x425a6839:return FileType.BZ2;case -0x74f7f8:return FileType.GZ;case 0x52617221:return FileType.RAR;default:return FileType.UNKNOWN;}}catch (Exception e){e.printStackTrace();}finally {try {if(inputStream!=null){inputStream.close();}} catch (IOException e) {e.printStackTrace();}}return FileType.UNKNOWN;}

解压压缩包的工具类


import org.apache.commons.compress.archivers.tar.TarArchiveEntry;
import org.apache.commons.compress.archivers.tar.TarArchiveInputStream;
import org.apache.commons.compress.archivers.sevenz.SevenZArchiveEntry;
import org.apache.commons.compress.archivers.sevenz.SevenZFile;
import com.github.junrar.Archive;
import com.github.junrar.exception.RarException;
import com.github.junrar.rarfile.FileHeader;
import org.springframework.stereotype.Component;import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.io.FileOutputStream;
import java.io.InputStream;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;//@Component
public class decompression {/*** 解压缩tar文件* @param file 压缩包文件* @param targetPath 目标文件夹* @param delete 解压后是否删除原压缩包文件*/public static void decompressTar(File file, String targetPath, boolean delete) {try (FileInputStream fis = new FileInputStream(file);TarArchiveInputStream tarInputStream = new TarArchiveInputStream(fis)) {// 创建输出目录Path outputDir = Paths.get(targetPath);if (!Files.exists(outputDir)) {Files.createDirectories(outputDir);}TarArchiveEntry entry;while ((entry = tarInputStream.getNextTarEntry()) != null) {Path entryPath = outputDir.resolve(entry.getName());if (entry.isDirectory()) {Files.createDirectories(entryPath); // 创建子目录} else {Files.createDirectories(entryPath.getParent()); // 确保父目录存在try (OutputStream fos = Files.newOutputStream(entryPath)) {byte[] buffer = new byte[2048];int count;while ((count = tarInputStream.read(buffer)) != -1) {fos.write(buffer, 0, count);}}}}// 如果需要删除原始文件if (delete) {Files.delete(file.toPath());}} catch (IOException e) {e.printStackTrace();}}/*** 解压缩7z文件* @param file 压缩包文件* @param targetPath 目标文件夹* @param delete 解压后是否删除原压缩包文件*//*** 解压 7z 文件** @param file       压缩包文件* @param targetPath 目标文件夹* @param delete     解压后是否删除原压缩包文件*/public static void decompress7Z(File file, String targetPath, boolean delete) {try (SevenZFile sevenZFile = new SevenZFile(file)) { // 自动关闭资源// 创建输出目录Path outputDir = Paths.get(targetPath);if (!Files.exists(outputDir)) {Files.createDirectories(outputDir);}SevenZArchiveEntry entry;while ((entry = sevenZFile.getNextEntry()) != null) {Path entryPath = outputDir.resolve(entry.getName());if (entry.isDirectory()) {Files.createDirectories(entryPath); // 创建子目录} else {Files.createDirectories(entryPath.getParent()); // 确保父目录存在try (OutputStream outputStream = new FileOutputStream(entryPath.toFile())) {byte[] buffer = new byte[2048];int len;while ((len = sevenZFile.read(buffer)) != -1) {outputStream.write(buffer, 0, len);}}}}// 删除原始文件(可选)if (delete) {Files.delete(file.toPath());}} catch (IOException e) {e.printStackTrace();}}/*** 解压 RAR 文件** @param file       压缩包文件* @param targetPath 目标文件夹* @param delete     解压后是否删除原压缩包文件*/public static void decompressRAR(File file, String targetPath, boolean delete) {try (Archive archive = new Archive(file)) { // 自动关闭资源// 创建输出目录Path outputDir = Paths.get(targetPath);if (!Files.exists(outputDir)) {Files.createDirectories(outputDir);}FileHeader fileHeader;while ((fileHeader = archive.nextFileHeader()) != null) {String fileName = fileHeader.getFileNameString().trim();Path filePath = outputDir.resolve(fileName);if (fileHeader.isDirectory()) {Files.createDirectories(filePath); // 创建子目录} else {Files.createDirectories(filePath.getParent()); // 确保父目录存在try (OutputStream outputStream = new FileOutputStream(filePath.toFile())) {archive.extractFile(fileHeader, outputStream);}}}// 如果需要删除原始文件if (delete) {Files.delete(file.toPath());}} catch (RarException | IOException e) {e.printStackTrace();}}/*** 解压 ZIP 文件** @param file       ZIP 文件* @param targetPath 目标文件夹* @param delete     解压后是否删除原压缩包文件*/public static void decompressZIP(File file, String targetPath, boolean delete) {try (InputStream fis = Files.newInputStream(file.toPath());ZipInputStream zipInputStream = new ZipInputStream(fis)) {// 创建输出目录Path outputDir = Paths.get(targetPath);if (!Files.exists(outputDir)) {Files.createDirectories(outputDir);}ZipEntry entry;while ((entry = zipInputStream.getNextEntry()) != null) {Path entryPath = outputDir.resolve(entry.getName());if (entry.isDirectory()) {Files.createDirectories(entryPath); // 创建子目录} else {Files.createDirectories(entryPath.getParent()); // 确保父目录存在try (FileOutputStream fos = new FileOutputStream(entryPath.toFile())) {byte[] buffer = new byte[2048];int len;while ((len = zipInputStream.read(buffer)) != -1) {fos.write(buffer, 0, len);}}}zipInputStream.closeEntry();}// 如果需要删除原始文件if (delete) {Files.delete(file.toPath());}} catch (IOException e) {e.printStackTrace();}}
}

控制层

这里使用接口的方式,接受前端传过来的文件


import com.zipfile.service.ZipService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;import java.io.IOException;@RestController
@RequestMapping("zipUpload/")
public class ZipController {@Autowiredprivate ZipService zipService;@PostMapping("upload")public void zipUpload(@RequestParam("file") MultipartFile file) throws IOException {zipService.upload(file);}}

实现类


import com.zipfile.decompression.decompression;
import com.zipfile.util.fileTypes;
import com.zipfile.zipenum.FileType;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;import java.io.File;
import java.io.IOException;import static com.zipfile.zipenum.FileType.ZIP;@Service
public class ZipServiceImpl implements ZipService {@Autowiredprivate fileTypes fileTypes;@Overridepublic void upload(MultipartFile file) throws IOException {FileType fileType = fileTypes.getFileType(file.getInputStream());System.out.println(fileType);if (fileType == ZIP){// 创建临时文件File tempFile = convertToFile(file);decompression.decompressZIP(tempFile,"E:\\",true);}}private File convertToFile(MultipartFile file) throws IOException {// 获取文件的原始文件名String originalFilename = file.getOriginalFilename();if (originalFilename == null) {throw new IOException("文件名为空!");}// 创建临时文件String prefix = originalFilename.substring(0, originalFilename.lastIndexOf('.'));String suffix = originalFilename.substring(originalFilename.lastIndexOf('.'));File tempFile = File.createTempFile(prefix, suffix);// 将 MultipartFile 的数据写入临时文件file.transferTo(tempFile);return tempFile;}}

依赖包

这是用到的依赖包

  <!-- tar 解压--><dependency><groupId>org.apache.commons</groupId><artifactId>commons-compress</artifactId><version>1.23.0</version></dependency><!--rar解压--><dependency><groupId>com.github.junrar</groupId><artifactId>junrar</artifactId><version>7.5.4</version> <!-- 请根据最新版本选择 --></dependency>

该代码仅实现了zip的解压

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/61591.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

IDEA 下载源码很慢,Download Source使用阿里云镜像仓库

参考&#xff1a; IDEA maven本地仓库、中心仓库、远程仓库配置 在观看第三方jar包的api时&#xff0c;有时候需要下载源码看下注释。 这个时候用idea 上的提示的Download Source会发现一直下载不下来。 因此就怀疑用的是apache的maven仓库&#xff0c;不是我们用的 aliyun 镜…

英文版本-带EXCEL函数的数据分析

一、问题&#xff1a; 二、表格内容 三、分析结果 四、具体的操作步骤&#xff1a; 销售工作表公式设计与数据验证 类别&#xff08;Category&#xff09;列公式&#xff1a; 在Category列&#xff08;假设为D列&#xff09;&#xff0c;根据ProductCode在Catalogue工作表中查找…

三层交换机静态路由实验

1、前置知识 2、实验目的 3、实验器材&#xff1a; 3560-23PS交换机2台、主机4台、交叉线1根和直通网线4根。 4、实验规划及拓扑 实验要求&#xff1a; &#xff08;1&#xff09;在交换机A和交换机B上分别划分基于端口的VLAN&#xff1a; 交换机 VLAN 端口成员 交换机…

PLC与PLC跨网段通讯的几种方法:厂区组网实践

PLC通常通过以太网或其他工业网络协议&#xff08;如PROFINET、Modbus TCP等&#xff09;进行通信。当PLC位于不同的网段时&#xff0c;它们不能直接通信&#xff0c;需要特殊的配置或设备来实现通信&#xff0c;不同网段的PLC通讯变得尤为重要。 随着工业网络的发展和工业4.0概…

观察者模式和订阅模式

观察者模式和订阅模式在概念上是相似的&#xff0c;它们都涉及到一个对象&#xff08;通常称为“主题”或“发布者”&#xff09;和多个依赖对象&#xff08;称为“观察者”或“订阅者”&#xff09;之间的关系。然而&#xff0c;尽管它们有相似之处&#xff0c;但在某些方面也…

HarmonyOs鸿蒙开发实战(20)=>一文学会基础使用组件导航Navigation

敲黑板&#xff0c;以下是重点技巧。文章末尾有实战项目效果截图及代码截图可参考 1.概要 Navigation是路由导航的根视图容器Navigation组件主要包含​导航页&#xff08;NavBar&#xff09;和子页&#xff08;NavDestination&#xff09;&#xff0c;导航页不存在页面栈中&am…

DevOps-Jenkins-新手入门级

1. Jenkins概述 1. Jenkins是一个开源持续集成的工具&#xff0c;是由JAVA开发而成 2. Jenkins是一个调度平台&#xff0c;本身不处理任何事情&#xff0c;调用插件来完成所有的工作 1.1 什么是代码部署 代码发布/部署>开发书写的程序代码---->部署测试/生产环境 web服务…

在win10下搭建ftp服务器

1 说明 本文档在win10下实现。 2 安装ftp服务器 打开“控制面板/程序和功能”&#xff0c;如下&#xff1a; 点击“启用或关闭windows功能”&#xff0c;如下&#xff1a; 安装“ftp服务器”&#xff0c;将下图红色圈中部分打勾&#xff0c;如下&#xff1a; 必须勾选…

数据结构C语言描述4(图文结合)--栈的实现,中序转后序表达式的实现

前言 这个专栏将会用纯C实现常用的数据结构和简单的算法&#xff1b;有C基础即可跟着学习&#xff0c;代码均可运行&#xff1b;准备考研的也可跟着写&#xff0c;个人感觉&#xff0c;如果时间充裕&#xff0c;手写一遍比看书、刷题管用很多&#xff0c;这也是本人采用纯C语言…

vue中路由缓存

vue中路由缓存 问题描述及截图解决思路关键代码及打印信息截图 问题描述及截图 在使用某一平台时发现当列表页码切换后点击某一卡片进入详情页后&#xff0c;再返回列表页时页面刷新了。这样用户每次看完详情回到列表页都得再重新输入自己的查询条件&#xff0c;或者切换分页到…

如何在 UniApp 中实现 iOS 版本更新检测

随着移动应用的不断发展&#xff0c;保持应用程序的更新是必不可少的&#xff0c;这样用户才能获得更好的体验。本文将帮助你在 UniApp 中实现 iOS 版的版本更新检测和提示&#xff0c;适合刚入行的小白。我们将分步骤进行说明&#xff0c;每一步所需的代码及其解释都会一一列出…

移动充储机器人“小奥”的多场景应用(上)

一、高速公路服务区应用 在高速公路服务区&#xff0c;新能源汽车的充电需求得到“小奥”机器人的及时响应。该机器人配备有储能电池和自动驾驶技术&#xff0c;能够迅速定位至指定充电点&#xff0c;为待充电的新能源汽车提供服务。得益于“小奥”的机动性&#xff0c;其服务…

Redis 的代理类注入失败,连不上 redis

在测试 redis 是否成功连接时&#xff0c;发现 bean 没有被创建成功&#xff0c;导致报错 根据报错提示&#xff0c;需要我们添加依赖&#xff1a; <dependency><groupId>org.apache.commons</groupId><artifactId>commons-pool2</artifactId>&l…

桌面怎么快速添加便签?适合桌面记事的便签小工具

在数字化时代&#xff0c;我们每天面对电脑处理大量任务&#xff0c;无论是工作计划、会议纪要还是个人生活琐事&#xff0c;都需要一个可靠的桌面记事工具来帮助我们记录和整理。因此&#xff0c;一款适合桌面使用的便签软件成为了我们不可或缺的助手。 敬业签就是这样一款功…

UE5 腿部IK 解决方案 footplacement

UE5系列文章目录 文章目录 UE5系列文章目录前言一、FootPlacement 是什么&#xff1f;二、具体实现 前言 在Unreal Engine 5 (UE5) 中&#xff0c;腿部IK&#xff08;Inverse Kinematics&#xff0c;逆向运动学&#xff09;是一个重要的动画技术&#xff0c;用于实现角色脚部准…

KLV6008固态继电器:高压应用的理想紧凑方案

在当今快节奏的电子领域&#xff0c;找到平衡性能、可靠性和安全性的组件至关重要。CRIA Semiconductor的KLV6008固态继电器(SSR)正是满足了这一要求。这款紧凑型继电器专为高压、低电流切换而设计&#xff0c;是适用于各种应用的多功能解决方案。 为什么选择KLV6008&#xff1…

在 Swift 中实现字符串分割问题:以字典中的单词构造句子

文章目录 前言摘要描述题解答案题解代码题解代码分析示例测试及结果时间复杂度空间复杂度总结 前言 本题由于没有合适答案为以往遗留问题&#xff0c;最近有时间将以往遗留问题一一完善。 LeetCode - #140 单词拆分 II 不积跬步&#xff0c;无以至千里&#xff1b;不积小流&…

HarmonyOs鸿蒙开发实战(21)=>组件间通信@ohos/liveeventbus

1.简介 LiveEventBus是一款消息总线&#xff0c;具有生命周期感知能力&#xff0c;支持Sticky&#xff0c;支持跨进程&#xff0c;支持跨APP发送消息。 2.下载安装 ohpm install ohos/liveeventbus 3.订阅&#xff0c;注册监听 4.发送事件 5. 完成 > 记得关注博主&#xff…

OpenCV和Qt坐标系不一致问题

“ OpenCV和QT坐标系导致绘图精度下降问题。” OpenCV和Qt常用的坐标系都是笛卡尔坐标系&#xff0c;但是细微处有些不同。 01 — OpenCV坐标系 OpenCV是图像处理库&#xff0c;是以图像像素为一个坐标位置&#xff0c;即一个像素对应一个坐标&#xff0c;所以其坐标系也叫图像…

nohup java -jar supporterSys.jar --spring.profiles.active=prod

文章目录 1、ps -ef | grep java2、kill 13713、ps -ef | grep java4、nohup java -jar supporterSys.jar --spring.profiles.activeprod &5、ps -ef | grep java1. 启动方式进程 1371进程 19994 2. 主要区别3. 可能的原因4. 建议 1、ps -ef | grep java rootshipper:~# p…