Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Robolectric in Android: Testing events?

I have written a few tests using robolectric and I now want to do some real test classes.

One thing I notice is that I can't test the events like onCreate, onLocationChanged etc.

What is the standard practice for testing the events?

Should iI extract the code that's inside the events and place them in a method, the event would call the method and also robolectro could call the method, of course the method would need to be public, right?

Also if I wish to test something within my method that is normally a private variable then I would need to add a public getter, right? Can I check this from robolectric?

Is there a better way to expose data to robolectric ?

like image 394
Martin Avatar asked Jul 24 '12 07:07

Martin


People also ask

What is Robolectric testing?

Robolectric is a framework that brings fast and reliable unit tests to Android. Tests run inside the JVM on your workstation in seconds. With Robolectric you can write tests like this: @RunWith(RobolectricTestRunner.

What are the disadvantages of using Robolectric?

So the main benefit about Robolectric is that it is a lot faster than Espresso or Instrumented tests in general. The downside is that it fakes an Android environment which you should be aware of. To validate real world problems, better use a classic Android Framework approach.

What is the significance of Robolectric?

Robolectric provides a JVM compile version of the android. jar file. Robolectric handles views, resource loading, and many other things that are implemented in the Android native. This enables you to run your Android tests in your development environment, without requiring any other setup to run the test.


2 Answers

When testing onCreate, I get robolectric to call onCreate and then test that the activity is in the correct state after onCreate. Here's an example:

@RunWith(RoboTestRunner.class)
public class DashboardActivityTest {

    private DashboardActivity activity;

    @Before
    public void setUp() throws Exception {
        activity = new DashboardActivity();
    }

    @After
    public void tearDown() throws Exception {
    }

    @Test
    public void testDashboardHasButtons() {
        activity.onCreate(null);
        Button btn1= (Button) activity.findViewById(R.id.btn1);
        assertNotNull(btn1);
        Button btn2= (Button) activity.findViewById(R.id.btn2);
        assertNotNull(btn2);
    }
}

Testing private methods usually indicates your design could be improved and isn't a Robolectric specific problem.

See this question for lots of discussion: How do I test a class that has private methods, fields or inner classes?

like image 61
Tom Pierce Avatar answered Sep 29 '22 10:09

Tom Pierce


As of v2 of Robolectric, this is not the proper way to start activities now:

MyActivity testActivity = new MyActivity();
testActivity.onCreate(null);

Now the proper way is to use this:

MyActivity testActivity = Robolectric.buildActivity(MyActivity.class).create().get();

This will give you an instance of the activity after calling onCreate.
If you want to test onStart, onResume, onPause, etc, it is the same way, just more methods.

MyActivity testActivity = Robolectric.buildActivity(MyActivity.class).create().start().resume().pause().stop().destroy().get();  

(add or remove the methods in above line of code to test the exact instance of the activity you want)

Just wanted to clarify the really new nice feature of Robolectric.

like image 43
levibostian Avatar answered Sep 29 '22 10:09

levibostian