Google+ 團隊的 Android UI 測試
- 原文鏈接:How the Google+ Team Tests Mobile Apps
- 譯者:allenlsy
- 譯者博文地址:http://allenlsy.com/android-ui-tests-in-google-plus-team/
- 校對者:
</ul> </blockquote>Android 測試主要分為3個類型:
單元測試(Unit Test)
區分UI代碼和功能代碼在Android開發中尤其困難。因為有時Activity既有Controller的功能,又有View的功能。Robolectric是 一個很優秀的Android測試框架,它提供了一個Android框架的stub,這樣測試運行時實際上是在JVM上運行,而不是在Android平臺 (比如Robotium和Instrumentation都是在Android平臺運行測試),從而提高了速度。另外請參考Gradle 對 Unit tests的支持。
封閉UI測試 (Hermetic UI Test)
這個測試方法使得測試不需要外部依賴和網絡請求。這樣做的主要目的是提高測試速度,減少測試時的外部影響,畢竟網絡調用是相對很慢的。Espresso可以用來模擬用戶的UI操作。
Monkey Test
Monkey Test 就好像一只猴子在測試app一樣,沒有任何規律的在你的app上胡按。計算機運行monkey test的時候,每秒鐘能做出幾千個UI動作(可以配置這個頻率),比如點擊和拖拽。所以這個測試可以算是一個壓力測試,用來檢測ANR。
Google+ 團隊總結了一些 UI 測試時的經驗和策略。
策略1: 不要使用 End-to-end 測試作為UI測試
先看一些定義:UI 測試 是為了確保對于用戶的UI動作,app能返回正確的UI輸出。End-to-end測試(E2E test) 是通過客戶端和后臺服務器的交互測試整個系統。下面這個圖在展示了測試步驟:
通常做UI測試,你需要后臺服務器,所以可能產生網絡調用。所以UI測試和E2E測試很像。但是在E2E測試中會遇到很多困難:
- 測試速度緩慢
- 網絡請求會失敗
- 難以Debug
</ul>下面看看如何解決這些問題。
策略2:使用偽服務器做封閉UI測試
這個策略中,你可以通過假的后臺服務器來避免網絡請求,以及其他外部依賴。技術上,你就需要在app本地提供返回數據了。有很多辦法可以做到,比如 手動做一次網絡請求,把response保存下來,在測試的時候重復這個response。這樣你就做了一個封閉在本地的偽服務器
當你有了這個偽服務器,你還需要給這個偽服務器寫測試。于是這是,你的E2E測試就分為了服務器測試,客戶端測試和集成測試。
現在這樣的解決方案,你需要自己維護偽服務器,本地數據庫和tests了。
下面這是E2E 測試的示例圖:
這是使用了偽服務器的封閉UI測試
其區別在于:Frontend Server的幾個數據源變了。由原來的真實后端,變成了封閉服務器,或者是mock服務器。這個在測試調用網絡API的時候非常有用。
策略3:使用Dependency Injection
Dependency Injection(依賴注入)可以幫助生成測試數據。我推薦選擇使用dagger作為依賴注入框架。
依賴注入在UI test和unit test都中都可以用于生成假數據。在instrumentation test框架中,測試用的apk文件和測試時運行的app,是在同一個進程下面,所以測試代碼可以調用app代碼。你還可以覆蓋app的 classpath,通過這種方式注入假數據。比如你可以用依賴注入來偽造一個網絡連接的實現,調用這個網絡連接的時候就可以提供假數據。
策略4:把app分為小的libraries
這個方法可以更好地模塊化你的app。你的app被分為更小的類庫之后,你可以為這些類庫添加他們自己的UI依賴或gradle庫依賴。
當你有了自己的庫,并提供依賴注入的支持,那么你可以為各個庫寫測試app。最后,可以寫集成測試來確保類庫直接的合作正確。
比如我們有一個登陸功能的庫,那么我可以寫一個測試app只為這個登陸功能庫:
總結:
- 不要用E2E測試來代替UI測試。更好的做法是用單元測試 + 集成測試 + UI測試。
- 使用封閉測試策略
- 使用依賴注入
- 把app分為不同的小組件小類庫,并分別寫測試,然后再寫集成測試來確保各組件之間的交互正確。
- 模塊化 UI 測試已經被證明了比E2E測試快,并且十分穩定。這樣的測試又能極大的提高開發效率。