如何在运行时和 dev-env 中从 jar 中复制文件夹的资源?



我目前正在制作一个具有预先制作的级别的游戏,目前我将它们存储在资源中。我希望解决如何从生产和开发环境中从JAR中提取文件夹的解决方案。

我尝试使用下面的给定方法复制文件夹,并以File defaultWorld = new File(GameData.class.getClassLoader().getResource("worlds/").getFile());传递SRC目的地为private static File worldsDir = new File("run/worlds");

public static void copyFolder(File src, File dest) {
    try {
        if (src.isDirectory()) {
            if (!dest.exists()) {
                dest.mkdir();
            }
            String[] files = src.list();
            for (String file : files) {
                copyFolder(new File(src, file), new File(dest, file));
            }
        } else {
            try (InputStream in = new FileInputStream(src)) {
                try (OutputStream out = new FileOutputStream(dest)) {
                    byte[] buffer = new byte[1024];
                    int length;
                    //copy the file content in bytes
                    while ((length = in.read(buffer)) > 0) {
                        out.write(buffer, 0, length);
                    }
                }
            }
        }
    } catch (IOException e) {
        e.printStackTrace();
    }
}

我期望上述方法可以在开发和生产env上使用,但是当打开文件输出流时,它会引发FileNotFoundException

you 不能在jar中列出资源。

您正在考虑的任何解决方法都不可靠。

  • 从不调用URL的getFile()方法。它不返回有效的文件名;它只是返回URL的路径和查询部分,任何百分比占整数。此外,JAR条目不是file: URL,因此,当它引用JAR条目时,资源路径永远不会成为有效的文件名。
  • 在JAR文件中列出内容的唯一方法是通过所有JAR条目迭代,但是您甚至不能保证可以访问您的JAR,因为不能保证Class Loaders是UrlClass Loaders,并且通常不能保证。使用jar: URL。
  • 您甚至不能依靠myApplication.class.getProtectiondomain((。getCodesource((,因为getCodesource((可以返回null。

如果您想从罐子中复制多个文件,请参阅以下一些可靠的方法:

  • 硬码您计划复制的资源列表。这是您的应用程序,因此您知道要放在罐子里的文件。
  • 将单个文本文件保留在您的罐子中,其中包含要复制的资源路径列表。
  • 将您的资源存储在嵌入罐子中的单个邮递档案中,并用包装myApplication.class.getResourceastream的zipinputstream自己提取它。

最新更新