Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Accessing a Java Resource as a File

I'm trying to access a resource from the class path/JAR file as a File object. I'm aware that it's the preferred method to use an InputStream object instead, but I'm using an external library (WorldEdit) which needs a File object.

Here's my code:

InputStream templStream = "".getClass().getResourceAsStream("/res/template.prom");
System.out.println("templateStream: " + templStream.toString());
File templFile = new File("".getClass().getResource("/res/template.prom").toURI());
System.out.println("templateFile: " + templFile.canRead());

Now while I'm still inside eclipse, both ways of accessing the resource work flawlessly and produce this output:

templStream: java.io.BufferedInputStream@746d1683
templFile: true

But after exporting the code into a JAR archive, the code fails:

templStream: sun.net.www.protocol.jar.JarURLConnection$JarURLInputStream@47aa261b
Exception in thread "main" java.lang.IllegalArgumentException: URI is not hierarchical
    at java.io.File.<init>(File.java:392)
    at SMCToPROM.main(SMCToPROM.java:101)

So I've been, without success, searching for a way for either accessing the resource as a File directly, or going the way of using an InputStream and converting that InputStream to a file.

The worst case fallback solution would be to copy the InputStream to a file on the filesystem, and then open that file, but I hope that won't be neccesary.

like image 371
mic_e Avatar asked May 15 '12 16:05

mic_e


1 Answers

The short answer is that you can't, because the resource isn't a File.

Either the third-party library is badly written if all it wants to do is read data from a source (and thus it should take an InputStream), or the library actually wants to do File-specific manipulations.

Assuming this isn't an oversight in the library that can be fixed, you'll need to actually create a file yourself. Try calling File.createTempFile(), populate this file with the contents of the resource yourself, and then pass this File object to the library. (Delete it once you're done, of course).

like image 51
Andrzej Doyle Avatar answered Oct 08 '22 17:10

Andrzej Doyle