Voglio leggere un file XML che si trova all'interno di uno degli jar
s inclusi nel mio percorso di classe. Come posso leggere qualsiasi file incluso nello jar
?Come leggere un file da jar in Java?
risposta
Se si desidera leggere il file da dentro l'utilizzo dell'applicazione:
InputStream input = getClass().getResourceAsStream("/classpath/to/my/file");
Il percorso inizia con "/", ma che non è il percorso nel file-system, ma nel classpath. Quindi, se il file si trova nel classpath "org.xml" e si chiama myxml.xml, il percorso sembra "/org/xml/myxml.xml".
InputStream legge il contenuto del file. Puoi avvolgerlo in un Reader, se vuoi.
Spero che questo aiuti.
+1 per explaning perché il principale "/" è necessario. –
Ah, questa è una delle mie materie preferite. Ci sono essenzialmente due modi per caricare una risorsa attraverso il percorso di classe:
Class.getResourceAsStream(resource)
e
ClassLoader.getResourceAsStream(resource)
(ci sono altri modi che coinvolgono ottenere un URL per la risorsa in modo simile, quindi aprendo una connessione ad esso, ma questi sono i due modi diretti).
Il primo metodo in realtà delega al secondo, dopo aver distrutto il nome della risorsa. Esistono essenzialmente due tipi di nomi di risorse: assoluto (ad esempio "/ percorso/a/risorsa/risorsa") e relativo (ad esempio "risorsa"). I percorsi assoluti iniziano con "/".
Ecco un esempio che dovrebbe illustrare. Considera una classe com.esempio.A. Considerare due risorse, una situata in/com/example/nested, l'altra at/top, nel classpath. Il seguente programma mostra nove possibili modi per accedere ai due risorse:
package com.example; public class A { public static void main(String args[]) { // Class.getResourceAsStream Object resource = A.class.getResourceAsStream("nested"); System.out.println("1: A.class nested=" + resource); resource = A.class.getResourceAsStream("/com/example/nested"); System.out.println("2: A.class /com/example/nested=" + resource); resource = A.class.getResourceAsStream("top"); System.out.println("3: A.class top=" + resource); resource = A.class.getResourceAsStream("/top"); System.out.println("4: A.class /top=" + resource); // ClassLoader.getResourceAsStream ClassLoader cl = A.class.getClassLoader(); resource = cl.getResourceAsStream("nested"); System.out.println("5: cl nested=" + resource); resource = cl.getResourceAsStream("/com/example/nested"); System.out.println("6: cl /com/example/nested=" + resource); resource = cl.getResourceAsStream("com/example/nested"); System.out.println("7: cl com/example/nested=" + resource); resource = cl.getResourceAsStream("top"); System.out.println("8: cl top=" + resource); resource = cl.getResourceAsStream("/top"); System.out.println("9: cl /top=" + resource); } }
L'output del programma è:
1: A.class [email protected] 2: A.class /com/example/[email protected] 3: A.class top=null 4: A.class /[email protected] 5: cl nested=null 6: cl /com/example/nested=null 7: cl com/example/[email protected] 8: cl [email protected] 9: cl /top=null
Per lo più cose fare ciò che ci si aspetterebbe. Il caso 3 fallisce perché la risoluzione relativa della classe è rispetto alla classe, quindi "top" significa "/ com/example/top", ma "/ top" significa ciò che dice.
Il caso 5 non riesce perché la risoluzione relativa del classloader è rispetto al classloader. Ma, anche inaspettatamente, Case-6 fallisce: ci si potrebbe aspettare che "/ com/example/nested" si risolva correttamente. Per accedere a una risorsa nidificata tramite il classloader è necessario utilizzare Case-7, cioè il percorso nidificato è relativo alla radice del classloader. Allo stesso modo, Case-9 fallisce, ma passa Case-8.
Ricorda: per java.lang.Class, getResourceAsStream() non delegare al classloader:
public InputStream getResourceAsStream(String name) { name = resolveName(name); ClassLoader cl = getClassLoader0(); if (cl==null) { // A system class. return ClassLoader.getSystemResourceAsStream(name); } return cl.getResourceAsStream(name); }
quindi è il comportamento di ResolveName(), che è importante.
Infine, poiché è il comportamento del classloader che ha caricato la classe che controlla essenzialmente getResourceAsStream() e il classloader è spesso un caricatore personalizzato, le regole di caricamento delle risorse potrebbero essere ancora più complesse. per esempio.per applicazioni Web, caricare da WEB-INF/classes o WEB-INF/lib nel contesto dell'applicazione Web, ma non da altre applicazioni Web isolate. Inoltre, i classloader ben educati delegano ai genitori, in modo che le risorse duplicate nel classpath potrebbero non essere accessibili utilizzando questo meccanismo.
Questo è essenzialmente la stessa risposta che ho dato, ma ha spiegato in modo molto maggiori dettagli. +1 – Mnementh
Ecco il metodo resolveName menzionato: https://gist.github.com/briangordon/5374626 –
Un JAR è fondamentalmente un file ZIP quindi trattalo come tale. Di seguito è riportato un esempio su come estrarre un file da un file WAR (trattarlo anche come file ZIP) e restituire il contenuto della stringa. Per il binario dovrai modificare il processo di estrazione, ma ci sono un sacco di esempi là fuori per questo.
public static void main(String args[]) {
String relativeFilePath = "style/someCSSFile.css";
String zipFilePath = "/someDirectory/someWarFile.war";
String contents = readZipFile(zipFilePath,relativeFilePath);
System.out.println(contents);
}
public static String readZipFile(String zipFilePath, String relativeFilePath) {
try {
ZipFile zipFile = new ZipFile(zipFilePath);
Enumeration<? extends ZipEntry> e = zipFile.entries();
while (e.hasMoreElements()) {
ZipEntry entry = (ZipEntry) e.nextElement();
// if the entry is not directory and matches relative file then extract it
if (!entry.isDirectory() && entry.getName().equals(relativeFilePath)) {
BufferedInputStream bis = new BufferedInputStream(
zipFile.getInputStream(entry));
// Read the file
// With Apache Commons I/O
String fileContentsStr = IOUtils.toString(bis, "UTF-8");
// With Guava
//String fileContentsStr = new String(ByteStreams.toByteArray(bis),Charsets.UTF_8);
// close the input stream.
bis.close();
return fileContentsStr;
} else {
continue;
}
}
} catch (IOException e) {
logger.error("IOError :" + e);
e.printStackTrace();
}
return null;
}
In questo esempio sto usando Apache Commons I/O e se si utilizza Maven qui è la dipendenza:
<dependency>
<groupId>commons-io</groupId>
<artifactId>commons-io</artifactId>
<version>2.4</version>
</dependency>
controllare prima la classe Loader.
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
if (classLoader == null) {
classLoader = Class.class.getClassLoader();
}
classLoader.getResourceAsStream("xmlFileNameInJarFile.xml");
// xml file location at xxx.jar
// + folder
// + folder
// xmlFileNameInJarFile.xml
Solo per completezza, non v'è stato recentemente un question sulla mailinglist Jython in cui una delle risposte di cui a questo thread.
La domanda era: come chiamare uno script Python che è contenuto in un file .jar dall'interno Jython, la risposta suggerita è la seguente (con "InputStream" come spiegato in una delle risposte di cui sopra:
PythonInterpreter.execfile(InputStream)
- 1. Come leggere un file da un file jar?
- 2. Esegui file .jar da un programma Java
- 3. Come creare un JAR da .java
- 4. Come proteggere un file Jar da decompilare?
- 5. Come creare un file jar da scala
- 6. Java - Creazione di una classe da un file Jar
- 7. Come creare un file Jar in Netbeans
- 8. Leggere un file di testo in java
- 9. Come confezionare opencv + java in un jar
- 10. Come eseguire un file JAR
- 11. Come crittografare un file .jar
- 12. Come utilizzare il file * .jar in un progetto Java?
- 13. Java - Come scoprire da quale file Jar proviene un'importazione?
- 14. Leggere il file java .properties da bash
- 15. codice Java per creare un file JAR
- 16. Come utilizzare le classi da file .jar?
- 17. come leggere un file parquet, in un codice java standalone?
- 18. Come leggere i bit da un file?
- 19. equivalente di file JAR Java in Erlang
- 20. È possibile leggere/scrivere bit da un file usando JAVA?
- 21. Come si compila un file java con dipendenze jar?
- 22. Leggere i dati da un file di testo utilizzando Java
- 23. ant per rimuovere file da un jar
- 24. Come chiudere un file PST in Java?
- 25. lettura del file MANIFEST.MF dal file jar utilizzando JAVA
- 26. Come leggere un file in una bitmap Java?
- 27. Come leggere un file di configurazione in Java
- 28. Come leggere i file .plist OSX da Java?
- 29. Come leggere da file con Files.lines (...). ForEach (...)?
- 30. Come estrarre i file .war in java? ZIP vs JAR
vedere http://stackoverflow.com/questions/16842306 – yegor256
Se volete leggere i file da una directory in vaso con qualsiasi numero di file, vedere [StackOverflow-link] (https://stackoverflow.com/questions/26185137/ primavera-boot-resource-non-trovato-quando-con-executeable-jar/39.818.817 # 39.818.817) –