这篇文章将继续上一篇的问题,实现我们的iunit框架与Guice框架的整合,这个模块主要用于那些用Guice来做DI容器的项目做测试用的,包括guice框架的启动与在测试类中自动注入@Inject标注的字段
1. 目标测试类的庐山真面目
packagecom.crazycoder2010.guice.sample; importorg.junit.Test; importcom.crazycoder2010.iunit.AbstractIUnitTestCase; importcom.crazycoder2010.iunit.GuiceStratupListener; importcom.crazycoder2010.iunit.annotation.GuiceModuleConfiguration; importcom.crazycoder2010.iunit.annotation.IUnitTestExecuteListeners; importcom.google.inject.Inject; @GuiceModuleConfiguration(classes={MyModule.class})//标注一下当前测试用例需要加载哪几个模块 @IUnitTestExecuteListeners(value={GuiceStratupListener.class})//启动Guice监听器,这样我们@GuiceModuleConfiguraition标注的内容才能生效:) publicclassClientTestextendsAbstractIUnitTestCase{ @Inject//要用到的服务 privateClientclient; @Test publicvoidtestClientGo(){ client.go();//直接调用就可以了,框架已经帮你注入了client的值,因此不会有空指针出现了 } } |
我们看到这个TestCase继承了我们第3节里介绍到的统一父类,然后注册了自己的IUnitTestExecuteListerner=GuiceStarupListener,然后还有个注解@GuiceModuleConfiguration,表示我们这个测试类要加载那几个Module,测试类中用到那几个服务,只要用@Inject标注一下实例变量即可--verysimple
2. GuiceStartupListener类
packagecom.crazycoder2010.iunit; importjava.util.ArrayList; importjava.util.List; importcom.crazycoder2010.iunit.annotation.GuiceModuleConfiguration; importcom.google.inject.Guice; importcom.google.inject.Injector; importcom.google.inject.Module; /** *用来启动Guice容器的Listener * *@authorKevin * */ publicclassGuiceStratupListenerextendsIUnitTestExecuteListenerAdapter{ @Override publicvoidprepareTestInstance(TestContexttestContext)throwsException{ //读取Guicemodules Class<?>c=testContext.getTestInstance().getClass(); List<Class<?extendsModule>>moduels=newArrayList<Class<?extendsModule>>(); while(c!=null){ GuiceModuleConfigurationconfiguration=testContext.getTestInstance() .getClass().getAnnotation(GuiceModuleConfiguration.class); if(configuration!=null){ for(Class<?extendsModule>cl:configuration.classes()){ if(!moduels.contains(cl)){//去重 moduels.add(cl); } } } c=c.getSuperclass(); } Module[]modulesArray=newModule[moduels.size()]; for(inti=0;i<moduels.size();i++){ modulesArray[i]=moduels.get(i).newInstance(); } //初始化injector Injectorinjector=Guice.createInjector(modulesArray); injector.injectMembers(testContext.getTestInstance());//这句是核心,让injector为当前testcase对象注入属性值,这也是为什么@Inject标注了字段名后就能直接用了的玄机所在 } } |
相关链接:
一个通用的单元测试框架的思考和设计04-实现篇-测试数据自动插入删除