4

I have been reading the same questioned that were asked here and on Quora, however, I still don`t understand why I cannot access the file that is located in the 'src/main/resources' folder. Everything works when I specify relative path manually "src/main/resources/config/serverConf.xml"

Project structure:

src/main/java/"project related folders"
src/main/resources/config/serverConf.xml

And the main class:

public class Main{

    public Main(){
        File file = new File(this.getClass().getResource("config/serverConf.xml").getPath());
        if(file.exists())
            System.out.println("Yes");
        else
            System.out.println("No");
    }

    public static void main(String[] args){
        Main main = new Main();
    }
}
alex_z
  • 416
  • 5
  • 12
  • 1
    https://stackoverflow.com/q/2593154/1531971 –  May 31 '18 at 19:05
  • 1
    Resource is not a file - it won't work. Your next question would be like "why it works from eclipse but does not work from JAR" – Antoniossss May 31 '18 at 20:04
  • Antoniossss could you explain how to make the program execute as I tried what experienced users answered and nothing worked. Also, I am not using Maven as a built tool... – alex_z May 31 '18 at 20:13
  • While ever `File` can be represented as an `URL`, not all `URL`s can be represented as a `File`. Try printing the URL returned from `.getResource(` and see if it contains a `!`. If so, that's one of the times. My question for you is *why does this program need a **`File`** as opposed to an `URL` or (otherwise) just access to the resource?* – Andrew Thompson Jun 01 '18 at 03:26
  • *"Antoniossss could you explain.."* Tip: Add @Antoniossss (or whoever, the `@` is important) to *notify* the person of a new comment. – Andrew Thompson Jun 01 '18 at 03:28
  • @AndrewThompson I tried to access the URL as yesterday, and I was getting NullPointerException – alex_z Jun 01 '18 at 10:01
  • *"I tried to access the URL as yesterday, and I was getting NullPointerException"* .. and you thought that starting with an invalid path to a `null` URL, converting that invalid URL to a `File` would somehow ***improve things?*** Have you ever heard the phrase *"Garbage in, garbage out!"*? – Andrew Thompson Jun 01 '18 at 10:07
  • @AndrewThompson now I understand what you mean by trying to use URL. I needed to access the file by firstly specifying ‘main’ directory (/main/resources/config/serverConf.xml). – alex_z Jun 01 '18 at 10:17
  • *"I needed to access the file by firstly specifying ‘main’ directory (/main/resources/config/serverConf.xml)."* That sounds wrong. Or at least, fragile and will later (when the app. is packaged for distribution) break. Did you look at the URL to see if it contains `!`? Did it? You still do not seem to have answered the question ***"why does this program need a File as opposed to an URL or (otherwise) just access to the resource?"*** I don't ask these questions for idle curiosity. I need that information to best help. So what is the answer? – Andrew Thompson Jun 01 '18 at 10:41
  • @AndrewThompson I used File, as then I used the DocumentBuilder to further Xml parsing. But URL has the getFile() so the File does not required. This is what I get when I printed out the Url (‘path to project’/out/production/‘Project Name’/Example/ – alex_z Jun 01 '18 at 10:46
  • *"I used File, as then I used the DocumentBuilder to further Xml parsing"* OK, but most APIs that have methods that accept files, also have methods that accept either an URL or a stream. Either of those can still work if the `serverConf.xml` document is in a Jar, or on another server, **where a `File` cannot work.** So don't ever convert the resource path / URL to a `File`! – Andrew Thompson Jun 01 '18 at 10:51
  • @AndrewThompson Yeah, thanks ! – alex_z Jun 01 '18 at 10:53

4 Answers4

2
"config/serverConf.xml"

Should be

"/config/serverConf.xml"
Antoniossss
  • 31,590
  • 6
  • 57
  • 99
1

The users Nikolas and Antoniossss already answered the question. Just to give a short explanation in case it helps. From your directory structure I guess you're using Maven. When you build the project using Maven, Maven copies all the folders and files to the target/classes folder which is the root of the class path. So in your case the following should work:

File file = new File(this.getClass().getResource("/config/serverConf.xml").getPath());

But if you want to use the relative path as in your original code, you should create the config folder in the directory where the Main.java class is located and put the serverConf.xml there. Then the following should work too:

File file = new File(this.getClass().getResource("config/serverConf.xml").getPath());

That said, the better way is to put the configuration files under src/main/resources folder.

ujulu
  • 3,289
  • 2
  • 11
  • 14
0

Usually the leading / will be your go-to with filepaths, but I was able to just give it the file name and it recognized it just fine for me.

File file = new File(this.getClass().getResource("serverConf.xml").getPath());

Isaac Smith
  • 137
  • 9
0

The url supplied to getResource() method must be relative to your classpath. Thus if you had to run this from the command line, you would need to supply the path to your resources folder for this to work, i.e:

java Main -cp src/main/resources/

If you're using an IDE, there's usually a configuration for adding the classpath

Bcombes
  • 1
  • 3