2

I imported an Android sample coded by Amazon involving AWS's DynamoDB which I got from here and was presumably written for Eclipse: https://github.com/awslabs/aws-sdk-android-samples/tree/master/DynamoDBMapper_UserPreference

Since Android Studio (0.8.1) uses gradle instead of ant, naturally things got auto-moved around in terms of dir structure when importing so (part of) it looks like this:

enter image description here

PropertyLoader gets the TVM credential info it needs to connect to the database DynamoDB from AwsCredentials.properties. Relevant methods:

public class PropertyLoader {

    private boolean hasCredentials = false;
    private String tokenVendingMachineURL = null;
    private boolean useSSL = false;
    private String testTableName = null;

    private static PropertyLoader instance = null;

    public static PropertyLoader getInstance() {
        if ( instance == null ) {
            instance = new PropertyLoader();
        }

        return instance;
    }

    public PropertyLoader() {
        try {
            Properties properties = new Properties();
            properties.load( this.getClass().getResourceAsStream( "AwsCredentials.properties" ) );

            this.tokenVendingMachineURL = properties.getProperty( "tokenVendingMachineURL" );
            this.useSSL = Boolean.parseBoolean( properties.getProperty( "useSSL" ) );
            this.testTableName = properties.getProperty( "testTableName" );

            if ( this.tokenVendingMachineURL == null || this.tokenVendingMachineURL.equals( "" ) || this.tokenVendingMachineURL.equals( "CHANGEME" ) || this.testTableName.equals( "" ) ) {
                this.tokenVendingMachineURL = null;
                this.useSSL = false;
                this.hasCredentials = false;
                this.testTableName = null;
            }
            else {
                this.hasCredentials = true;
            }
        }
        catch ( Exception exception ) {
            Log.e( "PropertyLoader", "Unable to read property file." );
        }
    }

However the getResourceAsStream line properties.load( this.getClass().getResourceAsStream( "AwsCredentials.properties" ) ); returns null. As you can see in my screenshot, AwsCredentials.properties is in the same dir as PropertyLoader and matches the case, which is all that should be required based on my readings of the method: http://mindprod.com/jgloss/getresourceasstream.html

getResourceAsStream() is always returning null

I have tried other things such as prefixing "\" (i.e. properties.load( this.getClass().getResourceAsStream( "\AwsCredentials.properties" ) ); and copying the credentials file and placing in the src folder (you can't see it in this screenshot because the explorer sorts by filetype(?) and places 'main' first, but it's there) as per this:

getResourceAsStream returning null

However, that hasn't fixed the issue either. Having tried these options and done research, I'm confused as to why it's returning null. How can I fix this?

Community
  • 1
  • 1
Kurt Wagner
  • 3,295
  • 13
  • 44
  • 71

2 Answers2

8

Created a dir called resources under /src/main/ and placed AwsCredentials.properties there and used

properties.load( PropertyLoader.class.getClassLoader().getResourceAsStream( "AwsCredentials.properties" ) );

instead of

properties.load( this.getClass().getResourceAsStream("AwsCredentials.properties" ) );

Not as elegant as I would like, but it works.

Kurt Wagner
  • 3,295
  • 13
  • 44
  • 71
-1

For up to a day I was struggling with this as well. And finally I was able to resolve this very neatly. The problem is not in the JAVA but in the all project structure. E.g. in Android Studio the whole project is under src/main/java whereas main is a flavour of the project. So if you've file(-s) to read from in source's package (e.g.) com/my/example/app you have to edit the build.gradle file for read (clazz.getResourceAsStream(file)) to work properly. I.e. under android define sourceSets like this:

android {
    /* ... Your stuff ... */

    sourceSets {
        // Lets have two flavours to make it more clear
        main {
            resources.srcDirs = ['src/main/java']
        }

        flavourFoo {
            resources.srcDirs = ['src/flavourFoo/java']
        }
    }
}

Hope this helps!

Toochka
  • 894
  • 1
  • 9
  • 25