In Espresso, we mainly have three components:
-
ViewMatchers: Allows you to find a view in the current view hierarchy. This can be done in various ways, such as searching by id, name, child, and so on. You can also use Hamcrest matchers, such as containsString.
-
ViewActions: Allows you to perform actions on the views, such as clicking, typing, clearing text, and so on.
-
ViewAssertions: Allows you to assert the state of a view that checks whether the condition under the view assertion passes.
Let's take a look at the following steps to understand acceptance testing using Espresso:
- Here's an example of a text matcher (a text matcher matches the text; it's a part of ViewMatchers):
onView(withId(R.id.textView)).check(matches(withText(not(containsString("Hello")))));
- Now we will create a simple test that will test whether clicking on the button changes the text from Hello World! to Goodbye World!:
- The following is an espresso test written to test the preceding functionality:
class MainActivityTest {
@Rule
@JvmField var activityRule: ActivityTestRule<MainActivity> = ActivityTestRule(MainActivity::class.java)
@Test
fun testButtonBehaviour() {
// Testing if the text is initially Hello World!
onView(withText("Hello World!"))
.check(matches(isDisplayed()))
onView(withId(button)).perform(click())
// Testing if the text is initially Goodbye World!
onView(withText("Goodbye World!"))
.check(matches(isDisplayed()))
}
}
- In the first line, we have created a rule that provides functional testing of a single activity. This will open the activity before the tests are run and close it once the tests are completed. The statements in the testButtonBehaviour method check the UI conditions, such as whether the text is initially Hello World! (first condition), then performs a click action on the button, and then finally checks whether the text is now Goodbye World!.
- You can also get hold of the "God" object—that is, Context—using the instrumentation API:
var targetContext:Context = InstrumentationRegistry.getTargetContext()
- If you want to start the activity from the intent, you just need to provide false as the third argument in the constructor of ActivityTestRule; it can be used as shown:
@Rule
@JvmField var intentActivityRule: ActivityTestRule<MainActivity> = ActivityTestRule(MainActivity::class.java,true,false)
@Test
fun testIntentLaunch(){
val intent = Intent()
intentActivityRule.launchActivity(intent)
onView(withText("Hello World!"))
.check(matches(isDisplayed()))
}
Another cool feature of Espresso is to record the interactions using Record Espresso Test. This records all the interactions that you make with the app, and can generate tests from it. To use that feature, follow these steps:
- Go to Run on the toolbar and select Record Espresso Test:
- It will then open a dialog, on which you can see the recorded steps:
- Clicking on OK will automatically generate the tests based on your interaction.