单元测试(模块测试)是开发者编写的一小段代码,用于检验被测代码的一个很小的、很明确的功能
是否正确。通常而言,一个单元测试是用于判断某个特定条件(或者场景)下某个特定函数的行为。
例如,你可能把一个很大的值放入一个有序list 中去,然后确认该值出现在list 的尾部。或者,你可能
会从字符串中删除匹配某种模式的字符,然后确认字符串确实不再包含这些字符了。
基于JUnit 来进行测试,包括运行在JVM上的本地单元测试,和运行在Android设备上的Instrumented测试。
JUnit
把单元测试或集成测试类写成JUnit 4测试类。此框架提供了便捷的方法来执行测试中常见的建立
(setup),拆除(teardown)和断言(assertion)操作。
一个基本的JUnit 4测试类是一个包含一个或多个测试方法的Java类。测试方法应以@Test注解开始,
并包含代码执行和验证单一的功能,这通常是待测组件中的一个业务逻辑单元。
一:基本流程
写测试类
写测试方法
运行JUnit Test进行测试
二:注解方式
在你的JUnit测试类中,你可以使用下面的注解,来对你测试代码的片段做特殊处理:
@Before:使用此注解来指定一段代码为建立(setup)操作。测试类会在每一个测试方法之前调用此
代码块。你可以有多个@Before注解的方法,但测试类调用这些方法的顺序无法保证。
@After:使用此注解来指定一段代码为拆除(teardown)操作。测试类会在每一个测试方法之后调
用此代码块。同样,你可以在测试代码中定义多个@After操作。使用此注解释放内存资源。
@Test:使用此注解来标注测试方法。一个测试类可以包含多个测试方法,都以此注解开头,返回
值为void
@Rule:Rule能以一种可重用的方式,灵活地添加或重定义每一个测试方法的行为。在Android测试
中,此注解是和Android Testing Support Library提供的测试规则类结合起来使用,例如ActivityTestR
ule或者ServiceTestRule。
@BeforeClass:使用此注解标明测试类只会调用一次的静态方法。此步骤对于昂贵的操作(例如连接
到数据库)是很有用的。
@AfterClass:使用此注解标明,在所有测试方法执行完毕后,会执行一次的静态方法。这一步骤中,
应释放在@BeforeClass代码块中分配的资源。
@Test(timeout=):一些注解支持设置参数。例如,你可以为测试方法指定一个超时时间。如果测试
没有在指定时间内介绍,它会自动失败。超时时间以毫秒为单位,例如@Test(timeout=5000)。
执行顺序为:@BeforeClass --> @Before --> @Test --> @After --> @AfterClass
使用JUnit的断言(Assert)类来验证对象状态的正确性。断言方法会比较你预期的值和测试得到的实
际值,如果不符则会抛出异常。Assertion classes描述了这些方法的细节。
三:断言方法
常用的断言方法:
assertEquals(args):根据传入的参数判断预期结果和实际结果是否相等。
assertTrue/False(args): 判断一个条件为true/false。
assertNotNull/Null(args): 判断一个对象是否为空。
assertSame/NotSame(args): 判断两个对象是否指向同一个对象。
fail(args): 中断测试方法,可以为其设置信息。
四:测试示例
Android studio 默认支持JUnit,创建一个新的项目,项目中自动添加了JUnit的依赖testCompile
'junit:junit:4.12',所以可以直接在Android studio中使用JUnit来进行单元测试。
本地单元测试
运行在本地JVM上的单元测试,主要的测试类在路径src/test下(Project面板视图)。
第一步:项目中的被测试类: 确定一个被测试的类,测试里面的方法运行返回是否符合功能要
求,比如在网络请求的时候,测试接口构建是否正确。
- // 要被测试的接口或类
- public interface RetrofitApi {
- @GET("https://api.github.com/users/gqq")
- Call<ResponseBody> getRequest();
- @POST("/Handler/UserHandler.ashx?action=register")
- Call<UserResult> getUserRequest(@Body User user);
- }
复制代码 第二步:创建测试类: 确定要被测试的类之后,在test路径下创建相应的测试类和测试方法来进
行测试,而更快捷的方式在该类上点击右键菜单--> Go To --> Test(ctrl+shift+T快捷键),自动创
建相应的测试类和方法,创建到test路径下
第三步:完善测试类和方法:
测试类和测试方法创建完成之后,在相应的方法中完善测试方法:
- public class RetrofitApiTest {
- private RetrofitApi retrofitApi;
- // @Before 在测试方法执行之前被调用
- @Before
- public void setUp() throws Exception {
- retrofitApi = RetrofitClient.getInstance().getRetrofitApi();
- }
- // 测试方法
- @Test
- public void getRequest() throws Exception {
- ResponseBody body = retrofitApi.getRequest().execute().body();
- assertNotNull(body);
- }
- // 测试方法
- @Test
- public void getUserRequest() throws Exception {
- UserResult userResult = retrofitApi.getUserRequest(new User("123", "123")).execute().body();
- assertEquals(1,userResult.getCode());
- }
- // 测试完成后执行
- @After
- public void tearDown() throws Exception {
- }
- }
复制代码 虽然在Android框架内支持运行instrumentation测试,但是目前开发重心主要集中在刚刚发布的作为
Android Testing Support Library一部分的新的AndroidJUnitRunner,测试库包含Espresso,用于运行
功能UI测试的框架。
第一步:添加依赖: 在gradle2.2默认添加了对单元测试的支持
- androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
- exclude group: 'com.android.support', module: 'support-annotations'
- })
- android {
- defaultConfig {
- testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
- }
- }
复制代码 所以不再进行依赖的添加。 没有默认添加依赖的话,需要手动添加以下依赖:
- dependencies {
- androidTestCompile 'com.android.support.test:runner:0.4'
- // Set this dependency to use JUnit 4 rules
- androidTestCompile 'com.android.support.test:rules:0.4'
- // Set this dependency to build and run Espresso tests
- androidTestCompile 'com.android.support.test.espresso:espresso-core:2.2.1'
- // Set this dependency to build and run UI Automator tests
- androidTestCompile 'com.android.support:support-annotations:24.2.0'
- }
- android {
- defaultConfig {
- testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
- }
- }
复制代码 第二步:确定要被测试的具有交互效果的页面:
例如注册页面,实现输入用户名和密码,点击注册按钮执行业务。
- @Bind(R.id.et_Username)
- EditText etUsername;
- @Bind(R.id.et_Passrword)
- EditText etPassrword;
- @OnClick(R.id.btn_Register)
- public void onClick() {
- // 执行业务
- }
复制代码第三步:创建测试类和测试方法: 在要被测试的类中点击右键菜单--> Go To --> Test(ctrl+shift+T快 捷键),自动创建相应的测试类和方法,创建到androidTest路径下。 第四步:完善测试类和测试方法: - import static android.support.test.espresso.Espresso.onView;
- import static android.support.test.espresso.action.ViewActions.click;
- import static android.support.test.espresso.action.ViewActions.typeText;
- import static android.support.test.espresso.matcher.ViewMatchers.withId;
- public class RetrofitPostActivityInstrumentedTest {
- @Rule
- public ActivityTestRule<RetrofitPostActivity> activityTestRule = new ActivityTestRule<RetrofitPostActivity>(RetrofitPostActivity.class);
- @Test
- public void onClick() throws Exception {
- onView(withId(R.id.et_Username)).perform(typeText("123456"));// 为id为et_Username的控件输入字符串“123456”
- onView(withId(R.id.et_Passrword)).perform(typeText("123456"));// 为id为et_Passrword的控件输入字符串“123456”
- onView(withId(R.id.btn_Register)).perform(click());// 为id为btn_Register的控件设置点击事件
- Thread.sleep(3000);// 因为注册为网络请求(耗时操作),所以线程休眠以等待结果。
- }
- }
复制代码
|