列出jar文件的内容

时间:2014-05-11 08:35:12

标签: java jar

package soundcliptest;

// development environment(NetBeans 8.0)
//
// NetBeansProjects
//     SoundClipTest
//         Source Packages
//             resources
//                ding.wav
//             soundcliptest
//                SoundClipTest.java
//

// unZipped jar file
//
// SoundClipTest
//    META-INF
//    resourses
//        ding.wav
//    soudcliptest
//        SoundClipTest.class
//

我还在学习如何使用这个工具。我似乎无法获得他们所属的进口货物。

我需要知道如何从代码中查看jar文件。 File方法不能破解它。必须有某种方法来查找资源“目录”的内容。我想要做的是在/ resources /下创建声音文件的菜单。我可以使它在开发环境中工作,但不能从jar文件中工作。也许有些“拉链”方法?但我还没找到他们。提前谢谢。

import java.awt.BorderLayout;
import java.awt.Dimension;
import java.io.*;
import java.net.URL;
import javax.sound.sampled.*;
import javax.swing.*;
import javax.swing.border.BevelBorder;

public class SoundClipTest extends JFrame {

    JTextPane myPane;
    String title;
    String showIt;

    public SoundClipTest() {

        // get something to write on
        this.myPane = new JTextPane();
        this.myPane.setPreferredSize(new Dimension(700, 100));
        this.myPane.setBorder(new BevelBorder(BevelBorder.LOWERED));

        try {
            // Open an audio input stream.
            URL dingUrl = getClass().getResource("/resources/ding.wav");

            // show the path we got
            String path = dingUrl.getPath();

            //trim 'ding.wav' from file path to get a directory path
            String dirPath = path.substring(0, path.length()-"ding.wav".length());

            // now get a Url for the dir from getResource and show THAT path
            URL dirUrl = getClass().getResource("/resources/");
            String urlPath = dirUrl.getPath();

            // the dirUrl path is just like the trimmed 'ding' file path
            // so use  urlPath to get a file object for the directory
            try {
                File f = new File(urlPath);  //works fine in dev environment
                String filePath = f.getPath();  // but not from jar file
                title = f.list()[0]; // from jar, null pointer exception here

                // whan things go right (HA HA) we display this
                showIt = ("                >>>>> IT WORKED!! <<<<<!" 
                        + "\n path to file:        "+ path 
                        + "\n path to dir:        " + dirPath 
                        + "\n path from URL: " +  urlPath  
                        + "\n path from file:  "+ filePath + "\n " + title);

            } catch (Exception e) {
                // you get this on display when executing the jar file
                showIt = ("          PHOOEY"
                        + "\n the ding  " + path 
                        + "\n trimmed path " + dirPath 
                        + "\n the URL path " + urlPath 
                        + "\n could not create a File object from path");

                 // the stack trace shows up only if you run from the terminal
               e.printStackTrace();
            }

            // We get a nice little 'ding', anyway
            AudioInputStream ais = AudioSystem.getAudioInputStream(dingUrl);
            Clip clip = AudioSystem.getClip();
            clip.open(ais);
            clip.start();

            //but nuttin else good -  show the disapointing results
            myPane.setText(showIt);

        } catch (UnsupportedAudioFileException | LineUnavailableException | IOException e) {
            e.printStackTrace();
        } catch (NullPointerException e) {
            System.out.println("Ouch!!! Damn, that hurt!");
            e.printStackTrace();
        }
    }

    public static void main(String[] args) {
        SoundClipTest me = new SoundClipTest();
        JFrame frame = new JFrame("Sound Test");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.getContentPane().add(me.myPane, BorderLayout.CENTER);
        frame.pack();
        frame.setVisible(true);
    }
}

2 个答案:

答案 0 :(得分:0)

好的,不是完整的答案,但由于该部分记录不完整(Oracle的页面已经过时),以下是如何在jar文件中使用ZIP文件系统:

final Path pathToJar = Paths.get(...).toRealPath();
final String jarURL = "jar:file:" + pathToJar;
final Map<String, String> env = new HashMap<>();

final FileSystem jarfs = FileSystems.newFileSystem(URI.create(jarURL), env);

final Path rootPath = jarfs.getPath("/resources");

然后您可以使用Files.newDirectoryStream()而不是rootPath来获取jar中“目录”内的文件列表。如果要以递归方式列出,请使用Files.walkFileTree()并编写自己的FileVisitor(大多数情况下,扩展SimpleFileVisitor就足够了。)

注意FileSystem实施Closeable;一旦完成,你应该确保.close()。对于这个问题,DirectoryStream也是如此。

答案 1 :(得分:0)

警告Emptor

这假设您没有摆弄类加载器,这将与URLClassLoader一起使用,但它是该类的实现细节,而不是公共API的一部分。

如果您加载了一个类路径目录资源,那么您将获得该目录中每个资源的一行。

让我们假设您有这种结构:

/resources
    /test1.txt
    /test2.txt

如果我们执行以下操作:

try (final Scanner scanner = new Scanner(getClass().getResourceAsStream("/resources"))) {
    while (scanner.hasNextLine()) {
        final String line = scanner.nextLine();
        System.out.println(line);
    }
}

这将输出:

test1.txt
test2.txt

因此,您可以使用它来返回文件名列表:

List<String> readClassPath(final String root) {
    final List<String> resources = new LinkedList<>();
    try (final Scanner scanner = new Scanner(getClass().getResourceAsStream(root))) {
        while (scanner.hasNextLine()) {
            final String line = scanner.nextLine();
            System.out.println(line);
            resources.add(root + "/" + line);
        }
    }
    return resources;
}

返回:

[/resources/test1.txt, /resources/test2.txt]