(转载)http://my.oschina.net/aibenben/blog/383068
一直想系统专业的了解测试这一块,但是工作过的公司都没有,都是程序员做完了就扔给测试MM直接测,MM也就只是按照需求文档点,也就没有了所谓的单元测试,功能测试。
这里写一个简单的单元测试 ,体验下,我相信好多朋友跟我一样,知道单元测试这个名字,但是真要做,不知怎么开始,所以跟大家分享下
一个登录界面,测试点击登录按钮后是否能正常跳转到首页(是不是觉得有点无聊....) 初次体验下android 的 单元测试
准确的说应该是activity的单元测试
先看目录结构. 来给LoginActivity写一个单元测试,新建一个类,我这叫LoginPresenterTest,然后继承ActivityUnitTestCase
![](https://i-blog.csdnimg.cn/blog_migrate/9f73772d2205d79b2a5e4a1ec1f9dad9.png)
2当我们继承ActivityUnitTestCase后,要重写的方法不能少setUp(),还有一个很重要的地方,空的构造方法,然后 super(LoginActivity.class); 这里如果不这样弄,测试运行就会报错
![](http://static.oschina.net/uploads/space/2015/0305/145543_x7SV_251064.png)
3.由于继承ActiviUnitTestCase的Activity不会被Android自动启动的。要单独启动Activity,你需要显式的调用startActivity()方法,并传递一个Intent来启动你的目标Activity
所以先全局的定义一个Intent 然后在setUp()这个初始化方法里面
mLoginIntent = new Intent(getInstrumentation().getTargetContext(), LoginActivity.class);这个时候我们先不急着调startActivity();
4,现在就可以开始写测试方法了,我想测试一下Button上的文字是不是我想要的。我们写一个test开头的方法名testLoginButton_labelText(),上面加上注解@MediumTest
(PS:只需要几毫秒的时间的应该被标记为@SmallTest,长时间运行的测试(100毫秒或更多)通常被标记为@MediumTest,@LargeTest,主要取决于测试访问资源在网络上或在本地系统。 )
所以我们这里@MediumTest
来,继续,大家看这个方法里面第一句,就是启动activity。
startActivity(mLoginIntent, null, null);
然后就是通过findViewByid找到Button.
final Button loginButton = (Button) getActivity().findViewById(R.id.btn_login);
然后就是从String获取到你觉得Button上的labe
final String buttontext = getActivity().getString(R.string.btn_login);
最后对比这个值
assertEquals("Unexpected button ladel text", buttontext, loginButton.getText());
准备就绪,我们来运行。
鼠标定位到这个方法名上,点击右键-->Run()-->选择小机器人
![](http://static.oschina.net/uploads/space/2015/0305/151339_bJEX_251064.png)
然后就跟正常run一样,等待,最后成功就会出现passed
因为String里面<string name="btn_login">登录</string> 我的Button
<Button
android:id="@+id/btn_login"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_below="@+id/et_password"
android:layout_margin="10dp"
android:text="@string/btn_login"/>
也是引用的这个btn_login。所以肯定对比是成功的
继续,假如不一样呢,请看,我换一个值去对比 <string name="title_activity_login">LoginActivity</string>.这肯定不一样
![](http://static.oschina.net/uploads/space/2015/0305/151827_6DUC_251064.png)
一样的,我们在方法名testLiginButton_labelText()上右键,直接Run(因为之前已经run过一次,所以这一次不会再有小机器人选)
然后等待结果
![](https://i-blog.csdnimg.cn/blog_migrate/6da526b158f03add9885a57d4e559980.png)
是不是觉得比成功要有成就感,因为通过测试发现问题了。。。
Unexpected button ladel text expected:<LoginActivity> but was:<登录>
好吧,我们再来玩一个。
现在我想测试点击登录按钮后,正常跳转到另外一个Activity
一样的写一个方法,方法名test开头testLoginActivityMoveToIndex();注解别忘记加了
![](http://static.oschina.net/uploads/space/2015/0305/152908_ctSm_251064.png)
方法里面第一句还是一样的,启动activity
startActivity(mLoginIntent, null, null);然后找到Button
final Button loginButton = (Button) getActivity().findViewById(R.id.btn_login);再然后 我们可以用performClick()来模拟点击事件
loginButton.performClick();
得到跳转后的Intent
final Intent loginIntent = getStartedActivityIntent();
去判断是否为空,如果为空就说明跳转失败
assertNotNull("Intent was null", loginIntent);
这一句是判断你在跳转后有没调finish()
assertTrue(isFinishCalled());
再回头看看LoginActivity里面Button监听器里面的代码
大家可以先把finish()这个方法注释掉,体验下报错
然后回来测试的方法右键,一样的运行,等待结果
如果注掉finish().就会测试出错误
.我们直接点击报错的地方,会定位到哪测试报错
很明显就是因为我们在跳转后没有finish(),但是测试方法里面我们有去测试是否有调 assertTrue(isFinishCalled());
,如果加上在LoginActivity里面加上finish(),那就会成功没问题了.
好了,这篇文章就是体验下所谓的Android单元测试。我会继续学习下去,便跟大家一起分享。之前学习MVP模式的时候,都说MVP模式的一个优点就是方便单元测试,所以我直接在MVPDemo 这个项目上写的例子,可是我现在还没有体会到这个优点,我现在就是想像web里面的ut测试一样,写一个方法,然后直接运行这个方法得到结果,这样我觉得MVP方便单元测试这个优点就真的突显极致了。 我也是一直在摸索中。希望大家能多多指点。