Android自动化测试之路——Service

对Service进行测试,首先你得熟悉service的两种生命周期,即onCreate——onBind 和onCreate——onStartCommand。

启动服务的方式分别是startService()和bindService()。

创建测试类需要继承ServiceTestCase这个类,默认初始化会设定mock Context和mock Application,已达到与被测对象的独立,实现单元测试的目的。

需要说明下的是ServiceTestCase.bindService()和Service.bindService()方法的不同之处在于:1、入参不一样,第一个只需要intent就行了。  2、返回值不一样 第一个返回IBinder对象

与ActivityInstrumentationTestcase一样,需要复写setUp与tearDown以达到初始化与事后处理的目的,若要在里面实现,需在super后编写实现语句。

默认情况下,ServiceTestCase会运行testAndroidTestCaseSetupProperly()方法来确定测试类正确地搭建好了Context。

那么对于Service进行测试到底要测什么呢?在SDK中所提到的主要有以下几个方面:

1.调用Context.startService()或者Context.bindService()后要确定onCreate()方法被正确地调用;同样,当调用Context.stopService(), Context.unbindService(), stopSelf()或者 stopSelfResult()等方法时要确定onDestroy()方法被正确地调用。
2.服务能够正确地处理Context.startService()的多次调用,只有第一次调用才会触发Service.onCreate()方法,但是每次都会调用Service.onStartCommand()方法。还要注意的是startService()不会嵌套调用,因此对Context.stopService()或者 Service.stopSelf() ( stopSelf(int)不再此列)的一次调用就应该能够终止服务。
3.测试服务在实现上的逻辑正确性。

下面就以一个示例代码来看:

public class IRemoteServiceTest extends ServiceTestCase {

    private final static String IRemoteService = "com.noah.remote.service.IRemoteService";
    private static Class iRemote;
    private IRemoteCommand iCommand;
    
    static{
        try {
            iRemote = Class.forName(IRemoteService);
        } catch (ClassNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    
    public IRemoteServiceTest() {
        super(iRemote);
        // TODO Auto-generated constructor stub
    }

    @Override
    protected void setUp() throws Exception {
        super.setUp();
    }

    @Override
    protected void tearDown() throws Exception {
        super.tearDown();
    }
    
    
    public void testOnCreate(){
        Intent in = new Intent();
        in.setClassName(getContext(), IRemoteService);
        
        IBinder binder = bindService(in);
        if(binder.isBinderAlive()){
            iCommand = IRemoteCommand.Stub.asInterface(binder);
        }
    }
    
    
}

若没有被测代码的源代码,但知道被测service的包名,可以用上面的方式构造一个测试类。

在testOnCreate测试方法中绑定这个service,最后拿到的iCommand对象就是我们的被测对象,接下来就可以对这个对象里面的api进行调用并检查是否运行正确。

startService的方式一样,在启动service后,通过getService()方法调用拿到这个service对象,再进行接下来的测试。

posted @ 2014-11-27 17:45  xiao.kkp  阅读(680)  评论(0编辑  收藏  举报