这里须要把Instrumentation类的视频的上、中、下三集一块儿看,把内容总结一下。。。java
视频地址:android
http://study.163.com/course/courseLearn.htm?courseId=712011#/learn/video?lessonId=881433&courseId=712011面试
http://study.163.com/course/courseLearn.htm?courseId=712011#/learn/video?lessonId=878104&courseId=712011正则表达式
http://study.163.com/course/courseLearn.htm?courseId=712011#/learn/video?lessonId=877119&courseId=712011windows
1、引子(面试题)微信
如何在一个app中作event事件?(touch、滑动和按键等)app
答:框架
一、Device.touch(x,y) //monkeyrunner的方法less
二、solo.clickOnView(String id) //Robotium的方法eclipse
三、driver.findElement(By.name("xxx")).click() //Selenium的方法
四、不采用任何开源或非开源的测试框架(monkeyrunner、robotium、appium、selenium、Androiddriver、uiautomator等都不准用)
此时就须要用google提供的基础测试类Instrumentation
注:Robotium就是基于Instrumentation的二次封装,因此理解Robotium的原理还在于Instrumentation
问题:
一、Robotium的运行原理是什么?
答:Robotium是经过对instrumentation的注入事件(sendKeyDownUpSync、sendPointerSync)的封装、以及经过调用instrumentation的runOnMainSync、runOnUiThread等来完成对控件的操做,让用户能够直接调用一个solo.clickOnText等方法,就可以完成操做,而不用本身去写一堆找到控件,而后再点击触发等方法
二、为何Robotium的testcase须要一个setup方法和一个teardown方法
答:分析Instrumentation的原理,InstrumentationTestCase或者InstrumentationTestCase2都须要有一个setUp和tearDown方法,一个用来进行前期准备,获取全部须要的东西,好比说主Activity,好比说获取到全部的控件ID,而后在下面的test方法中才能用这些ID进行相应测试的操做。
根本缘由是由于:setup和teardown是junit必须执行的生命周期函数,全部的Test类都是基于这个作的,因此必需要有这两个方法才行。
三、Robotium的AndroidManifest.xml中配置的节点<Instrumentation>又是什么含义?不导入jnuit-report.jar包的时候,Instrumentation中配置的 android:name="android.test.InstrumentationTestRunner",若是用了这个jnuit-report.jar包以后,就须要修改Instrumenation的节点配置为android:name="com.zutubi.android.junitreport.JUnitReportTestRunner"?
答:按照理解,这个配置的Instrumentation节点的anroid:name指的就是用以启动的TestRuner的名,只有配置了这个以后,测试程序才可以启动起来,这个启动过程应该又回到上一篇Robotium里面记录的那样了,运行一个测试程序,会先运行一个系统工具Activity Manager,而后Activity Manager经过Instrumentation框架来启动和控制TestRunner,可是你须要给Activity Manager提供TestRuner的名,就是指的这里配置的android:name
Instrumentation的这个AndroidManifest.xml的标签中的配置(该标签位于Application标签的外面):
<instrumentation
android:name="android.test.InstrumentationTestRunner"
android:targetPackage="xxx.xxx.xxx"/>
android:name指定TestRunner,这就是导入了一个命名空间,一个包名,就是android.test.Instrumentation,这个标签一导入,系统就知道你要应用Instrumentation测试框架了
2、万能的Instrumentation类
First:what is Instrumentation?
答:
Instrumentation是执行Application Instrumentation代码的基类,当应用程序运行的时候Instrumentation处于开启(备注:须要了解应用程序运行以前就已经开启哪些东西?),Instrumentation将在任何应用程序运行前初始化,能够经过它监测系统与应用程序之间的交互。
Second:how to implement the Instrumentation?
答:
Instrumentation的实现是经过在AndroidManifext.xml中加一个<Instrumentation>的标签,具体以下:
Third:how to understand the Instrumentation?
答:
Instrumentaion比较像Windows里面的钩子(Hook),在系统和应用程序之间装了一个特殊装置用以进行监听
作自动化测试的时候用到的类是:InstrumetationTestCase类,(Instrumentation是一个测试基类,InstrumentationTestCase是一个测试框架,那么具体Android自己官方提供的多个测试类之间是个啥样的关系呢??
Robotium是对InsttumentationTestCase2的二次封装,这个InstrumentationTestCase其实跟InstrumenatationTestCase2已经有点差异了,InstrumentationTestCase2已经对InstrumentationTestCase作了一个简化处理,好比增长了public方法getActivity(),就能够直接得到当前被测对象的Activity,而不用像在InstrumentationTestCase里面那样,经过getInstrumentation().startActivitySync(intent)方法来获取Activity了。。。
3、实现touch、keyEvent等事件
一、准备安卓的环境(java环境、eclipse、环境变量配置)
二、写一个安卓的app(被测app)
三、开始写测试框架代码
测试必需要保证测试app和被测程序签名一致,既然是本身写的,那么确定是用debug签名比较方便,这样被测代码和测试代码在不一样的包中,可是在同一个工程里,签名确定一致;若是没有源码的话,也须要签名一致,就须要进行重签名了。
具体的代码就是,建一个包名来建立app,而后一个待测程序创建一个包,一个测试程序创建一个包。
Instrumentation对安卓操做系统的版本没有要求,这个是特别好的
demo1:实现对一个button的点击操做
具体代码内容详解:
一、Intent.setClassName(packageName, MainActivity.class.getName)方法
二、startActivitySync(Intent intent)方法:
Intent是一个意图,在安卓开发里面能够经过Intent.setClass,以后用this.startActivity(Intent intent)就能够跳转到你想要去的那个Activity
startActivitySync的这个方法,在启动了这个APP以后,将这个Intent传递给他,而后它就可以给你返回当前的MainActivity
三、Junit4的assertEquals和robotium的searchText
assertEquals方法须要输入expected string和actual string,而后二者进行比较,返回是否相等,用此来作校验;
serchText方法是将全部的TextView所有找到,放到一个集合中,而后去作对比(经过正则表达式)
Instrumentation是怎么跟robotium对应上的???其实直接看InstrumenetationTestCase2,会更加清晰,因此Robotium是须要extends InstrumentationTestCase2的。其实东西都是同样的,就是你要知道包名,而后知道类名,而后经过这个类名去findViewById来获取到你须要的控件ID,以后调用方法对这个控件进行操做(包括sendPointSync等注入事件、runOnMainSync、runOnUiThread方法等来操做控件),以后根据当前控件的状态,与你预期想要的状态作一个对比,就能够知道是否达到了想到的结果。另外,还须要在AndroidManifest.xml中进行<Instrumentation>节点的配置,用以告诉ActivityManager要用什么TestRunner。
demo2和demo3:
instrumentation.sendKeyDownUPSync详解
sendPointerSync方法(可以产生手指操做控件的响应效果)
MotionEvent
一个Error的处理:java.lang.SecurityException:Injecting to another application requires INJECT_EVENT permission
解决方案:直接在AndroidManifest.xml中进行配置,若是出现相似的这种涉及到perssion的问题,也是相似,直接在Manifest.xml中配置便可,应该都能解决。
4、Instrumentation类API基础
一、callActivityOnCreate(Activity activity, Bundle icicle)
说明:Perform calling of an activity's onCreate(Bundle) method
一个activity的onCreate(Bundle savedInstanceState)方法,这个Bundle对象是用来存储Activity的状态,好比Activity被stop但不是destory时,这个对象就用上了,以后再resume回来时,就要用到这个Bundle对象来恢复以前的状态,比较像递归里面的堆栈信息的存储
二、getContext()
说明:获得上下文的一个引用,就能够进一步获得view、windows、控件
三、startActivitySync()
说明:以同步方式start一个Activity,即这是一个阻塞性的方法,必需要start起这个Activity以后,返回告终果,而后程序才能继续往下走
所谓同步:就是发出一个请求后什么事都不作,一直等待请求返回后才会继续作事;
所谓异步:就是发出请求后继续去作其余事,这个请求处理完成后会通知你,这时候就能够处理这个回应了。
四、sendKeyDownUpSync(int key)
downup的点击事件,经过对一些系统按键的操做来完成。好比KeyEvent.KEYCODE_MENU、KeyEvent.KEYCODE_HOME等
五、sendPointerSync(MotionEvent event)
发送一个具体的点触事件,MotionEvent有obtain方法,能够针对具体的Down或者UP事件进行操做,在某一个特定的坐标位置,经过这个可以看到测试case时,程序上会出现被点击选中的阴影效果,而直接调用button.performClick()方法是没有这个效果的。
金阳光测试 |
新浪微博:金阳光woody |
网站地址 |
一、百度搜:金阳光测试 二、官网:www.goldensunshine.cc |
微信公众号 |
|