Calabash-Androidのテスト高速化、GPS、スクショ、データ駆動型テスト:スマホ向け無料システムテスト自動化ツール(7)(2/2 ページ)
本連載では、AndroidおよびiOSアプリ開発における、システムテストを自動化するツールを紹介していきます。今回は、Calabash-Androidによるテスト実行サイクル高速化の実現や、GPSの操作・スクリーンショットの撮影・ステップの実行タイミングの調整などさまざまな「ステップ定義」、「データ駆動型テスト」を実現するための「Scenario Outline」について解説します。
さまざまな「ステップ定義」
連載第5回では、「ステップ定義」の基本を解説し、NumberPickerを操作するためのステップ定義方法を紹介しましたが、ステップ定義には、他にもさまざまなものがあります。
GPSの操作
Calabash-Androidでは、GPSを操作するための「ステップ定義」も用意されています。
効果 | テストシナリオ内での実際の記述方法 | ステップ定義 |
---|---|---|
指定した緯度・経度にGPSを設定する | When I am at 35.6102724, 139.7481288 | Then /^I am at ([-+]?[0-9]*\.?[0-9]+), ([-+]?[0-9]*\.?[0-9]+)$/ |
指定した緯度・経度にGPSを設定する | Then I go to 35.6102724, 139.7481288 | Then /^I go to ([-+]?[0-9]*\.?[0-9]+), ([-+]?[0-9]*\.?[0-9]+)$/ |
ちなみにアプリからGPSを操作するためには、「{プロジェクトのルート}/app/src/main/AndroidManifest.xml」ファイルに、下記の定義を追加する必要があります。
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
スクリーンショットの撮影
Calabash-Androidには、下記のスクリーンショット撮影用の「ステップ定義」が用意されています。
テストシナリオ内での実際の記述方法 | ステップ定義 |
---|---|
Then take picture | Then /^take picture$/ |
Then I take a picture | Then /^I take a picture$/ |
Then I take a screenshot | Then /^I take a screenshot$/ |
これらを使用すると、プロジェクトのルートに、「screenshot_x.png」の名前でスクリーンショットの画像ファイルが作成されます(「screenshot_0.png」「screenshot_1.png」「screenshot_2.png」……のように、xの部分は0からインクリメントされます)。
・スクリーンショットファイルの出力先の指定
スクリーンショットファイルの出力先は、Calabash-Androidの実行時に下記手順で指定することも可能です。
$ SCREENSHOT_PATH=./result/ calabash-android run {YOUR_APK_FILE}
指定できるパスは、プロジェクトのルートからの相対パスです。指定するパスに相当するディレクトリは、事前に作成しておく必要があります。作成しておかないと、スクリーンショット撮影時にエラーとなります。
詳しくは、Screenshot locationも参考にしてください。
・テスト失敗時のスクリーンショットの自動撮影の停止方法
Calabash-Androidのデフォルト設定では、テスト失敗時にも自動的にスクリーンショットを撮影します。ファイル名および出力先は、上記と同じです。テストシナリオを作成途中の場合、この画像ファイルがどんどん増えてきて邪魔になることがあります。
そのため、この機能を停止したい場合は、「{プロジェクトのルート}/features/support/app_life_cycle_hooks.rb」の下記の箇所をコメントアウトしてみてください。
After do |scenario| if scenario.failed? # screenshot_embed ←テスト失敗時に、スクリーンショットを自動撮影しないようにします。 end shutdown_test_server end
・機能の限界と拡張
一方でこのCalabash-Androidのスクリーンショット撮影機能には、次のような問題もあります。これらを解決するためには、スクリーンショットの撮影機能を拡張する必要があります。
- ファイル名を指定できない
- フィーチャーごと/シナリオごとにフォルダー/ディレクトリを分けてファイルを保存できない
これを解決するための「ステップ定義」の例を紹介します。
下記の例は、「{プロジェクトのルート}/report/bdd/{フィーチャー名}」ディレクトリを作成し、そこに「{シナリオ名}-x.png」(「x」の部分は0からインクリメントされます)の名前でスクリーンショットを撮影します。
この例をベースに、皆さんのプロダクトに合った出力方法を模索してみてください。
AfterConfiguration do |config| FeatureNameMemory.feature_name = nil FeatureNameMemory.scenario = nil ←追加 end Before do |scenario| (中略) FeatureNameMemory.feature_name = feature_name FeatureNameMemory.scenario = scenario ←追加 (中略) FeatureNameMemory = Class.new class << FeatureNameMemory @feature_name = nil @scenario = nil ←追加 attr_accessor :feature_name, :scenario, :invocation ←追加 end
@@baseDir = "./report/bdd/" Then(/^take photo$/) do screenshotDir = @@baseDir + FeatureNameMemory.feature_name screenshotName = FeatureNameMemory.scenario.name FileUtils.mkdir_p(screenshotDir) unless FileTest.exists?(screenshotDir) screenshot_embed({:prefix => screenshotDir, :name => screenshotName, :label => screenshotName}) end
なお、「FeatureNameMemory.scenario」の仕様については、Cucumber::Ast::Scenarioをご確認ください。
ステップの実行タイミングの調整
Calabash-AndroidもSeleniumなどと同様、表示に時間がかかるなどして、指定したUIコンポーネントの表示が終わりきっていない状況でステップを実行すると、当該UIコンポーネントが見つからないというエラーとして扱われてしまいます。
こうしたエラーを防止するため、Calabash-Androidでは、ステップの実行タイミングを調整するための「ステップ定義」が用意されています。
・待ち時間を明示的に指定する方法
効果 | テストシナリオ内での実際の記述方法 | ステップ定義 |
---|---|---|
次のステップを実行するまで1秒待つ | Then I wait for 1 second | Then /^I wait for 1 second$/ |
次のステップを実行するまで1秒待つ | Then I wait for a second | Then /^I wait for a second$/ |
次のステップを実行するまで2秒待つ | Then I wait | Then /^I wait$/ |
次のステップを実行するまで、指定した秒数待つ | Then I wait for 3 seconds | Then /^I wait for (\d+) seconds$/ |
・UIコンポーネントの表示を待つ方法
上記「待ち時間を明示的に指定する方法」は、一見便利ではありますが、一方で次のような課題もあります。
- UIコンポーネントの表示時間が、実行するPC/エミュレーター/実機によってそれぞれ異なるため、待ち時間を一律に指定しづらい
- 待ち時間を一定にするために、テスト対象のエミュレーター/実機を絞ることは、テストの目的として本末転倒
- テストシナリオ内に待ち時間を指定するステップを増やしすぎると、本来検証したいことが見えづらくなってしまう
「Specification by Example」の11章でも、「待ち時間を明示的に指定する方法は可能ならば避けるべし」と明言されています。そのため、UIコンポーネントの表示を待つ下記の方法の採用をオススメします。
効果 | テストシナリオ内での実際の記述方法 | ステップ定義 |
---|---|---|
プログレスバーが表示されなくなるまで待つ | Given I wait for progress | Then /^I wait for progress$/ |
指定したテキストが表示されるまで待つ | When I wait for "まどか" to appear | Then /^I wait for "([^\"]*)" to appear$/ |
指定したテキストが表示されるまで待つ | Then I wait to see "まどか" | Then /^I wait to see "([^\"]*)"$/ |
指定したテキストが表示されるまで、指定した秒数待つ。指定した秒数を超えるとタイムアウトエラー | Then I wait up to 3 seconds for "まどか" to appear | Then /^I wait up to (\d+) seconds for "([^\"]*)" to appear$/ |
指定したテキストが表示されるまで、指定した秒数待つ。指定した秒数を超えるとタイムアウトエラー | Then I wait up to 3 seconds to see "まどか" | Then /^I wait up to (\d+) seconds to see "([^\"]*)"$/ |
指定したIDのButtonが表示されるまで待つ(Button以外は不可) | Then I wait for the "name" button to appear | Then /^I wait for the "([^\"]*)" button to appear$/ |
指定したアクティビティ名の画面が表示されるまで待つ | Then I wait for the "preview" screen to appear | Then /^I wait for the "([^\"]*)" screen to appear$/ |
指定したIDのViewが表示されるまで待つ | Then I wait for the view with id "add" to appear | Then /^I wait for the view with id "([^\"]*)" to appear$/ |
指定したアクティビティ名の画面が表示されるまで待つ。指定した秒数を超えるとタイムアウトエラー | Then I wait up to 5 seconds for the "preview" screen to appear | Then /^I wait up to (\d+) seconds for the "([^\"]*)" screen to appear$/ |
指定したアクティビティ名の画面が表示されるまで待つ。指定した秒数を超えるとタイムアウトエラー | Then I wait upto 5 seconds for the "preview" screen to appear | Then /^I wait upto (\d+) seconds for the "([^\"]*)" screen to appear$/ |
「データ駆動型テスト」を実現するための「Scenario Outline」
「データ駆動型テスト」(「データドリブンテスト」「Data-driven testing」とも呼称)とは、Excelなどの表に用意したデータを使用して、同じテストを異なるデータを利用しながら実施すること、またはその仕組みです。
Calabash-Androidでも、前回の『例をベースに仕様を見つける』の表形式と似た方法で、「データ駆動型テスト」を実施できます。
ポイントは、次の通りです。
- 「Scenario Outline:」で始まるステップを定義する
- 「データ駆動型テスト」で代入したい箇所は、「<データ名>」の書式でシナリオに記述する
- ちなみに、「<データ名>」はそのままリテラルとして扱われるため、ダブルクォーテーションを使用する「ステップ定義」を使用する場合は、「"<データ名>"」のようにダブルクォーテーションをステップ内で明示的に指定する
- シナリオの最後に「Examples:」と書き、代入したいデータ表を定義する
「{プロジェクトのルート}/features/PreviewCustomer.feature」をベースに、「SpecifyByExampleTable.feature」の表データを組み合わせた例「ScenarioOutlineExample.feature」を、下記に示します。
(中略) Scenario Outline: Add customer information and preview it by using WebView Given I press "button_add" When I enter text "<name>" into field with id "name" ←一番下にある表形式の該当データを取得し、当該「ステップ定義」を呼び出す。 And I enter text "<email>" into field with id "email" And I press "<gender>" And choose age as <age> And go preview And wait for preview screen Then I should see name as "<name>" And I should see "<email>" at "mail" And I should see "<previewGender>" at "gender" And I should see "<age>" at "age" And I should see "<division>" at "division" Examples: ←この宣言の後に、表形式でデータを定義する |name |email |gender |age|previewGender|division| |暁美 ほむら|homura.akemi@example.com |genderFemale|20 |女性 |F1層 | |鹿目 まどか|madoka.kaname@example.com|genderFemale|34 |女性 |F1層 | (以下略)
9行目の指定方法については、『NumberPickerの操作』で解説しています。
次回はSeleniumでモバイルアプリのテストができる「Appium」
今回まで4回にわたり、Calabashの基本からCalabash-Androidをより高度に利用する際に必要となる点について説明してきましたが、いかがでしたでしょうか。
次回は、「Selenium」でモバイルアプリのテストができるツール「Appium」を紹介します。
- iOS/AndroidのUIテストを自動化するAppiumのテストスクリプトの書き方とインスペクターの使い方
- SeleniumのUIテスト自動化をiOS/AndroidにもたらすAppiumの基礎知識とインストール方法、基本的な使い方
- Calabash-Androidのテスト高速化、GPS、スクショ、データ駆動型テスト
- Calabash-AndroidによるBDDの実践とJenkinsによる「Living documentation」
- Calabash-Androidでテストシナリオを作成する方法
- iOS/AndroidにCucumberのBDDをもたらすテストフレームワークCalabashの基礎知識とインストール
- Androidテストで便利なuiautomatorviewer、UiScrollableの使い方、テキスト入力API制限事項の回避方法
- Android SDK標準の何でもテストツールuiautomatorの基本的な使い方
- システムテスト自動化の基礎知識とMonkeyTalkの使い方
参考資料
- Calabasn-Androidのrdoc(0.5.2)
- BDD in Action
- Specification by Example
- Growing Object-Oriented Software Guided by Tests
- The Cucumber Book
- Cucumber Recipes
著者紹介
伊藤宏幸
楽天株式会社 開発プロセスオプティマイゼーション部 品質保証課 テスト駆動開発グループ所属 アジャイルコーチ(執筆当時)
アジャイルコーチおよびシステムアーキテクトとして、実際に開発現場に入り、CI/CD(Jenkins)、TDD/BDDをベースとした技術基盤の構築と、それらをベースとした開発プロセスの改善支援を行っている。モットーは、開発効率の向上による「Be happy!」の実現。
2014年3月より、テスト自動化研究会(STAR)に参加。
2014年7月、アメリカで開催された世界最大のアジャイルのカンファレンス「Agile 2014」に登壇。
- テーマ『Technology-Driven Development: Using Automation and Techniques to Grow an Agile Culture』、公式サイトページ、プレゼン資料、論文
著書『プログラミングの教科書 かんたん UML入門』(共著/技術評論社)
ブログ「THE HIRO Says」
Twitter:@hageyahhoo
Copyright © ITmedia, Inc. All Rights Reserved.
関連記事
- テスト自動化の歴史と今後、良い/悪い事例〜システムテスト自動化カンファレンス2013レポート
テスト自動化を開発の“武器”にするための3つのポイントや、“自動化”の良い事例、悪い事例など、テストの現場を「進化させる」知見が多数紹介されたカンファンレンスの模様をレポートする。 - ビジネス目標を見据えたテスト設計が肝!「DevOps時代のテスト自動化カンファレンス 冬の陣」開催
DevOpsの実践で肝となるソフトウェアテストの自動化。しかし@ITの読者調査でも50%以上が「テスト環境に課題あり」と回答した。これにどう対応すれは良いのだろうか? カンファレンス登壇者の言葉にヒントを探る。 - Kiwi+CocoaPodsで始めるiOSアプリの振る舞いテスト入門
現代の開発現場において欠かせないCI/継続的デリバリを、iOSアプリ開発に適用するためのツールやノウハウを解説する連載。今回は、iOSアプリの機能の振る舞いをテストするテスティングフレームワークの特長とインストールの仕方、主な使い方を解説します。 - Android SDKでビジネスロジックのテストを自動化するには
- 第2回Androidテスト祭りレポート:Android開発の上層テストで失敗しないためのポイントとは
セキュリティ設計や受け入れテストガイドライン、CIツールJenkins+コードレビューGeritt、テスト効率化ノウハウ、リモートテストサービスなど