こんにちは、株式会社Pentagonでエンジニアをしている阿久津です。
Flutterでもテストを自動化したい! と思ったことはありませんか?
Flutterで自動テストを行う方法はいくつかあるのですが、今回はWidgetテストの方法を紹介します。
画面のテストなので、Seleniumなどと似た感じです。
【こんな人に読んで欲しい】
- Flutterの自動テストに興味がある方
【この記事を読むメリット】
- FlutterでWidgetテストを行うイメージが掴めます
この記事を読めば、Widgetテストのやり方をマスターできるので、ぜひご覧ください。
目次
ウィジェットテストを行う際に必要なパッケージ
必要なパッケージは初期状態で入っていると思いますが、以下が最低限必要です。(ユニットテストと同じ)
pubspec.yaml
dev_dependencies:
flutter_test:
sdk: flutter
build_runner: <newest_version>
コード
プロダクトコード
(本題では無いので割愛)
テストコード
@GenerateMocks([TopViewModel])
void main() {
// ViewModelのモック
final viewModel = MockTopViewModel();
testWidgets('ViewModelから取得した項目が画面に表示されること', (WidgetTester tester) async {
// ViewModelから取得する項目をモック設定
when(viewModel.item).thenReturn([Item(id: '001', name: 'apple')]);
// Widgetをテスターに設定
await tester.pumpWidget(ProviderScope(
overrides: [
// ViewModelをモックに切り替える為にProvider設定を上書き
topViewModelNotifierProvider.overrideWithProvider(
Provider((_) => viewModel),
),
],
child: GetMaterialApp(
home: TopPage(),
),
));
// ViewModelから情報の取得が完了するまで待機する
await tester.pumpAndSettle();
// "apple"というテキストが表示されている事を検証
expect(find.text('apple'), findsOneWidget);
});
}
少しコードの意味がわかりづらいかもしれませんが、モック設定とRiverpodのための設定を除けば、以下の手順のみです。
void main() {
testWidgets('ViewModelから取得した項目が画面に表示されること', (WidgetTester tester) async {
// Widgetをテスターに設定
await tester.pumpWidget(GetMaterialApp(
home: TopPage(),
),
));
// "apple"というテキストが表示されている事を検証
expect(find.text('apple'), findsOneWidget);
});
}
Widgetテストを行うまでの流れをまとめると、以下のように非常にシンプルです。
- テスターにテスト対象のWidget(SUT)を渡す
- 表示すべき項目が表示されているか検証
まとめ
WidgetテストはWidgetを起動して、表示内容を検証するだけ。
Widgetテストを実行するまでの注意点として、以下の2つをおさえておきましょう。
- テストセットアップが大変になることがある(関連するProviderのモック設定等)
- CSSセレクターのように、アサーション対象の項目を簡単に特定できない
メンテナンスが間に合わなくなると、あっという間に回帰テストの存在意義が失われる現場がある中で、この2点は中々に苦しいものだなと感じました。
モックやfindの部分にはちゃんと触れなかったので、またまとめようかと思います。
今後も品質の安定化の為にできる事を模索していきます。