VOICE

iOSアプリケーションへのUITest導入 【ZYYX Tech Blog】

こんにちは、第二事業部でエンジニアをしている渡邊です。普段はiOSアプリの開発プロジェクトを担当しています。今回はiOSアプリケーションのテストについてお話ししていきます。

はじめに

これまで私はいくつかのiOSアプリ開発、保守案件を担当しましたが、テストの導⼊にはほぼ関わったことがありませんでした。しかし、先日担当したWebアプリケーションの保守案件で、少しですがテストコードに触れる機会がありました。そのときに感じたメリットを以下にご紹介します。

  • 結合テスト時に報告される不具合が⽐較的少ない
  • 安⼼して改修、リファクタリングができる
  • コードが疎結合になる

普段関わることの多いiOSアプリ開発でも、このような効果が⾒込めるのでは?と思いました。そこで、今回は実際のアプリにUITestを導⼊し、通常の実装に加えてどの程度の⼿間がかかりそうか、また実案件に導⼊できそうかを検討してみます。

UITest導入対象アプリについて

概要

SwiftUIを使用してiOSアプリにUITestを導入した方法について紹介します。

対象者

iOSアプリのUITest導⼊に興味のある⽅

実行環境

  • Xcode 15.1
  • Swift 5.8.1
  • フレームワーク SwiftUI

今回使⽤するアプリは、飲⾷店検索アプリです。飲⾷店のデータはHOTPEPPERグルメAPIを利⽤しています。(画像では店名等が表示されないように処理しています)UIは以下の画像のようになっています。各画⾯の仕様は、後のテストコードでわかる内容になっているため省略します。

飲⾷店検索アプリ

GUIアーキテクチャは MVVM を採用しています。

UITestの導入

ここからはUITestのコード実装について、画⾯ごとに説明していきます。

UITestのコード実装

主に画⾯のテストでは、初期状態とタップイベントの検証を⾏いました。 全体的なテストケースのコードの流れは、以下のようになっています。

  1. アプリ起動
  2. 検証対象画⾯の要素取得
  3. タップイベント等があった時にイベント発⽕
  4. 画⾯要素の状態を検証

また、テストコードファイル以外に本体コードへの修正が必要です。「2. 検証対象画⾯の要素取得」は画⾯要素のIDを指定して取得しているので、本体コードであらかじめ指定しておく必要があります。実際には以下の通りです。

UITestのコード実装_検証対象画⾯の要素取得

IDはString型の値を指定すれば良いのですが、あつかいやすく Enum として画⾯ごとに定義しています。

UITestのコード実装_Enum

検索結果画面

検索結果画面のコード

基本的には検索画⾯と同様です。この画⾯の場合、初期表⽰として検索結果有り・無しの2パターンの検証を⾏う必要があります。そのため launchArguments を利⽤して、以下のようにMockを差し替えています。

検索結果画面のコード_launchArgumentsの利⽤

⾃前で定義したViewを使っているため、画⾯要素の取得に関して注意点があります。⾃前で定義したViewでは、 otherElements を指定すると共に、id指定時に accessibilityElements() を指定する必要があります。

検索結果画面のコード_accessibilityElements()

飲⾷店詳細画⾯

飲⾷店詳細画⾯のコード

こちらもこれまでと同様です。この画⾯では、Listで共通化したセルを表⽰していますが、セルには同じidが指定されています。そのため⼀旦それぞれのセルを取得し、さらにidを指定してセル内のテキストなどを取得しています。

さいごに

実際にiOSアプリへのUITest導⼊をやってみて、ハードルはそこまで高くないと感じました。 難点をあげると、本体コードにテストコードのための実装が⼊ってしまうことです。UITestを導⼊する上で、これは避けられない点かもしれません。

IDの指定⽅法が統⼀されていないと、かなりあつかいにくいコードになる可能性があります。事前にルールを決めて、チーム内で共有しておくべきでしょう。また、画⾯のパターンを複数検証するためには設計⾯でも考慮が必要です。MVVMなどを利⽤して、画⾯とプレゼンテーションロジック、状態管理を切り離す等のルールを統⼀しておくことで、テスタビリティだけでなく保守性も向上します。

UITest導⼊をまとめると、個⼈的には以下の2つがポイントになると思いました。

  • ID 指定ルールを明らかにする
  • 画⾯データを切り替えやすい状態にする

上記の2つを意識すれば、実案件への導⼊も難しくないと感じます。実案件ではより複雑な画⾯になり、課題も増えると思いますので、機会があればiOSアプリ開発の現場で試してみたいです。