Nodnarb3
Nodnarb3

Reputation: 27

Reading a file from resource package

I have read many posts on here and done many Google searches but I am still unable to read a file from another java package within my current project.

In one of my classes I have the following code, however the input stream is always null. I have tried using the context class loader, as well as many other solutions but to no avail.

InputStream is = this.getClass().getResourceAsStream( "opcodes.txt" );  
System.out.println(is);

Another attempt was:

InputStream is = ClassName.class.getResourcceAsStream("/resources/opcodes.txt");

which also returned null.

Any help or explanation for why I can not find the file within a resource package would be great.

p.s. I am using eclipse if that makes a difference.

EDIT: If I use an OpenFileDialog to find the file, I am able to open and read it, so the file does exist and is not corrupt.

Upvotes: 0

Views: 1672

Answers (2)

deepak marathe
deepak marathe

Reputation: 408

Resource files are generally placed in src/main/resources/ directory in your project. These resources are also packed in the jar alongside the compiled class files with .class extension.

I have created a sample maven project with the directory hierarchy discussed above. project structure

The resource file sample-resource.properties can be accessed in the program as below:

    package temp;

    import java.io.InputStream;
    import java.util.Scanner;

    public class ResourceTest {
        public static void main(String[] args) {
            InputStream inputStream = ResourceTest.class.getResourceAsStream("/sample-resource.properties");
            Scanner scanner = new Scanner(inputStream);
            while (scanner.hasNext()) {
                System.out.println(scanner.nextLine());
            }
        }
    }

This would read and print the contents of the resource file: enter image description here

Upvotes: 1

logcat
logcat

Reputation: 283

The documentation of the getResourceAsStream() method, found here: http://docs.oracle.com/javase/7/docs/api/java/lang/Class.html#getResourceAsStream(java.lang.String) says that: " Before delegation, an absolute resource name is constructed from the given resource name using this algorithm:

If the name begins with a '/' ('\u002f'), then the absolute name of the resource is the portion of the name following the '/'. Otherwise, the absolute name is of the following form: modified_package_name/name Where the modified_package_name is the package name of this object with '/' substituted for '.' ('\u002e'). "

Your first attempt would have succeeded had the resource been located within the same package as the one the class you're invoking the method from is located. Your second attempt fails because, like the documentation says, the name of the file you give ("/resources/opcodes.txt") is replaced by "resources/opcodes.txt". I guess it means that the method will now search for package resources WITHIN the package where the class that invokes the method is located and not outside of it. Since you don't have such an inner package, the method returns null.

A workaround would be to define a class within the package where your resource is located. That class could be empty for all you care. Just call:

ClassWithinResourcePackage.class.getResourceAsStream("opcodes.txt");

from within the class you currently invoke the method from, and it works.

I also tried to use the ".." syntax I know from command line, but it doesn't work. I think the documentation implies the method is looking for a file within the same package only.

Upvotes: 1

Related Questions