java.util.zip.ZipException: lỗi khi mở tệp zip


77

Tôi có một tệp Lọ, trong đó có các Chum lồng nhau khác. Khi tôi gọi hàm tạo mới JarFile()trên tệp này, tôi nhận được một ngoại lệ có nội dung:

java.util.zip.ZipException: lỗi khi mở tệp zip

Khi tôi giải nén thủ công nội dung của tệp Jar này và nén lại, nó hoạt động tốt.

Tôi chỉ thấy ngoại lệ này trên WebSphere 6.1.0.7 và các phiên bản cao hơn. Điều tương tự cũng hoạt động tốt trên tomcat và WebLogic.

Khi tôi sử dụng JarInputStream thay vì JarFile, tôi có thể đọc nội dung của tệp Jar mà không có bất kỳ ngoại lệ nào.


3
Cảm ơn gợi ý về cách giải nén tệp - điều đó đã sửa cho tôi.
Bryan Larsen

Tôi đã gặp sự cố này trên Mac khi Windows và Linux hoạt động tốt. Sử dụng JarInputStream đã khắc phục sự cố cho tôi.
Boris van Schooten

Tôi đã gặp phải sự cố tương tự trên Tomcat Start UP [catalina.properties]: org.apache.catalina.startup.TldConfig tldScanJarCẢNH BÁO: Không xử lý được JAR [jar: ../ opensaml.jar! /] Cho các tệp TLD ZipExceptionđể giải quyết vấn đề này, hãy thêm opensaml. ~ .Jar vào Application lib thư mục.
Yash

Có vẻ là phụ thuộc hệ điều hành. Với Java 8, một trong những cái lọ của tôi có thể đọc được từ MacOS và Linux nhưng không phải với Windows 7. Cái lọ có dung lượng khoảng 80 MByte. Các lọ cũ hơn có thể đọc được trên cùng một Windows 7. Sẽ có các tùy chọn gỡ lỗi tốt hơn cho việc này.
Wolfgang Fahl

Câu trả lời:


27

Đảm bảo rằng tệp jar của bạn không bị hỏng. Nếu nó bị hỏng hoặc không thể giải nén, lỗi này sẽ xảy ra.


18

Tôi phải đối mặt với cùng một vấn đề. Tôi có một kho lưu trữ zip mà java.util.zip.ZipFile không thể xử lý nhưng WinRar đã giải nén nó rất tốt. Tôi đã tìm thấy bài viết trên SDN về các tùy chọn nén và giải nén trong Java. Tôi đã sửa đổi một chút một trong các mã ví dụ để tạo ra phương pháp cuối cùng có khả năng xử lý kho lưu trữ. Thủ thuật là sử dụng ZipInputStream thay vì ZipFile và đọc tuần tự kho lưu trữ zip. Phương pháp này cũng có khả năng xử lý kho lưu trữ zip trống. Tôi tin rằng bạn có thể điều chỉnh phương pháp cho phù hợp với nhu cầu của mình vì tất cả các lớp zip đều có các lớp con tương đương cho các kho lưu trữ .jar.

public void unzipFileIntoDirectory(File archive, File destinationDir) 
    throws Exception {
    final int BUFFER_SIZE = 1024;
    BufferedOutputStream dest = null;
    FileInputStream fis = new FileInputStream(archive);
    ZipInputStream zis = new ZipInputStream(new BufferedInputStream(fis));
    ZipEntry entry;
    File destFile;
    while ((entry = zis.getNextEntry()) != null) {
        destFile = FilesystemUtils.combineFileNames(destinationDir, entry.getName());
        if (entry.isDirectory()) {
            destFile.mkdirs();
            continue;
        } else {
            int count;
            byte data[] = new byte[BUFFER_SIZE];
            destFile.getParentFile().mkdirs();
            FileOutputStream fos = new FileOutputStream(destFile);
            dest = new BufferedOutputStream(fos, BUFFER_SIZE);
            while ((count = zis.read(data, 0, BUFFER_SIZE)) != -1) {
                dest.write(data, 0, count);
            }
            dest.flush();
            dest.close();
            fos.close();
        }
    }
    zis.close();
    fis.close();
}

3
zis.close(); fis.close();nên ở trong mệnh đề cuối cùng - duh (hoặc sử dụng thử với tài nguyên)
Mr_and_Mrs_D

Điều này giải quyết vấn đề chính xác của tôi! Sự cố đang sử dụng ZipFile thay vì ZipInputStream! Thx bạn rất nhiều <3
CrazyProg

10

Nó có thể liên quan đến log4j.

Bạn có tệp log4j.jar trong websphere java classpath (như được định nghĩa trong tệp khởi động) cũng như classpath ứng dụng không?

Nếu bạn chắc chắn rằng tệp log4j.jar nằm trong java classpath và nó KHÔNG nằm trong thư mục web-inf / lib của ứng dụng web của bạn.


Nó cũng có thể liên quan đến phiên bản kiến (có thể không phải trường hợp của bạn, nhưng tôi đưa nó vào đây để tham khảo):

Bạn có tệp .class trong đường dẫn lớp của mình (nghĩa là không phải là thư mục hoặc tệp .jar). Bắt đầu với ant 1.6, ant sẽ mở các tệp trong classpath kiểm tra các mục kê khai. Cố gắng mở này sẽ không thành công với lỗi "java.util.zip.ZipException"

Vấn đề không tồn tại với ant 1.5 vì nó không cố gắng mở tệp. - vì vậy hãy đảm bảo rằng đường dẫn classpath của bạn không chứa tệp .class.


