Running UI tests take more time than unit tests, but we still need it. Espresso is an Android UI test framework. you can get a view by id or text, then click a button or type data in an EditText to verify behavior is correct.
Find a view
Finding a view by its id
onView(withId(R.id.someId)).perform(typeText("Some Text"))
Finding a view by matching a text.
onView(withText("Some text")).check(matches(isDisplayed()))
Clicking a view by its id
onView(withId(R.id.button)).perform(click())
Espresso dependencies
Add the following dependencies on app’s build.gradle file.
dependencies {
androidTestImplementation 'com.android.support.test:rules:1.0.2'
androidTestImplementation 'com.android.support.test:runner:1.0.2'
androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.0.2'
}
Write UI test
Use previous sample: sing up.UI test is located at androidTest
just like the Instrumented test. Create a RegisterTest
class.
@LargeTest annotation indicates that the test duration can be more than 1 second.
@LargeTest
class RegisterTest {
}
To test MainActivity, use ActivityTestRule
to get an Activity instance.
class RegisterTest {
@Rule
@JvmField
var activityActivityTestRule
= ActivityTestRule(MainActivity::class.java)
}
Write a UI test for register success:
- Type a123456789 on
loginId
. - Type a111111111 on
password
. - Click the
send
button. - Verify contains a text “Sign Up Success” on view.
@Test
fun rightPassword_should_startActivity() {
//type "a123456789" on loginId
onView(withId(R.id.loginId)).perform(typeText("a123456789")
, ViewActions.closeSoftKeyboard())
//type "a111111111" on password
onView(withId(R.id.password)).perform(typeText("a111111111")
, ViewActions.closeSoftKeyboard()) //click send button
onView(withId(R.id.send)).perform(click()) //verify screen should display "Sign Up Success"
onView(withText("Sign Up Success"))
.check(matches(isDisplayed()))
}
Click the green triangle to run the test. You’ll see the emulator is running test.
Typing the wrong password should alert.
@Test
fun wrongPassword_should_alert() {
//type login id
onView(withId(R.id.loginId)).perform(typeText("a123456789")
, ViewActions.closeSoftKeyboard()) //type password
onView(withId(R.id.password)).perform(typeText("1234")
, ViewActions.closeSoftKeyboard()) //click send button
onView(withId(R.id.send)).perform(click())
//register fail should alert
onView(withText("Error"))
.inRoot(isDialog())
.check(matches(isDisplayed()))
}
Run the test and pass it.
Let’s refactor the code. The flowering codes show how to type a123456789 on loginId
and type a111111111 on password
.
@Test
fun rightPassword_should_startActivity() {
onView(withId(R.id.loginId)).perform(typeText("a123456789"), ViewActions.closeSoftKeyboard())
onView(withId(R.id.password)).perform(typeText("a111111111"), ViewActions.closeSoftKeyboard()) ...
}
Extract these two lines of codes to the inputRightRegisterData
method. In this test case, we only need to know typing right id and password should start an Activity, the detail should be encapsulation.
@Test
fun rightPassword_should_startActivity() {
inputRightRegisterData()
...
}
Same as wrong password tests case.
@Test
fun wrongPassword_should_alert() {
inputWrongRegisterData()
...
}
Github:
https://github.com/evanchen76/AndroidTDD_uitestsample
Reference:
https://developer.android.com/training/testing/espresso
Next: Android TDD Part 10 — Robolectric