23

I have a project A, which contains some java files and a classpath resource R.txt. Within the project I use ClassLoader.getSystemResource("R.txt"); to retrieve R.txt.

Then I have a project B which includes project A's jar-file. Now getSystemResource("R.txt") wont find the textfile (and yes, it's still in the root of the jar file). Even trying "/R.txt" as was suggested on some other site didn't work. Any ideas?

tcb
  • 2,745
  • 21
  • 20
Johan Sjöberg
  • 241
  • 1
  • 2
  • 4

3 Answers3

52

Use getResource instead of getSystemResource to use a resource specific to a given classloader instead of the system. For example, try any of the following:

URL resource = getClass().getClassLoader().getResource("R.txt");
URL resource = Foo.class.getClassLoader().getResource("R.txt");
URL resource = getClass().getResource("/R.txt");
URL resource = Foo.class.getResource("/R.txt");

Note the leading slash when calling Class.getResource instead of ClassLoader.getResource; Class.getResource is relative to the package containing the class unless you have a leading slash, whereas ClassLoader.getResource is always absolute.

Jon Skeet
  • 1,421,763
  • 867
  • 9,128
  • 9,194
  • Amazing. This completely solved my problem. Thanks for the superfast input // Johan – Johan Sjöberg Dec 14 '09 at 10:58
  • One more related question: we may get InputStream from this URL resources, but how could we create a **File** object from the returned URL object. I tried to create a **URI** object with the "URLObject.toURI()", and use this URI object to create a file, unfortunately, it throws an "URI is not hierarchical exception". Could you give me some help ? Thanks a lot . – Ensom Hodder Aug 11 '12 at 21:39
  • 2
    @EnsomHodder: Um, not sure - but not all resources *are* files - in particular, it won't be if it's in a jar file. – Jon Skeet Aug 11 '12 at 22:25
  • Thanks for the explanation of when the `/` is needed. – asgs Sep 19 '12 at 05:15
  • @Jeff: I've rolled back the edit because `Class.ClassLoader` isn't a classname. The method is in the `ClassLoader` class. Yes, you often *call* `Class.getClassLoader()` to get a classloader, but the call is still `ClassLoader.getResource`... – Jon Skeet Feb 19 '14 at 18:48
5

Apparently your JAR is not loaded by the system classloader, so getSystemResource() can't work. This should work:

ClassFromProjectA.class.getClassLoader().getResource("R.txt")

IMO more convenient is putting resources inside the same package as the classes that use them, so you can use the shorter

ClassFromProjectA.class.getResource("R.txt")

(or, inside that class just getClass().getResource("R.txt"))

Michael Borgwardt
  • 342,105
  • 78
  • 482
  • 720
2

Does ClassLoader.getResource() work ? At the moment you're simply specifying that the system classloader is to be used.

Eddie Curtis
  • 1,207
  • 8
  • 20
Brian Agnew
  • 268,207
  • 37
  • 334
  • 440