Java解析zip文件,并識別壓縮包里面的文件轉換成可操作的IO流方式
更新時間:2024年08月26日 09:04:19 作者:BestTomDoG
這篇文章主要介紹了Java解析zip文件,并識別壓縮包里面的文件轉換成可操作的IO流方式,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
Java解析zip文件,并識別壓縮包里面的文件轉換成可操作的IO流
前幾天項目遇到一個棘手的問題,
批量上傳人員的證件照,因為java操作文件夾不好操作,
最后決定把存放人員證件照的文件夾壓縮成zip文件,
通過java去解析,然后把里面的文件轉成list集合,這里使用的jdk提供的 java.util.zip包
第一步
引入需要的maven依賴
<dependency>
<groupId>commons-fileupload</groupId>
<artifactId>commons-fileupload</artifactId>
<version>1.3.3</version>
</dependency>第二步
創(chuàng)建UnzipFileVo對象(文件的載體)
@Data
public class UnzipFileVo {
private MultipartFile file;
}第三步
編寫轉換工具類
public class ZipUtil {
public static List<UnzipFileVo> Ectract(MultipartFile multipartFile) throws IOException {
List<UnzipFileVo> list= new ArrayList<>();
//獲取文件輸入流
InputStream input = multipartFile.getInputStream();
//獲取ZIP輸入流(一定要指定字符集Charset.forName("GBK")否則會報java.lang.IllegalArgumentException: MALFORMED)
ZipInputStream zipInputStream = new ZipInputStream(new BufferedInputStream(input), Charset.forName("GBK"));
ZipFile zf = toFile(multipartFile);
//定義ZipEntry置為null,避免由于重復調用zipInputStream.getNextEntry造成的不必要的問題
ZipEntry ze = null;
//循環(huán)遍歷
while ((ze =zipInputStream.getNextEntry())!= null) {
InputStream is = zf.getInputStream(ze);
UnzipFileVo unzipFileVo = new UnzipFileVo();
unzipFileVo.setFile(getMultipartFile(is,ze.getName()));
list.add(unzipFileVo);
}
//一定記得關閉流
zipInputStream.closeEntry();
input.close();
return list;
}
/**
* 獲取封裝得MultipartFile
*
* @param inputStream inputStream
* @param fileName fileName
* @return MultipartFile
*/
public static MultipartFile getMultipartFile(InputStream inputStream, String fileName) {
FileItem fileItem = createFileItem(inputStream, fileName);
//CommonsMultipartFile是feign對multipartFile的封裝,但是要FileItem類對象
return new CommonsMultipartFile(fileItem);
}
private static ZipFile toFile(MultipartFile multipartFile) throws IOException {
if (multipartFile == null || multipartFile.getSize() <= 0) {
return null;
}
File file = multipartFileToFile(multipartFile);
if (file == null || !file.exists()) {
return null;
}
ZipFile zipFile = new ZipFile(file, Charset.forName("GBK"));
return zipFile;
}
private static File multipartFileToFile(MultipartFile multipartFile) {
File file = null;
InputStream inputStream = null;
OutputStream outputStream = null;
try {
inputStream = multipartFile.getInputStream();
file = new File(multipartFile.getOriginalFilename());
outputStream = new FileOutputStream(file);
write(inputStream, outputStream);
} catch (IOException e) {
e.printStackTrace();
} finally {
if (inputStream != null) {
try {
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
if (outputStream != null) {
try {
outputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return file;
}
public static void write(InputStream inputStream, OutputStream outputStream) {
byte[] buffer = new byte[4096];
try {
int count = inputStream.read(buffer, 0, buffer.length);
while (count != -1) {
outputStream.write(buffer, 0, count);
count = inputStream.read(buffer, 0, buffer.length);
}
} catch (RuntimeException e) {
throw e;
} catch (Exception e) {
throw new RuntimeException(e.getMessage(), e);
}
}
/**
* FileItem類對象創(chuàng)建
*
* @param inputStream inputStream
* @param fileName fileName
* @return FileItem
*/
public static FileItem createFileItem(InputStream inputStream, String fileName) {
FileItemFactory factory = new DiskFileItemFactory(16, null);
String textFieldName = "file";
FileItem item = factory.createItem(textFieldName, MediaType.MULTIPART_FORM_DATA_VALUE, true, fileName);
int bytesRead = 0;
byte[] buffer = new byte[8192];
OutputStream os = null;
//使用輸出流輸出輸入流的字節(jié)
try {
os = item.getOutputStream();
while ((bytesRead = inputStream.read(buffer, 0, 8192)) != -1) {
os.write(buffer, 0, bytesRead);
}
inputStream.close();
} catch (IOException e) {
throw new IllegalArgumentException("文件上傳失敗");
} finally {
if (os != null) {
try {
os.close();
} catch (IOException e) {
}
}
if (inputStream != null) {
try {
inputStream.close();
} catch (IOException e) {
}
}
}
return item;
}
}第四步
調用工具
@PostMapping("/UploadManagerPhoto")
public ActionResult uploadManagerPhoto(MultipartFile file) throws IOException {
if(Objects.isNull(file) || file.isEmpty()) {//驗證文件是否為空
return ActionResult.fail("上傳文件為空或不存在");
}
List<UnzipFileVo> unzipFileVoList = UnZipUtil.Ectract(file);
List<UnzipFileVo> collect = unzipFileVoList.stream().filter(item -> item.getFile().getOriginalFilename().contains(".") && item.getFile().getSize() > 0).collect(Collectors.toList());//獲取zip文件里面的文件,并組裝到新的List對象//過濾文件夾
//上面就是把zip壓縮包的內容轉換稱了文件流集合,下面可根據(jù)自己的業(yè)務對文件進行操作
int sum = 0;
for (int i = 0; i < collect.size(); i++) {
//這是我自己封裝的上傳方法,大家可以根據(jù)自己的實際情況對文件進行操作
UploaderVO uploaderVO = fileService.uploader("document", collect.get(i).getFile());//調取上傳方法,返回上傳成功對象
sum++;
}
return ActionResult.success("解析zip成功,成功上傳"+sum+"條數(shù)據(jù)");
}總結
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關文章
詳解Java中super的幾種用法并與this的區(qū)別
這篇文章主要介紹了Java中super的幾種用法并與this的區(qū)別,有需要的朋友可以參考一下2013-12-12
SpringData JPA實體映射與關系映射的實現(xiàn)
Spring Data JPA作為Spring生態(tài)系統(tǒng)中的核心項目,通過JPA規(guī)范提供了優(yōu)雅而強大的實體映射與關系處理機制,下面就來介紹一下,感興趣的可以了解一下2025-04-04
淺談java中replace()和replaceAll()的區(qū)別
這篇文章主要介紹了java中replace()和replaceAll()的區(qū)別,兩者都是常用的替換字符的方法,感興趣的小伙伴們可以參考一下2015-11-11