Một lưu ý nhỏ là bạn có cân nhắc đến việc có các lọ riêng biệt không?
Bạn có thể trong tệp kê khai của lọ chính của mình, tham khảo các lọ khác có thuộc tính này:

Class-Path: one.jar two.jar three.jar

Sau đó, đặt tất cả các lọ của bạn vào cùng một thư mục.
Một lần nữa, có thể không hợp lệ cho trường hợp của bạn, nhưng vẫn có để tham khảo.


Cảm ơn vì ý kiến ​​của bạn. Tuy nhiên, tôi không có log4j.jar trong đường dẫn liên kết Java websphere.
Sandhya Agarwal

9

Tôi đã từng thấy ngoại lệ này trước đây khi bất cứ thứ gì JVM coi là thư mục tạm thời đều không thể truy cập được do không có ở đó hoặc không có quyền ghi.


3

Tôi đã giải quyết vấn đề này bằng cách xóa các thư mục jboss-xyz / server [config] / tmp và jboss-xyz / server / [config] / work.


2

Tôi đã thấy điều này với một tệp Zip cụ thể với Java 6, nhưng nó đã biến mất khi tôi nâng cấp lên Java 8 (không kiểm tra Java 7), vì vậy, có vẻ như các phiên bản ZipFile mới hơn trong Java hỗ trợ nhiều thuật toán nén hơn và do đó có thể đọc các tệp. không thành công với các phiên bản trước đó.


0

Liquibase đã nhận được lỗi này cho tôi. Tôi đã giải quyết vấn đề này sau khi tôi gỡ lỗi và xem liquibase cố gắng tải các thư viện và nhận thấy rằng nó đang bị lỗi trên các tệp kê khai cho commons-codec-1.6.jar. Về cơ bản, có một tệp zip bị hỏng ở đâu đó trong đường dẫn của bạn hoặc có một phiên bản không tương thích đang được sử dụng. Khi tôi khám phá kho lưu trữ Maven cho thư viện này, tôi thấy có những phiên bản mới hơn và đã thêm phiên bản mới hơn vào pom.xml. Tôi đã có thể tiếp tục tại thời điểm này.


0

Tôi đã ngoại lệ

java.util.zip.ZipException: invalid entry CRC (expected 0x0 but got 0xdeadface)
    at java.util.zip.ZipInputStream.read(ZipInputStream.java:221)
    at java.util.zip.ZipInputStream.closeEntry(ZipInputStream.java:140)
    at java.util.zip.ZipInputStream.getNextEntry(ZipInputStream.java:118)
...

khi giải nén một kho lưu trữ trong Java. Bản thân kho lưu trữ dường như không bị hỏng khi 7zip (và những người khác) đã mở nó mà không gặp bất kỳ sự cố hoặc khiếu nại nào về CRC không hợp lệ.

Tôi đã chuyển sang Apache Commons Compress để đọc các mục zip và điều đó đã giải quyết được sự cố.


0

Trên Windows7, tôi gặp sự cố này qua kết nối mạng Samba cho Tệp Java8 Jar lớn> 80 MByte. Sao chép tệp vào ổ đĩa cục bộ đã khắc phục sự cố.


0

Trong trường hợp của tôi, của tôi -Dloader.path="lib"chứa các lọ khác không cần. ví dụ: mvn dependency:copy-dependenciesliệt kê 100 tệp jar. nhưng libthư mục của tôi chứa 101 tệp jar.


0

Trong trường hợp của tôi SL4j-api.jar với nhiều phiên bản đang xung đột trong repo maven. Tôi đã xóa toàn bộ thư mục SL4j-api trong m2 maven repo và cập nhật dự án maven, xây dựng dự án maven hơn là chạy dự án trong máy chủ JBOSS. vấn đề đã được giải quyết.


-1

Đơn giản để vượt qua ZipException, tôi đã sử dụng một trình bao bọc cho 1.14 có tên được viết bởi thrau giúp dễ dàng giải nén hoặc nén từ và vào các đối tượng Tệp.commons-compressjarchivelib

Thí dụ:

public static void main(String[] args) {
        String zipfilePath = 
                "E:/Selenium_Server/geckodriver-v0.19.0-linux64.tar.gz";
                //"E:/Selenium_Server/geckodriver-v0.19.0-win32.zip";
        String outdir = "E:/Selenium_Server/";
        exratctFileList(zipfilePath, outdir );
}
public void exratctFileList( String zipfilePath, String outdir ) throws IOException {
    File archive = new File( zipfilePath );
    File destinationDir = new File( outdir );

    Archiver archiver = null;
    if( zipfilePath.endsWith(".zip") ) {
        archiver = ArchiverFactory.createArchiver( ArchiveFormat.ZIP );
    } else if ( zipfilePath.endsWith(".tar.gz") ) {
        archiver = ArchiverFactory.createArchiver( ArchiveFormat.TAR, CompressionType.GZIP );
    }
    archiver.extract(archive, destinationDir);

    ArchiveStream stream = archiver.stream( archive );
    ArchiveEntry entry;

    while( (entry = stream.getNextEntry()) != null ) {
        String entryName = entry.getName();
        System.out.println("Entery Name : "+ entryName );
    }
    stream.close();
}

Sự phụ thuộc của Maven «Bạn có thể tải xuống các bình từ Kho lưu trữ Maven Sonatype tại org / rauschig / jarchivelib / .

<dependency>
  <groupId>org.rauschig</groupId>
  <artifactId>jarchivelib</artifactId>
  <version>0.7.1</version>
</dependency>

@xem

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.