Buddhi
Buddhi

Reputation: 2324

class.getResource returns null

I am using the following to get the URL of this particular file, but it returns null. Does anyone have any suggestions as to the problem or an alternate way to do this?

URL url = ExchangeInterceptor.class.getResource("GeoIP.dat");

Upvotes: 83

Views: 131727

Answers (23)

koppor
koppor

Reputation: 20551

Facts:

  1. IntelliJ puts compiled classes to out/production/classes.
  2. IntelliJ puts resources to out/production/resources.
  3. IntelliJ puts out/production/classes as first in the class path
  4. The JDK searches the first directory in the classpath only [source]

Consequence: Resources are not found, independently whether MyClass.class or myClassInstance.getClass() is used.

My workaround: Copy all files from out/production/resources to out/production/classes. Then, it works.


Links:

Upvotes: 1

Joop Moore
Joop Moore

Reputation: 1

In intellij i had to Build > "Rebuild Project". It seems it didn't automatically see the files i added to the maven resources directory.

Upvotes: 0

sergeych
sergeych

Reputation: 869

Strangely effective in my case (IJ 2022.1.4) was: close project (for example, quit IDEA), delete the /.idea folder completely (egg, rm -rd .idea), open project. When it re-imports the project, it runs as expected. Note: you loose about everything not included in gradle configs.

Upvotes: 0

Asad-ullah Khan
Asad-ullah Khan

Reputation: 1863

A warning to all using the Path or Paths classes in Java: if you are on the god forsaken operating system known as Windows you will not be able to use Path.of or Paths.get as this will put backslashes in your path which Java will attempt to load and promptly fail. Instead use this:

Path.of(paths...).toString().replace(File.separator, "/")

You should always use this as it is OS independent. If anyone has a better or built in way please comment, I was unable to find one.

Upvotes: 0

CodeToLife
CodeToLife

Reputation: 4171

say you have :

titleLabel.setIcon(new ImageIcon(getClass().getResource("/uz/assets/icon.png")));//wrong !!

rightclick on the folder(mine is assets) an set Mark Directory as Resources if you dont see that rightclick on project name and pickup Open module settings

enter image description here

Rightclick on resorces folder(assets in my case) and select 'Resources' Now go back to the above java instruction and remove path BUT leave / like:

titleLabel.setIcon(new ImageIcon(getClass().getResource("/icon.png")));// correct one

Upvotes: 1

Memo 313 MediaSA
Memo 313 MediaSA

Reputation: 79

I realized using new File(location) works just fine in #dev and can also access files outside the /project folder

Upvotes: -1

yggdraa
yggdraa

Reputation: 2050

For those who use Intellij Idea: check for Settings > Build, Execution, Deployment > Compiler > Resource patterns.

The setting contains all extensions that should be interpreted as resources. If an extension does not comply to any pattern here, class.getResource will return null for resources using this extension.

Upvotes: 75

shareef
shareef

Reputation: 9581

I use Intellij version Ultimate 2019.3

Go to

Settings -> Compiler -> Resource patterns.

Click ok. Rerun Application/Server.

In my case, i included the jks in the project!

enter image description here

Upvotes: 0

Stefan Zhelyazkov
Stefan Zhelyazkov

Reputation: 3001

I was able to fix it by adding "./" to the beginning of the file like this:

getClass().getClassLoader().getResource("./file.txt")

Upvotes: 4

samet kaya
samet kaya

Reputation: 115

This is my example solution. Work for me.

The project structure:

•   Source Packages
   •    game
       •    Game.java
   •    game.images
       •    tas_right.png

In the game class:

URL path=this.getClass().getClassLoader().getResource("images/tas_right.png")

Upvotes: 3

Pnemonic
Pnemonic

Reputation: 1825

Instead of having the resource file in the same folder as your source files, create a resources folder parallel to the java source folder.

Before:

  • src
    • main
      • java
        • MyClass.java
        • file.bin
        • file.txt

After:

  • src
    • main
      • java
        • MyClass.java
      • resources
        • file.bin
        • file.txt

Upvotes: 1

Taras Melnyk
Taras Melnyk

Reputation: 3275

