单元测试 NPE,当我添加片段自定义转换时

Posted

技术标签:

【中文标题】单元测试 NPE,当我添加片段自定义转换时【英文标题】:Unit tests NPE, when I add fragment custom transitions 【发布时间】:2016-02-08 05:46:37 【问题描述】: 当我添加 自定义转换 时,

OnBackPressed() 测试会引发 NPE。没有自定义过渡很好。为什么?

此 NPE 仅发生在单元测试中,而不是应用程序中。

 class MyActivity 
    @Override
    public void onBackPressed() 
        .......
        super.onBackPressed();
    

    private void putFragment(Fragment fragment) 
            String tag = fragment.getClass().getName();

            FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();

            // TEST FAILED IF I ADD THE FOLLOWING LINE
            transaction.setCustomAnimations(
                    R.anim.slide_in_left_fade_in,
                    R.anim.fade_out_short_anim_time,
                    R.anim.fade_in_short_anim_time,
                    R.anim.slide_out_right_fade_out);

            transaction.replace(R.id.ub__add_profiles_content, fragment, tag);
            transaction.addToBackStack(tag);
            transaction.commit();
    


class MyActivityTest extends RiderRobolectricBase 

    @Test
    public void onBackPressed() 
       putFragment(someFragment);

       mMyActivity.onBackPressed();
    

例外:

java.lang.NullPointerException
    at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1126)
    at android.support.v4.app.FragmentManagerImpl.removeFragment(FragmentManager.java:1304)
    at android.support.v4.app.BackStackRecord.popFromBackStack(BackStackRecord.java:909)
    at android.support.v4.app.FragmentManagerImpl.popBackStackState(FragmentManager.java:1625)
    at android.support.v4.app.FragmentManagerImpl.popBackStackImmediate(FragmentManager.java:561)
    at android.support.v4.app.FragmentActivity.onBackPressed(FragmentActivity.java:166)
    at MyActivity.onBackPressed(MyActivity.java:28)

【问题讨论】:

请发布fade_in_short_anim_time 和slide_out_right_fade_out 的布局,至少是那些xml。 【参考方案1】:

Onbackpress 您正在从 backstack 中反转之前的步骤。第一个是 删除现有的片段。片段与活动分离并且 您没有保留此片段的实例。

java.lang.NullPointerException
    at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1126)
    at android.support.v4.app.FragmentManagerImpl.removeFragment(FragmentManager.java:1304)
    at android.support.v4.app.BackStackRecord.popFromBackStack(BackStackRecord.java:909)
    at android.support.v4.app.FragmentManagerImpl.popBackStackState(FragmentManager.java:1625)
    at android.support.v4.app.FragmentManagerImpl.popBackStackImmediate(FragmentManager.java:561)
    at android.support.v4.app.FragmentActivity.onBackPressed(FragmentActivity.java:166)
    at MyActivity.onBackPressed(MyActivity.java:28)

你的电话putFragment(someFragment)。 所以当你去调用 setCustomAnimations。上一个视图不会保存以在过渡中使用。

// TEST FAILED IF I ADD THE FOLLOWING LINE
transaction.setCustomAnimations(
    R.anim.slide_in_left_fade_in,
    R.anim.fade_out_short_anim_time,
    R.anim.fade_in_short_anim_time,
    R.anim.slide_out_right_fade_out);

您可以在片段的 oncreate 方法中保留该实例:

setRetainInstance(true);

至于在您的应用中工作,我在您的活动的 onBackPressed 事件中看不到代码。

【讨论】:

【参考方案2】:

代码似乎正确。我怀疑由于setCustomAnimations 呼叫,您在使用replace() 后无法呼叫addToBackStack()。因此,为了快速测试,只需删除对 addToBackStack 的调用即可。

通常您可以在 replace() 之后调用 addToBackStack()。我做了很多次。

让我知道你的结果...

【讨论】:

以上是关于单元测试 NPE,当我添加片段自定义转换时的主要内容,如果未能解决你的问题,请参考以下文章

如何在Typescript中对私有方法进行单元测试

在 UI 测试/单元测试期间将自定义字符串写入日志

如何使用属性单元测试自定义视图

如何使用不同的jest.config.js进行单元和组件测试?

带有自定义类型的角度单元测试给出了找不到命名空间

带有或不带有主机应用程序的单元测试自定义 iOS 框架