7

私は始めたばかりjunitで、最初に遭遇した問題は、フラグメントをどのようにテストすればよいですか?

テスト中のアクティビティには、メイン レイアウトである 1 つのフラグメントがあります。

@Override
protected void setUp() throws Exception {
    super.setUp();
    Intent intent = new Intent(getInstrumentation().getTargetContext(),
            ActivityWelcome.class);
    startActivity(intent, null, null);

    FragmentManager fragmentManager = getActivity().getSupportFragmentManager();
    mFragmentWelcome = (FragmentWelcome) fragmentManager.findFragmentByTag(FragmentWelcome.TAG);
    if (mFragmentWelcome == null) {

        mFragmentWelcome= FragmentWelcome.newInstance();
        fragmentManager
                .beginTransaction()
                .replace(android.R.id.content, mFragmentWelcome, FragmentWelcome.TAG)
                .commit();
    }
}

次に、レイアウトのテストに進みます。

@SmallTest
public void testLayout() {

    ImageButton buttonImage = (ImageButton) getActivity().findViewById(my.package.R.id.button_invites);
    assertNotNull(buttonImage);
    assertEquals("ImageButton Invite has an invalid drawable"
            , getActivity().getResources().getDrawable(my.package.R.drawable.light_social_invite)
            , buttonImage);
}

エラー:

java.lang.NullPointerException
    at my.package.test.ActivityWelcomeUnitTest.testLayout(ActivityWelcomeUnitTest.java:55)
    at java.lang.reflect.Method.invokeNative(Native Method)
    at android.test.InstrumentationTestCase.runMethod(InstrumentationTestCase.java:214)
    at android.test.InstrumentationTestCase.runTest(InstrumentationTestCase.java:199)
    at android.test.AndroidTestRunner.runTest(AndroidTestRunner.java:169)
    at android.test.AndroidTestRunner.runTest(AndroidTestRunner.java:154)
    at android.test.InstrumentationTestRunner.onStart(InstrumentationTestRunner.java:545)
    at android.app.Instrumentation$InstrumentationThread.run(Instrumentation.java:1551)

次の場合に失敗します。

ImageButton buttonImage = (ImageButton) mFragmentWelcome.getView().findViewById(my.package.R.id.button_invites);

フラグメントが null である理由がわかりません。明らかにこの操作を間違って実行しています。誰か教えてください。

4

3 に答える 3

9

実際には、UI スレッドがメイン ビューをフラグメントで構成するまで待つ必要があります。

同じエラーが発生したので、Robotium のソースを調べて、それをどのように処理するかを確認しました。応答は、必要な時間を待機するいくつかのメソッドを使用することです。

フラグメントの場合、アサーションを実行する前にそのようなものを使用できます:

protected Fragment waitForFragment(String tag, int timeout) {
        long endTime = SystemClock.uptimeMillis() + timeout;
        while (SystemClock.uptimeMillis() <= endTime) {

            Fragment fragment = getActivity().getSupportFragmentManager().findFragmentByTag(tag);
            if (fragment != null) {
                return fragment;
            }
        }
        return null;
    }

私は5000ミリ秒のタイムアウトを使用していますが、うまくいくようです。

したがって、コードで置き換える必要があります

mFragmentWelcome = (FragmentWelcome) fragmentManager.findFragmentByTag(FragmentWelcome.TAG);

mFragmentWelcome = (FragmentWelcome) waitForFragment(FragmentWelcome.TAG, 5000);

編集: この応答は、junit が拡張されていることを前提としていますActivityInstrumentationTestCase2<T>

于 2013-07-22T14:18:18.487 に答える
4

テストのために、次の行をメソッドActivityUnitTestCaseに追加する必要がありました。waitForFragment

// haven't really checked if this is necessary
getInstrumentation().waitForIdleSync();
// without this, waitForFragment() failed to find the fragment
getActivity().getFragmentManager().executePendingTransactions();
于 2014-07-08T13:12:31.283 に答える
1

U から com.robotium.solo.Solo を使用できます'com.jayway.android.robotium:robotium-solo:5.2.1'

    mInstrumentation = InstrumentationRegistry.getInstrumentation();
    mSolo = new Solo(mInstrumentation);
    mDevice = UiDevice.getInstance(InstrumentationRegistry.getInstrumentation());
    .....
    mSolo.waitForFragmentById();
于 2016-04-18T14:15:51.057 に答える