Sunday, May 21, 2017

Testing Content Providers with Robolectric

There are many samples of testing content providers with Robolectric that seem incorrect.  They would instantiate content provider directly, manually call onCreate(), and then register the provider with the shadow content resolver.  But when you do this, the provider's getContext() will return null if you call it from within onCreate() method.

What seems to work is the following:

@RunWith(RobolectricTestRunner.class)
@Config(constants = BuildConfig.class)
public class ProviderTestJUnit {
    private static final String AUTHORITY = “com.example.provider";
    private Context context;

    @Before
    public void setUp() {
        context = RuntimeEnvironment.application;
        ShadowContentResolver.registerProviderInternal(AUTHORITY,
                Robolectric.setupContentProvider(Provider.class));
    }

    @Test
    public void simpleQuery() {
        final ContentResolver cr = context.getContentResolver();
        final Uri uri = new Uri.Builder()
                .scheme(ContentResolver.SCHEME_CONTENT)
                .authority(AUTHORITY).build();
        final Cursor cursor = cr.query(uri, null, null, null, null);
        assertNotNull(cursor);
    }
}

When you call ShadowContentResolver.registerProviderInternal(), the content provider is created, properly initialized, and then its onCreate() is called.  Calling getContext() from within onCreate() will return non-null context.

After simple setUp() initialization the test will run.  The test code looks the same as if you tested your provider on an emulator or a device.


No comments:

Post a Comment