I've faced with the similar problem. From Java SE API for getResource​(String name) :

If the name begins with a '/' ('\u002f'), then the absolute name of the resource is the portion of the name following the '/'.

So I've added '/' before my directory : MyClass.class.getResource("/dir_name/").

In your case try to add '/' before your file name:

URL url = ExchangeInterceptor.class.getResource("/GeoIP.dat");

Upvotes: 13

Max
Max

Reputation: 5101

If you're using Gradle and IntelliJ, and changing Resource patterns didn't work, and your resource roots are set correctly...you can try this:

enter image description here

Settings > Build, Execution, Delpoyment > Build Tools > Gradle > Runner > Delegate IDE build/run actions to gradle. (IntelliJ 2017.3.3)

Source: https://youtrack.jetbrains.com/issue/IDEA-176738#comment=27-2518612

Upvotes: 8

Akash Agarwal
Akash Agarwal

Reputation: 2550

While using IntelliJ, I generated the project as a JavaFX app and then added maven framework support to it. Turns out, I then placed my resource in src/main/resources and had to add ./ behind every resource name that while using them in the code.

Also as stated in a previous answer, only loading the resource by a classLoader worked.

So for me, the final URL loading was done using:

URL url = getClass().getClassLoader().getResource(String.format(".%ssample.fxml", File.separatorChar));

The File.separatorChar returns / on *nix and \ on windows.

Upvotes: 5

MewX
MewX

Reputation: 4312

I solved this problem by pointing out the resource root on IDEA.

Initially the directory was so and the icon was a plain folder icon

Before

enter image description here

Right click on a directory (or just the project name) -> Mark directory As -> Resource Root.

After

after

Recompile & rejoice :P

Upvotes: 19

Wins
Wins

Reputation: 3460

Use the getResource method of the class' ClassLoader

URL url = ExchangeInterceptor.class.getClassLoader().getResource("GeoIP.dat");

Upvotes: 38

Semmel
Semmel

Reputation: 27

In case of eclipse.

Just a hint. Your code could be correct, but your jre configuration not. I ran into the the same error, nothing helped, until i checked the eclipse settings.

Make sure, that you set your execution environment right.

Preferences -> Java -> Installed JREs -> use "jdk..." as compatible JRE 

Upvotes: -3

Peter Jamieson
Peter Jamieson

Reputation: 745

The file needs to be in the classpath, e.g.: -

bin/my/package/GeoIP.dat

The / prefix seems to be a lie. The following would work.

URL url = ExchangeInterceptor.class.getResource("my/package/GeoIP.dat");

I suspect the issue is that you do not have the file in the classpath.

Upvotes: 2

Jakub Zaverka
Jakub Zaverka

Reputation: 8874

First, you need to make sure you are accessing the right file on the right path. You can verify that by getClass().getResource("GeoIP.dat").getAbsolutePath().

Secondly, the path specifier is case-sensitive, so make sure your file is not named "geoIP.dat" or "GeoIP.DAT".

Upvotes: -5

merovin
merovin

Reputation: 89

Just in case someone still has problems to understand that:

.getResource() grants you access to the local bin folder. That means, your resources need to be located in YourProject/bin/package/. The root folder is YourProject/bin/ and can be accssed by adding the prefix / to the String argument, like iirekm said.

Upvotes: 8

iirekm
iirekm

Reputation: 9446

Where do you have put this GeoIP.dat? In the same package as ExchangeInterceptor, or in the "root" package. If in the same package, your code is OK, if in the root - add '/' prefix.

Maybe you're using M2Eclipse? If configured incorrectly, it also may result in such problems. Another cause of such problems may be: misconfigured classloaders, misconfigured OSGi, ...

Upvotes: 2

Martin Algesten
Martin Algesten

Reputation: 13620

The path is relative to the classpath root and if you don't give an absolute path, it is looking in the same package as the class you're using (in this case ExchangeInterceptor). To find something in the root use /GeoIP.dat.

Upvotes: 49

javamonkey79
javamonkey79

Reputation: 17795

No, that is the right way afaik. Make sure the resource is on your classpath. This is often the cause of these types of problems.

Upvotes: 5

Related Questions