Android Test Support Library — Espresso

本篇簡單介紹如何設置 Android UI Test - Espresso 與 基本的用法。

What is Espresso ?

Espresso主要模擬使用者對一個 app project所執行的動作,必且是獨立一個 UI Thread 來執行操作,適用於白箱測試。支援 Android 2.1(API 8)以上,並使用 AndroidJunitRunner 執行。

Step 1 關閉動畫 (這個步驟很重要,一定要設定)

通常在設定 > 開發人員選項裡面,並確認以下三個功能皆為關閉的狀態。
- Window animation scale
- Transition animation scale
- Animator duration scale

Step 2 Set Up bulid.gradle

以下為官方的example

以上為使用Espresso前的基本設定。


Espresso 基本用法

Espresso有以下三種基本的Component
 1. ViewMatchers (找到你要的View,主要是 implements Matcher<? super View> interface)
 2. ViewAction (指定View要做的動作)
 3. ViewAssertions (assert 確認View的狀態)
以下為官方的example 
onView(withId(R.id.my_view)) // withId(R.id.my_view) is a ViewMatcher
 .perform(click()) // click() is a ViewAction
 .check(matches(isDisplayed())); // matches(isDisplayed()) is a ViewAssertion

由上面的example,可以看出流程為:
 1. Matcher利用R.id.my_view找到View
 2. 接著對View執行click的動作
 3. 最後確認View是否isDisplayed

接著介紹每個Component裡常用的method與用法

  1. Finding a view with onView在Espresso中都是使用onView method 與 ViewMatcher來找到View,除此之外ViewMatcher也支持hamcrest
    而常用的方法有以下幾種:
     1. 根據ID來找到View - onView(withId(R.id.textView))
     2. 根據View裡的text來找到ID - onView(withText(“textView”))
     3. 也可以使用allOf來做fliter,可以搭配 hasDescendant 、 hasSibling()、 is() 、instanceOf()來判斷條件onView(allOf(instanceOf(TextView.class)), withId(R.id.textView)) 
    這邊我覺得利用 ID 是最直覺的方法,不過如果你的命名有重複,會產生AmbiguousViewMatcherException,所以盡可能命名不要重複
  2. Performing an action on a view
    取得View後即可對View執行動作了!Espresso都是使用 perform method,常用的方法有以下幾種:
    click()
    - onView(withId(R.id.button)).perform(click());
    typeText() & closeSoftKeyboard(),輸入的文字與關閉鍵盤
    - onView(withId(R.id.editText)).perform(typeText(“Hello Espresso”), closeSoftKeyboard());
    swiftLeft()、swiftRight(),如果有使用viewPager的話可以向右或左滑動 — — onView(withId(R.id.viewpager)).perform(swipeLeft());
  3. Checking if a view fulfills an assertion
    Espresoo中的assertion都是用 check method,最常用的就是matches
    onView(withId(R.id.textView)).check(matches(withText(R.string.hello)));
Note : 官方不建議把要check的條件寫在onView中
 Don’t use assertions like withText inside 
onView.onView(allOf(withId(…), withText(“Hello!”))).check(matches(isDisplayed()));
此外官方建議AdpaterView(ListView、GridView)使用onData來取得View,不過因為敝公司已經幾乎使用RecyclerView來代替ListView所以有興趣的人可以參考[Using onData with AdapterView controls (ListView, GridView, …)](https://google.github.io/android-testing-support-library/docs/espresso/basics/index.html)

以下為官方的Example

這邊講解每個Annotation
@RunWith(AndroidJUnit4.class),一定要加,必須指定測試的是執行於AndroidJUnit4
@Rule,指定要測試的Activity
@Test,撰寫每個 Unit Test 時必須加上,每個Test皆為獨立的。

Set Up Run Test Configuration

撰寫完畢後,最後在設定 Run Test Configuration就大功告成了。
選擇「Run > Edit Configuration 」,點選左上角的的「+」新增一個 Android Tests在 General Tab 下的 Module 選擇「App」

參考資料
Hello Android!來杯 Espresso 吧!
Android Support Library
Android Support Library Tutorials
One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.