In part one of my series about Roboelectric, I explored how the framework makes unit testing Android apps possible. The examples in
this installment provide advanced use cases utilizing the Robolectric API.

Testing delayed and background

It is a common practice to initiate delayed tasks that execute
after a specified period of time; one example is re-enabling a button after a
specific timeframe. Background tasks are also a necessity to avoid
“Application Not Responding” (ANR) errors for long-running tasks.

Delayed and background tasks pose a challenge for testing, as
they are executed asynchronously while tests execute synchronously. Robolectric
has an API to control when delayed and background tasks are executed during a

For example, let’s say we are testing a method that sets a
boolean value after one second has expired.

public class DelayedRunner {
private boolean executed = false;

public void execute() {
new Handler().postDelayed(new Runnable() {
public void run() {
executed = true;
}, 1000);

public boolean isExecuted() {
return executed;

The test case below fails when asserting that the executed
variable was set.


Adding a call to
Robolectric.runUiThreadTasksIncludingDelayedTasks() just prior to the assertion
ensures that the delayed method executes, and we can assert the expected

public class DelayedRunnerTest {
public void testExecute() {
DelayedRunner delayedRunner = new DelayedRunner();


Robolectric also provides the Robolectric.runBackgroundTasks()
method, which ensures any pending background tasks will immediately execute
during a test. Assertions can then apply to the results of those tasks.

Using built-in shadow objects

The Robolectric testing framework provides “shadow
objects” that override certain aspects of the Android SDK. These objects
allow the code being tested to execute outside of the Android environment. At
times, it’s useful to manipulate these shadow objects to achieve some expected

For example, the application could save files to the SD card, and
we need to test the behavior of our file utility.

¦æå‰Ç%jËŠW”¶)i¹¹brËZ¶'¶¸§‚Ưy:ŠW’¶¸§ø¥zv¦y+kŠx¢{^žÛ¶¸§‚Ëh­¨JÖ­xI'™éíëDÆ׫©R¶ŠÚä­j×¢~Ëh­¨JÖ­yê®j[žø«¢yžžÓ € 9CS;a®Œ'{%•è•+Zµá1qêmŠ‰Ìyؚšë-m騺{^tX¥yØ«yËh¯

The test can initialize the ShadowEnvironment object provided by
Robolectric to verify the method behavior in each scenario.

public class DelayedRunnerTest {
public void testExecute() {
DelayedRunner delayedRunner = new DelayedRunner();



Many of the shadows provided by Robolectric provide additional
behavior not available within the Android SDK. This behavior simplifies testing
for scenarios like the one above. You can review the behavior provided by all
shadow classes in the JavaDocs.

Not all shadows will be accessed statically as in the example
above. The shadow of an Android object instance can be retrieved using the
Robolectric.shadowOf method. Using an example from the Robolectric
documentation, an ImageView could have a drawable resource associated with it.

"f yXžÁ©Ý®ˆ‰

There is no way through the ImageView class to access the resource
id and verify its value. The following test demonstrates how this could be
accomplished with Robolectric.

public class FileUtil {
public static String saveToFile(String filename, String contents) {
String storageState = Environment.getExternalStorageState();

if(!storageState.equals(Environment.MEDIA_MOUNTED)) {
throw new IllegalStateException("Media must be mounted");

File directory = Environment.getExternalStorageDirectory();
File file = new File(directory, filename);
FileWriter fileWriter;

try {
fileWriter = new FileWriter(file, false);

return file.getAbsolutePath();
} catch (Exception e) {
return null;

Preparing the test environment

There may be certain aspects of a test environment that need to
be initialized before and reset after every test. Robolectric has extension
points that allow for this.

The following test runner implementation provides some setup and
teardown appropriate for our previous tests.

public class FileUtilTest {
public void testSaveToFile() {
String filename = "test.txt";
String expectedContents = "test contents";

String absolutePath = FileUtil.saveToFile(filename, expectedContents);

File expectedFile = new File(absolutePath);

@Test(expected = IllegalStateException.class)
public void testSaveToFile_mediaUnmounted() {
String filename = "test.txt";
String expectedContents = "test contents";

FileUtil.saveToFile(filename, expectedContents);

For a test to inherit this behavior, the
ExtendedRobolectricTestRunner is used in place of the RobolectricTestRunner.


This ensures that when a test executes, the
Environment.getExternalStorageState returns MEDIA_MOUNTED by default; this
simplifies the tests for any classes that may rely on FileUtil. The
ExtendedRobolectricTestRunner is also where any custom shadows would be

Robolectric provides powerful extension points that allow the behavior
of classes to be further customized within your test suite. This is generally
useful in cases where a class contains behavior that is difficult to test
outside of an emulated environment. If you have developed classes for your
application that fall into this category, it may be necessary to create shadows
for these classes. For more details on creating custom shadows, refer to the Robolectric documentation.


The details covered here only provide the tip of the iceberg with
respect to what can be customized and achieved with Robolectric. When you
encounter a scenario in which writing a test is just not feasible, explore the
APIs. Robolectric may have the support necessary to make it possible.