About Unit Test In Android(安卓单元测试研究,附技术分享ppt)

  1. what is unit test?
    单元测试中的单元是一个系统或一个程序的组成部分,单元测试就是要对这些组成部分进行独立地、隔离地以某种约束和规则进行的测试,以发现每一部分的问题或者确定该部分不存在问题。

    Essentially, a unit test is a method that instantiates a small portion of our application and verifies its behavior independently from other parts. A typical unit test contains 3 phases: First, it initializes a small piece of an application it wants to test (also known as the system under test, or SUT), then it applies some stimulus to the system under test (usually by calling a method on it), and finally, it observes the resulting behavior. If the observed behavior is consistent with the expectations, the unit test passes, otherwise, it fails, indicating that there is a problem somewhere in the system under test.

    也即,单元测试实例化系统的一小部分,然后相对独立地确定此部分的行为是否正确。

  2. why unit test?

    The goal of Android unit test is to isolate each part of the program and show that the individual parts are correct. A unit test provides a strict, written contract that the piece of code must satisfy. As a result, it affords several benefits.—Wikipedia

    将系统的不同模块分离进行测试,有利于不同team和不同团队成员协作,不同team可以独立地完成各自的任务,而不用相互block,对于同一team的不同成员也同样适用。

  3. test theory

    • 系统要分层或者分模块
      不同的Part可能有不同的特征,应采用不同的测试工具和测试方法
    • 最小化原则
      如果一个测试没有pass的原因有多种,涉及的系统模块不止一个,那么这个测试不符合最小化原则,不能用于快速地发现问题。
    • 系统的各模块之间要解耦
      如果系统各模块之间的耦合过于严重,在实例化预测试Part时,需要Mock多个其他Part的组件,增加了测试成本和不确定性因素。
    • 从实际出发编写有价值的测试
      比如数据的状态很复杂,且其状态会影响其在RecyclerView中的显示或者交互,那么编写这部分的UI测试是有价值的。
    • 测试用例要全面,Mock对象要能逼近真实系统。
      在前后端隔离测试时,通常前端需要Mock一些数据,来模拟后端的返回,达到前端独立测试的目的
      道理很简单,如果不这样,测试就没有价值,就不能起到各系统模块独立开发独立测试的作用。
    • 测试对象,依赖对象,Mock对象,测试标准
      • 测试对象:我们关注的对象,测试的目的是确定他是否能正确工作,可以是View,可以是Service,DAO,或者Utils,对于View,我们关心的是其显示和交互是否达预期,对于后者,我们关心的是其接口的返回。
      • 依赖对象:可以是参数,也可以是测试对象的某个成员,测试对象的功能依赖于此对象,这是程序为什么解耦了就利于测试的根源。
      • Mock对象:根据依赖对象的数据结构和接口创建的模拟对象或者假对象
      • 测试标准:什么情况下Passed,什么情况下Failed
    • 如何在进行不同Parts之间的独立测试
  4. 分层
    一般采用MVP模式的Android APP架构分为三层:View层-Presenter层-Model层
    测试层也大致可分为三层:

    • UI测试层
      • 待测对象:所有的Activity,Fragment
      • 依赖对象:Presenter;Data;Event
      • Mock对象:Data;Dataset;Event
      • 测试标准:UI是否如预期显示和达到预期的交互效果
      • 如何独立测试:
        情形一:测试refreh,对象:RecyclerView
        ok: mock对象 > 一个有若干元素的list,标准 > RecyclerView是否显示了那些元素
        empty: mock对象 > emptylist,标准 > UI是否显示了空状态
        error: mock对象 > error,标准 > UI是否显示了错误状态
        情形二:测试某一按钮的点击交互:Button
        mock对象 > 点击事件,标准 > 点击事件后,系统是否做了正确的事
        总结:利用Android现有的Instrumentation测试框架,免去了创建Mock View,Mock Intent,Mock Context等的工作,我们只用创建Mock Data,Mock Event以及Mock State,然后测试UI的显示或者交互是否合乎标准。
        可用框架
        Android Instrumentation Test Framework and Esspresso and UI Automator and Mockito
        and AssertJ for Android and robolectric
    • Presenter测试层
      • 待测对象:Presenter,Model,View
      • 依赖对象:Model,View
      • Mock对象:Parameters,Subscriber,Model,View
      • 测试标准:请求能否被执行,数据能否正确传到UI
      • 如何独立测试:
        情形:调用presenter.loadMore() API,传入mock参数,mock Model,在Subscriber中检查返回的数据是否正确以及返回数据是否能够传递到View。
        总结: mock参数容易得到,mock Model是个麻烦,因为并非真正请求服务器,mock Model需要根据请求post mock data,而且要和测试代码运行在同一线程。
        可用框架:
        Hamcrest and AssertJ
    • Model测试层
      • 待测对象:所有的Presenter
      • 依赖对象:Repositiory,Datasource
      • Mock对象:NetworkParameter
      • 测试标准:dataSource 是否能返回正确的数据
      • 如何独立测试:mock 若干NetworkParameter,调Datasource.retrieveData。
        总结
        model层其实有两个实现者:Repository and DataSource,可以分别对这两部分测试,测Repository需要mock datasource和 mock NetworkParameter,测DataSource需要mock 若干NetworkParameter
        可用框架:
        Hamcrest and AssertJ
  5. 总结
    综上所述:UI层的测试可采用的第三方测试框架有多种,但 Esspresso and UI Automator是官方推荐的UI测试工具,Esspresso的API可读性很高,既能测UI,又能测交互(包括数据交互),而且扩展性较高。 Hamcrest and AssertJ提供了可读性很高的断言API,后者还支持利用Generator和模板生成断言类,功能很强大,唯一不足的是AssertJ的2.+版本引用的部分JDK API在android系统是被精简掉的,所以会出现编译错误,无法运行测试,使用AssertJ 1.+版本或者不适用AssertJ 2.+的部分API可避免以上问题。
    最后:为了测试,请编写低耦合的代码!

参考资料
技术分享ppt:单元测试研究
[1]. Unit Tests, How to Write Testable Code and Why it Matters
[2]. Android Testing Tutorial: Unit Testing like a True Green Droid
[3]. Android Espresso 测试框架介绍
[4]. Using Espresso for Easy UI Testing
[5]. Unit tests with Mockito - Tutorial
[6]. Android/Testing
[7]. Robolectric
[8]. Hamcrest
[9]. Esspresso Examples In Github
[10]. Introduction to Android Espresso
[11]. Testing UI for a Single App
[12]. Google Sample in Github
[13]. Mockito Tourial
[14]. EasyMock

你可能感兴趣的:(android,单元测试)