我试图为支持架构组件生命周期事件的功能添加单元测试。为了支持生命周期事件,我为函数添加了@OnLifecycleEvent
批注,该事件发生时我想做一些事情。
一切都按预期工作,但我想为该功能创建一个单元测试,以在发生预期事件时检查我的功能是否运行。
public class CarServiceProvider implements LifecycleObserver {
public void bindToLifeCycle(LifecycleOwner lifecycleOwner) {
lifecycleOwner.getLifecycle().addObserver(this);
}
@OnLifecycleEvent(Lifecycle.Event.ON_STOP)
public void onClear() {
Log.i("CarServiceProvider", "onClear called");
}
}
我试图模拟LifecycleOwner并创建新的LifecycleRegistery来更改生命周期观察者的状态,但我没有这样做。
如何更改状态更改后调用的onClear()
函数?
尽管我不是一个忠实的粉丝,但我还是会选择Robolectric来利用ActivityController来实现这一目标。
鉴于Observer pattern的“可观测值”应用于Android Lifecycle工作流是“活动”,“片段”……应用程序上下文是必须的,我们需要以某种方式将其引入我们的测试场景。
我通过这样做达到了预期的结果
build.gradle
testCompile "org.robolectric:robolectric:3.5.1"
CarServiceProviderTest.java
@RunWith(RobolectricTestRunner.class)
@Config(constants = BuildConfig.class)
public class CarServiceProviderTest {
@Test
public void shouldFireOnClear(){
//Grab the Activity controller
ActivityController controller = Robolectric.buildActivity(JustTestActivity.class).create().start();
AppCompatActivity activity = (AppCompatActivity) controller.get();
//Instanciate our Observer
CarServiceProvider carServiceProvider = new CarServiceProvider();
carServiceProvider.bindToLifeCycle(activity);
//Fire the expected event
controller.stop();
//Assert
Assert.assertTrue(carServiceProvider.wasFired);
}
}
CarServiceProvider.java
public class CarServiceProvider implements LifecycleObserver {
public boolean wasFired;
public void bindToLifeCycle(LifecycleOwner lifecycleOwner) {
lifecycleOwner.getLifecycle().addObserver(this);
}
@OnLifecycleEvent(Lifecycle.Event.ON_STOP)
public void onClear() {
wasFired = true;
}
}
您应该可以使用LifecycleRegistry
您的测试将执行以下操作:
@Test
public void testSomething() {
LifecycleRegistry lifecycle = new LifecycleRegistry(mock(LifecycleOwner.class));
// Instantiate your class to test
CarServiceProvider carServiceProvider = new CarServiceProvider();
carServiceProvider.bindToLifeCycle(lifecycle);
// Set lifecycle state
lifecycle.handleLifecycleEvent(Lifecycle.Event.ON_STOP)
// Verify that the ON_STOP event was handled, with an assert or similar check
...
}
如果您正在测试Lifecycle.Event.ON_DESTROY,那么您可能需要在此之前调用handleLifecycleEvent(Lifecycle.Event.ON_CREATE)。
[如果您要使用真实的单元测试(而不是AndroidTest)进行测试,最好的选择是使用Robolectric,它模拟Android框架,而Robolectric 4.0即将问世。但是,您正在尝试测试与Android Framework的实际交互,因此这是一个更适合真正的集成测试套件和AndroidTest的任务。您可以对其进行单元测试,但是最确定的测试方法是在设备上实际调用生命周期事件(Espresso会执行的操作)并验证它是否被调用。
只要您正确地模拟了生命周期所有者,就可以在不使用Roboletric的情况下使用单元测试进行测试。
val lifecycleOwner: LifecycleOwner = Mockito.mock(LifecycleOwner::class.java)
val lifecycle = LifecycleRegistry(Mockito.mock(LifecycleOwner::class.java))
lifecycle.markState(Lifecycle.State.RESUMED)
Mockito.`when`(lifecycleOwner.lifecycle).thenReturn(lifecycle)
[观察变量时使用此lifecycleOwner,可以使用Mockito.verify来查看是否已调用回调