I have a need is to load a CSV file on a cron job, the file contains a list of ids. located in the resource folder.
At first I load it with a reader and a file path relative from the package to the file location. code is like:
IdLoader.class.getClassLoader().getResource("ids.csv");
It passed the local unit test loading. Yet when run it, the code build into a JAR file, and always give me an error with file can't be found.
Later I switched to another approach using:
public static final InputStream CSV_FILE_INPUT_STREAM =
IdLoader.class.getClassLoader().getResourceAsStream("ids.csv");
And after build, this make the code pass and load ids at runtime.
What was the difference between the two approaches that made the first one passed and the second one fails?
In unit test phase you do not have files in JAR so the resource path is a valid URL and you can open such file. That's because there would be no sense to build JAR when tests were not passing.
Once it passes tests and JAR is built your resource path URL points to content of JAR like 'myapp.jar!data/file.csv' that's unfortunately not a valid path to be opened by filereader.
So for a content fike of JAR you either need to use getResourceAsStream method of Classloader or open JAR with an JAR archiver (it's internally zip compression) and then you can load a file from there using a decompressor.