<!--defaultCSS-->
几个基本概念:
1、什么是
Instrumentation?
Instrumentation,类似于Activity,是安卓的一个专属概念;我们把它看做一个专门用于监控其他类的工具类。它具有启动其他类的能力
2、什么是Emma?
emma是一个测试代码覆盖率的工具,可以在执行测试后获取测试代码的覆盖率。它的基本原理是通过对编译后的class文件进行插装,在执行测试的同时,向内存中写入覆盖率信息,等测试执行完后,从内存中获取覆盖率信息并生成报表。
执行的步骤:
1、实现功能代码
2、编写测试插装代码
我们会实现从一个继承自Instrumentation的类
EmmaInstrumentation,来管理我们要测试的程序。它接管了我们程序的启动和停止,并且在程序推出的时候,把emma生成在内存中的覆盖率信息输出到文件中。
基本代码框架如下:
//从Instrumentation派生,并且实现FinishListener接口,该接口用于监听真正Activity的停止,输出覆盖率文件
public class EmmaInstrumentation extends Instrumentation implements FinishListener
//启动的时候,创建的是包装后的activity,而不是原有的activity
public void onCreate(Bundle arguments) {
super.onCreate(arguments);
mIntent = new Intent(getTargetContext(), InstrumentedActivity.class);
mIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
start();
}
//启动程序
public void onStart() {
super.onStart();
Looper.prepare();
InstrumentedActivity activity = (InstrumentedActivity) startActivitySync(mIntent);
activity.setFinishListener(this);
}
//在结束的时候,生成报告
@Override
public void onActivityFinished() {
generateCoverageReport();
finish(Activity.RESULT_OK, mResults);
}
//报告的生成
Class<?> emmaRTClass = Class.forName("com.vladium.emma.rt.RT");
Method dumpCoverageMethod = emmaRTClass.getMethod(
"dumpCoverageData", coverageFile.getClass(), boolean.class,
boolean.class);
dumpCoverageMethod.invoke(null, coverageFile, false, false);
//包装测试类的实现,目的是不修改程序的功能代码添加监听程序结束的功能
public static class InstrumentedActivity extends
TemperatureConverterActivity {
private FinishListener mListener;
public void setFinishListener(FinishListener listener) {
mListener = listener;
}
@Override
public void finish() {
if (LOGD)
Log.d(TAG + ".InstrumentedActivity", "finish()");
super.finish();
if (mListener != null) {
mListener.onActivityFinished();
}
}
}
3、配置工程
插装的代码编写完了之后,我们要AndroidManifest.xml文件中配置上相应的数据
//允许写文件
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<instrumentation android:name="com.example.instrumentation.EmmaInstrumentation" android:targetPackage="com.example.i2at.tc"></instrumentation> (补充:这里的target只需要填写和AndroidMainifest.xml中定义的package一样就可以了;和具体代码的package没有关系,工程下代码的的覆盖率都会被统计出来)
<activity android:name="com.example.instrumentation.EmmaInstrumentation$InstrumentedActivity"></activity>
4、打包、安装
ant clean、ant instrument、 ant installi通过这三个命令完成打包和安装的过程
5、运行、测试
D:\development\adt\sdk\platform-tools>
adb.exe shell am instrument -e coverage tr
ue -w com.example.i2at.tc/com.example.instrumentation.EmmaInstrumentation
INSTRUMENTATION_CODE: -1
执行上述命令运行程序,程序启动后,按照操作测试程序,测试完后,程序正常退出,此时,会生成覆盖率的文件在/mnt/sdcard下
执行 adb.exe pull /mnt/sdcard/coverage.ec获取文件到本地
6、生成覆盖率文件
java -cp D:\development\adt\sdk\tools\lib\emma.jar emma report -r html -in coverage.em,coverage.ec -Dreport.html.out.file=coverage.html -Dreport.metrics=class:80
执行上述命令生成覆盖率文件,其中coverage.ec是我们执行完测试后生成的文件,而coverage.em是在插装时生成的元数据文件。报告的输出为coverage.html,我们可以从该文件中看出测试代码的覆盖率
问题:为什么在输出覆盖率文件的时候会提示没有权限?但是在AndroidManifest.xml文件中已经配置了写权限
回答:如果我们使用的是模拟器的话,则必须要配置模拟的SD Card的size参数,否则,就会报没有权限的错误。