[英]Why does class.getResource() keep returning null although there is a resource at the specified path?
[英]In Java, why does class.getResource(“/path/to/res”); not work in the runnable jar when copying files to the system?
我一直在從事一個項目,該項目要求用戶在首次運行時“安裝”該程序。 此安裝需要將所有資源從“ res”文件夾復制到用戶硬盤驅動器上的專用目錄。 我有下面的代碼塊運行良好,但是當我從eclipse中導出可運行的jar時,我收到了一個堆棧跟蹤,指示InputStream為null。 安裝循環將數組列表中每個文件的路徑傳遞給導出功能,這就是問題所在(使用InputStream)。 路徑已在Eclipse和可運行jar中正確傳遞,所以我懷疑這是問題所在。 我進行了研究,發現了類似的其他問題,但是建議的修復(使用類加載器等)均無效。 我不明白為什么我現在的方法可以在Eclipse中工作,但不能在jar中工作呢?
(還存在一個名為installFiles的File ArrayList)
private static String installFilesLocationOnDisk=System.getProperty("user.home")+"/Documents/[project name]/Resources/";
public static boolean tryInstall(){
for(File file:installFiles){
//for each file, make the required directories for its extraction location
new File(file.getParent()).mkdirs();
try {
//export the file from the jar to the system
exportResource("/"+file.getPath().substring(installFilesLocationOnDisk.length()));
} catch (Exception e) {
return false;
}
}
return true;
}
private static void exportResource(String resourceName) throws Exception {
InputStream resourcesInputStream = null;
OutputStream resourcesOutputStream = null;
//the output location for exported files
String outputLocation = new File(installFilesLocationOnDisk).getPath().replace('\\', '/');
try {
//This is where the issue arises when the jar is exported and ran.
resourcesInputStream = InstallFiles.class.getResourceAsStream(resourceName);
if(resourcesInputStream == null){
throw new Exception("Cannot get resource \"" + resourceName + "\" from Jar file.");
}
//Write the data from jar's resource to system file
int readBytes;
byte[] buffer = new byte[4096];
resourcesOutputStream = new FileOutputStream(outputLocation + resourceName);
while ((readBytes = resourcesInputStream.read(buffer)) > 0) {
resourcesOutputStream.write(buffer, 0, readBytes);
}
} catch (Exception ex) {
ex.printStackTrace();
System.exit(1);
} finally {
//Close streams
resourcesInputStream.close();
resourcesOutputStream.close();
}
}
堆棧跟蹤:
java.lang.Exception: Cannot get resource "/textures\gameIcon.png" from Jar file.
感謝所有幫助! 謝謝
將您的JAR文件重命名為ZIP,將其解壓縮並檢查資源去向何處。
您可能會在Eclipse中使用Maven,這意味着使用Eclipse的功能導出Runnable JAR不會將資源正確放置在JAR中(如果您使用默認的Maven文件夾名稱,它們將最終位於JAR的文件夾資源下)約定)。
如果是這種情況,則應使用Maven的Assembly插件(或“ uber-JAR”的Shade插件)來創建可運行的JAR。
即使您沒有使用Maven,也應檢查資源是否正確放置在生成的JAR中。
PS也不要這樣做:
.getPath().replace('\\', '/');
而且永遠不要依賴特定的分隔符-使用java.io.File.separator
來確定系統的文件分隔符。
堆棧跟蹤:
java.lang.Exception: Cannot get resource "/textures\\gameIcon.png" from Jar file.
資源錯誤時的名稱。 正如ClassLoader.getResource(String)
的Javadoc描述的(而Class.getResourceAsStream(String)
引用ClassLoader
以獲得詳細信息):
資源的名稱是一個
/
分隔的路徑名,用於標識資源。
無論您是從文件系統還是從Jar文件中獲取資源,都應始終使用/
作為分隔符。
使用\\
有時可能會起作用,有時則不會:無法保證。 但這總是一個錯誤。
在您的情況下,解決方案是更改了調用exportResource
:
String path = file.getPath().substring(installFilesLocationOnDisk.length());
exportResource("/" + path.replace(File.pathSeparatorChar, '/'));
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.