LoginSignup
40
35

More than 5 years have passed since last update.

(Android) 同期が必要なテストを書く

Posted at

IdlingResourceを使ったUIテスト

Espressoを使って,このようなテストを書きました.

  1. リスト表示用のデータをサーバからとってくる
  2. データをリストにセットする
  3. リストをクリックする
  4. 遷移先の詳細画面に,正しい情報が送れたか確認

このテストでは,
「リストにデータがセットされたのを確認してから,クリック」
という流れを書かなければいけません.

Espressoでは,テストするアクションのタイミングをコントロールできるよう,
IdingResourceというものが用意してあります.

今回はその基本的な使い方について話します.

IdingResrouceとは

IdlingResrouceとは,android.support.test.espressoに含まれるインターフェースで,
以下3つの抽象メソッドが定義されています.

  1. getName () : logなどで使うためのリソースの名前の定義
  2. isIdleNow () : テストするアクションをいつまで待たせるかの定義
  3. registerIdleTransitionCallback() : コールバックオブジェクトの受け取り

「ある条件を満たしてから,テストアクションを行う」ことをEspressoに指示するためには,
IdlingResourceを実装したクラスを作成して,Espressoに登録する という手順を踏みます.

IdlingResrouceの作成

今回は,「リストにデータがセットされた」という条件を次のように定義します.

public boolean isItemLoaded(RecyclerView list) {
    return list.getAdapter()!=null && list.getAdapter().getItemCount() != 0;
}

上の条件をEspressoに伝えるためのIdlingResourceはこうなります.

LoadingIdlingResource
private class LoadingIdlingResource implements IdlingResource {

    private ResourceCallback resourceCallback;
    private RecyclerView recyclerView;

    private LoadingIdlingResource(RecyclerView recyclerView) {
        this.recyclerView = recyclerView;
    }

    @Override
    public String getName() {
        return LoadingIdlingResource.class.getSimpleName();
    }

    @Override
    public boolean isIdleNow() {
        boolean idle = isItemLoaded(recyclerView);
        if (idle && resourceCallback != null) {
            resourceCallback.onTransitionToIdle();
        }
        return idle;
    }

    @Override
    public void registerIdleTransitionCallback(ResourceCallback resourceCallback) {
        this.resourceCallback = resourceCallback;
    }

    private boolean isItemLoaded(RecyclerView list) {
        return list.getAdapter()!=null && list.getAdapter().getItemCount() != 0;
    }
}

同期のロジックを定義するisIdleNow()メソッドの定義が主な作業になります.
Espressoは,LoadingIdlingResource.isIdleNow()を呼んでtrueが返ってきたら,
次のテストアクションの実行に移ります.

IdlingResourceを使ったテスト

作成したLoadingIdlingResourceを使って,
「リストにデータがセットされたのを確認してから,クリック」
という流れを含むテストはこうなります.

LoadingIdlingResrouceTest.java
public void testRecyclerView_click() {
    // Set up an ActivityMonitor
    Instrumentation.ActivityMonitor receiverActivityMonitor =
            getInstrumentation().addMonitor(ImageDetailActivity.class.getName(),null, false);

    // wait until list item is loaded
    IdlingResource idlingResource = new LoadingIdlingResource(mRecyclerView);
    Espresso.registerIdlingResources(idlingResource);

    // start DetailActivity by clicking RecyclerView item.
    Espresso.onView(ViewMatchers.withId(android.R.id.list)).perform(
            RecyclerViewActions.actionOnItemAtPosition(0, ViewActions.click()));

    // unregister idling resources
    Espresso.unregisterIdlingResources(idlingResource);

    // Remove the ActivityMonitor
    getInstrumentation().removeMonitor(receiverActivityMonitor);

    // assertion
    Activity activity = receiverActivityMonitor.waitForActivityWithTimeout(1000);
    Intent intent = activity.getIntent();
    String json = intent.getStringExtra(ImageDetailActivity.EXTRA_CONTENT);
    assertEquals(getExpected(), json);
}

終わりに

このブログを参考に実装しました.分かりやすいです.
Square Island: Espresso: Custom Idling Resource

参考URL

EspressoSamples - android-test-kit - Advanced Espresso Samples
Square Island: Espresso: Custom Idling Resource

40
35
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
40
35