java解決包含中文名文件壓縮後上傳至linux服務器,解壓縮後文件名亂碼

問題描述:

項目需求將帶有中文名稱的多個文件壓縮至zip包,並上傳至linux服務器。採用jdk自帶的ZipOutputStream輸出流以壓縮文件的格式寫入文件,壓縮文件上傳成功之後,使用unzip命令解壓縮zip包,發現帶有中文名稱的文件的文件名爲亂碼。

解決方案:

使用ZipArchiveOutputStream代替jdk自帶的ZipOutputStream寫入壓縮文件

jar包依賴如下:

<dependency>
          <groupId>org.apache.commons</groupId>
          <artifactId>commons-compress</artifactId>
          <version>1.5</version>
</dependency>

代碼具體實現如下:

public static void zipFile(File[] allFiles){
        String filePath = "/home/upload/test.zip";
        File zipFile = new File(filePath);
        ZipArchiveOutputStream zos = null;
        try {
            //創建寫入文件的zip輸出流
            zos = new ZipArchiveOutputStream(zipFile);
            zos.setEncoding("UTF8");
            ZipEncoding zipEncoding = ZipEncodingHelper.getZipEncoding("UTF8");
            if(allFiles !=null && allFiles.length>0){
                for(File file:allFiles){
                    String fileName= file.getName();
                    ZipArchiveEntry zipEntry = new ZipArchiveEntry(file,fileName);
                    ByteBuffer byteBuffer = zipEncoding.encode(fileName);
                    //從給定的文件名稱和字節數組組裝unicode路徑名稱
                    UnicodePathExtraField unicodePathExtraField = new UnicodePathExtraField(fileName,byteBuffer.array(),byteBuffer.arrayOffset(),byteBuffer.limit()-byteBuffer.position());
                    zipEntry.addExtraField(unicodePathExtraField);
                    //將ZipArchiveEntry頭部寫入到輸出流
                    zos.putArchiveEntry(zipEntry);
                    InputStream inputStream = new FileInputStream(file);
                    BufferedInputStream bufferedInputStream = new BufferedInputStream(inputStream);
                    byte[] bufferByte = new byte[1024];
                    //讀取文件內容
                    while(bufferedInputStream.read(bufferByte)>0){
                        zos.write(bufferByte);
                    }
                    //將文件數據寫入
                    zos.closeArchiveEntry();
                    //關閉緩存輸入流
                    bufferedInputStream.close();
                }
            }
            zos.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章