View Single Post
  #28  
Old 05-23-2018, 22:11
Mkz Mkz is offline
Friend
 
Join Date: Jan 2002
Posts: 98
Rept. Given: 0
Rept. Rcvd 2 Times in 2 Posts
Thanks Given: 5
Thanks Rcvd at 22 Times in 15 Posts
Mkz Reputation: 2
Ah, I see your point now. The duplication a/A was not on the filenames, but on the folders / package names.

After a lot of confusion, because I was having the same problem you mentioned, I think I figured out the reason. It was 7-zip's problem, not the generated JAR

Here's some standalone java code to create a JAR with duplicate directories (and files as well):
Code:
import java.io.File;
import java.io.IOException;
import java.nio.file.FileSystem;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.spi.FileSystemProvider;
import java.util.HashMap;
import java.util.Map;


/**
 * Test code for Zip creation from within java
 * 
 * Extracted from Dex2Jar code, more specifically:
 *   https://github.com/pxb1988/dex2jar/blob/eca2c98278ec30e31c3953e0a030505987a6f8ca/dex-translator/src/main/java/com/googlecode/d2j/dex/Dex2jar.java#L270
 *
 */
public class ZipFSTest {

    public static void to(Path file) throws IOException {
        if (Files.exists(file) && Files.isDirectory(file)) {
            doTranslate(file);
        } else {
            try (FileSystem fs = createZip(file)) {
                doTranslate(fs.getPath("/"));
            }
        }
    }

    private static void doTranslate(Path file) throws IOException {
        byte[] contents = new byte[] { 0x40, 0x41, 0x42 };
        
        System.out.println("Translating path: " + file);
        
        System.out.println("Creating: " + file.resolve("/a/b/c/").toAbsolutePath());
        Files.createDirectories(file.resolve("/a/b/c/"));
        Files.write(file.resolve("/a/b/c/a.txt"), contents);
        Files.write(file.resolve("/a/b/c/A.txt"), contents);
        
        System.out.println("Creating: " + file.resolve("/A/b/c/").toAbsolutePath());
        Files.createDirectories(file.resolve("/A/b/c/"));
        Files.write(file.resolve("/A/b/c/a.txt"), contents);
        Files.write(file.resolve("/A/b/c/A.txt"), contents);
        
        System.out.println("Creating: " + file.resolve("/a/b/C/").toAbsolutePath());
        Files.createDirectories(file.resolve("/a/b/C/"));
        Files.write(file.resolve("/a/b/C/a.txt"), contents);
        Files.write(file.resolve("/a/b/C/A.txt"), contents);
    }

    private static FileSystem createZip(Path output) throws IOException {
        Map<String, Object> env = new HashMap<>();
        env.put("create", "true");
        Files.deleteIfExists(output);
        Path parent = output.getParent();
        if (parent != null && !Files.exists(parent)) {
            Files.createDirectories(parent);
        }
        for (FileSystemProvider p : FileSystemProvider.installedProviders()) {
            System.out.println("Checking provider: " + p.getClass().getName());
            String s = p.getScheme();
            if ("jar".equals(s) || "zip".equalsIgnoreCase(s)) {
                return p.newFileSystem(output, env);
            }
        }
        throw new IOException("cant find zipfs support");
    }
    
    public static void main(String[] args) throws IOException {
        
        to(new File("abc.zip").toPath());
        System.out.println("Done");
    }

}

If you run it on windows, you'll end up with "abc.zip" like the one I attached here.
Open it on 7-zip and you'll see a single root dir "a", followed by "b" and finally by "c". Inside there are 3 "a.txt"'s and 3 "A.txt"'s - the problem you mention.

However, list the file contents from the command line and all is well:
"jar tf abc.zip" or "unzip -l abc.zip":
Code:
a/
a/b/
a/b/c/
a/b/c/a.txt
a/b/c/A.txt
A/
A/b/
A/b/c/
A/b/c/a.txt
A/b/c/A.txt
a/b/C/
a/b/C/a.txt
a/b/C/A.txt
Open it in jd-gui and each package is separated, with A.txt and a.txt inside

Just wish I had not wasted so much time blindly trusting 7-zip's output and digging through the JRE's com.sun.nio.zipfs.ZipFileSystemProvider until remembering to use a command line listing of the archive contents.
Attached Files
File Type: zip abc.zip (2.1 KB, 2 views)
Reply With Quote
The Following 2 Users Say Thank You to Mkz For This Useful Post:
sendersu (05-24-2018), tonyweb (05-24-2018)