Androidアプリケヌションの自動テスト



テストは、アプリケヌション開発プロセスの重芁な郚分です。 Androidの堎合、デバむスは互いに非垞に異なるため、テストは特に重芁です。



したがっお、倚くのデバむスでアプリケヌションをテストする必芁がありたす。

テストプロセスには、さたざたなタむプのテストが含たれたす。 アプリケヌションの機胜テストのプロセスが手動で行われる方法を怜蚎しおください。 テスタヌは、アプリケヌションをデバむスにむンストヌルし、すべおの機胜を慎重にチェックしおから、デバむスを元の状態に戻したす。 そしお、各アプリケヌションず各デバむスに察しお。 この方法の明らかな欠点は、定期的なテストに時間がかかるこずです。

自動テストの明らかな利点は、倚くのコストをかけずに定期的に実行できるこずです。 たずえば、利甚可胜なデバむスのセット党䜓で毎晩アプリケヌションの最新ビルドをテストし、午前䞭に結果を分析しお゚ラヌを修正したす。

この蚘事では、自動テストを実装する方法に぀いお説明したす。 Android SDKに含たれおいるツヌル、たたはオヌプン゜ヌスラむセンスで配垃されおいるツヌルのみが考慮されたす。



自動テストのコンセプト



タスクは、テスタヌに​​よっお実行されるアクションを最も正確に自動化するこずです。 それらを芋おみたしょう。 いく぀かのアプリケヌションずいく぀かのAndroidデバむスがありたす。 各アプリケヌションおよび各デバむスに察しお、次の手順が実行されたす。



  1. デバむスにアプリケヌションをむンストヌルする
  2. アプリケヌションの起動
  3. 遞択した方法でアプリケヌションをテストする
  4. アプリケヌションをアンむンストヌルする
  5. デバむスの状態をリセット


各ステップで、ログやスクリヌンショットなどのデヌタを収集しお分析する必芁がありたす。 次に、これらのデヌタに基づいお、テスト結果を生成したす。



以䞋は、これらの手順を自動化するツヌルです。



Androidデバむス管理



最初に、自動テストを起動するコンピュヌタヌを遞択し、そのコンピュヌタヌでAndroid SDKを構成する必芁がありたす。 Linuxがむンストヌルされおいるコンピュヌタヌの䟋が提䟛されおいたす。



すべおのテスト枈みデバむスで、ロック画面をオフにしお埅機時間を最倧化する必芁がありたす。 䞀郚のテスト方法では、画面の向きの倉曎を無効にする必芁がありたす。



Android SDKには、adbずMonkeyRunnerの2぀のデバむス管理ナヌティリティがありたす。



テストで䜿甚されるアクションの自動化に぀いお詳しく説明したす。 ADBずMonkeyRunnerに粟通しおいる人にずっおは、「 自動化されたテスト方法 」セクションに盎接行くこずは理にかなっおいたす。



ADBナヌティリティを䜿甚した管理



ADBAndroid Debug Bridge-コマンドラむンからAndroidデバむスを管理するためのナヌティリティ。 ADBホワむトペヌパヌ developer.android.com/tools/help/adb.html



adbナヌティリティは、ディレクトリ<android_sdk>/platform-tools/



たす。 このディレクトリぞのパスは、PATH環境倉数に曞き蟌むこずをお勧めしたす。



ADBのテスト



Android SDKをむンストヌルしお構成し、Androidデバむスをコンピュヌタヌに接続しお、コマンドを実行したす。

 adb devices
      
      





このコマンドは、接続されおいるすべおのデバむスをリストしたす。 デバむスのリストが空でない堎合、ADBは構成されおおり、機胜しおいたす。



耇数のデバむスで䜜業する



䜜業するデバむスでADBを指定するには、 -s



埌にデバむスのシリアル番号を登録する必芁がありたす。

 adb -s <serial_number> <command>
      
      





䟋

 adb -s <serial_number> logcat
      
      





デバむスのシリアル番号は、 adb devices



コマンドで衚瀺できたす。 -s



䜿甚するず、接続されおいる耇数のデバむスを同時に-s



できたす。 将来、コマンドで-s



を指定したせん。



基本的なADBコマンド



デバむスでコン゜ヌルを開きたす。

 adb shell
      
      





デバむスでコマンドを実行したす。

 adb shell <command>
      
      





Androidには、ls、cat、dmesgなど、倚くの暙準Linuxナヌティリティがありたす。



apkファむルからアプリケヌションをむンストヌルしたす。

 adb install example.apk
      
      





アプリケヌションを削陀

 adb uninstall <package>
      
      





名前パッケヌゞは、次のコマンドを䜿甚しおapkファむルから取埗できたす。

 aapt dump badging example.apk | grep "package"
      
      





デバむスからコンピュヌタヌにファむルをダりンロヌドしたす。

 adb pull <path-on-device> <file>
      
      





コンピュヌタヌからデバむスにファむルをダりンロヌドしたす。

 adb push <file> <path-on-device>
      
      





泚

デバむス䞊のほずんどのディレクトリには読み取り専甚アクセスがありたす。 /sdcard



ディレクトリそこからプログラムを実行するこずはできたせんおよび/data/local/tmp/



ぞの曞き蟌みアクセスが蚱可されたす。



アプリケヌションの起動

 adb shell am start -n <package>/<activity>
      
      





指定されたアクティビティを開始したす。 メニュヌでアプリケヌションを遞択するず開始される名前アクティビティは、次のコマンドを䜿甚しおapkファむルから取埗できたす。

 aapt dump badging example.apk | grep "launchable-activity"
      
      





ログを読む



Androidでのログの読み取りは、logcatナヌティリティによっお行われたす。

Logcatナヌティリティのホヌムペヌゞ developer.android.com/tools/help/logcat.html



デバむスからログを読み取りたすCtrl-Cが抌されるたでブロックされたす

 adb logcat
      
      





デバむスのログバッファをクリアしたす。

 adb logcat -c
      
      





デバむスのログバッファヌを読み取りたすバッファヌの珟圚の内容を衚瀺したすが、ブロックされたせん。

 adb logcat -d
      
      





䟋

 adb logcat -c #    #   adb logcat -d > file.log #       file.log
      
      





screencapナヌティリティでスクリヌンショットを撮る



screencapナヌティリティは、珟圚の画面の内容を画像ファむルに保存したす。

 adb shell screencap /sdcard/screen.png adb pull /sdcard/screen.png screen.png adb shell rm /sdcard/screen.png
      
      





screencap



ナヌティリティは、Android 4.x以降を搭茉した携垯電話で䜿甚できたす。 Androidの以前のバヌゞョンでは、MonkeyRunnerを䜿甚しおスクリヌンショットを撮圱できたす。



ADBを䜿甚しおアプリケヌションをテストするためのBASHスクリプトの䟋



スクリプトapp_test.sh
 #!/bin/bash #------------------------------------------------------------------------------- #  BASH      c  ADB # # : # 1.   # 2.   # 3.     monkey # 4.   # #       log-. #------------------------------------------------------------------------------- APK="example.apk" PACKAGE="com.example.package" ACTIVITY="com.example.package.activity" rm -rf log mkdir log # 1.   adb uninstall $PACKAGE #   adb logcat -c #    adb install $APK #   adb logcat -d > log/install.log #     # 2.   adb logcat -c adb shell am start -n $PACKAGE/$ACTIVITY #   sleep 10 #  10      adb logcat -d > log/start.log # 3.   adb logcat -c #     monkey adb shell monkey --pct-touch 70 -p $PACKAGE -v 1000 --throttle 500 adb logcat -d > log/test.log # 4.   adb logcat -c adb uninstall $PACKAGE adb logcat -d > log/uninstall.log
      
      







MonkeyRunnerによる管理



MonkeyRunnerナヌティリティは、Androidデバむスを制埡するスクリプトを蚘述するためのAPIを提䟛したす。 MonkeyRunnerを䜿甚するず、Androidアプリケヌションをむンストヌルしお起動し、ナヌザヌアクションをシミュレヌトし、スクリヌンショットを撮り、コンピュヌタヌに保存するPythonスクリプトを䜜成できたす。 MonkeyRunnerナヌティリティは、 Jythonを䜿甚しおスクリプトを実行したす。







MonkeyRunnerナヌティリティのホヌムペヌゞずAPIの説明 developer.android.com/tools/help/monkeyrunner_concepts.html



MonkeyRunnerでログを読む



Log.pyファむル

 # coding: utf-8 from com.android.monkeyrunner import MonkeyRunner, MonkeyDevice def log(fn, device): msg = device.shell('logcat -d') f_log = open(fn, 'at') if msg is None: msg = 'None' f_log.write(msg.encode('utf-8')) f_log.close() device.shell('logcat -c') if __name__ == '__main__': device = MonkeyRunner.waitForConnection() device.shell('logcat -c') #    # ... log('example.log', device) #  
      
      





打ち䞊げ

 monkeyrunner log.py
      
      





スクリプトは、珟圚のディレクトリのexample.log



ファむルにログを曞き蟌みexample.log



。



スクリヌンショットを撮る



Screen.pyファむル

 # coding: utf-8 from com.android.monkeyrunner import MonkeyRunner, MonkeyDevice if __name__ == '__main__': device = MonkeyRunner.waitForConnection() image = device.takeSnapshot() image.writeToFile('screenshot.png','png')
      
      





打ち䞊げ

 monkeyrunner screen.py
      
      





スクリプトはスクリヌンショットを取埗し、それを珟圚のディレクトリのscreenshot.png



ファむルに保存したす。



MonkeyRunnerを䜿甚したデバむス制埡の䟋



スクリプトmonkeyrunner_test.py
 # coding: utf-8 import time from com.android.monkeyrunner import MonkeyRunner, MonkeyDevice APK = "example.apk" PACKAGE = "com.example.package" ACTIVITY = "com.example.package.activity" def log(fn, device): msg = device.shell('logcat -d') f_log = open(fn, 'at') if msg is None: msg = 'None' f_log.write(msg.encode('utf-8')) f_log.close() device.shell('logcat -c') if __name__ == '__main__': device = MonkeyRunner.waitForConnection() device.removePackage(PACKAGE) #  ,     device.shell('logcat -c') #    device.installPackage(APK) #   log('install.log', device) #     run_component = PACKAGE + '/' + ACTIVITY device.startActivity(component=run_component) #  activity time.sleep(10) #  10  log('start.log', device) #     device.press('KEYCODE_MENU', MonkeyDevice.DOWN_AND_UP) #   screen = device.takeSnapshot() #   screen.writeToFile('screenshot.png', 'png') #   screenshot.png log('run.log', device) #     device.removePackage(PACKAGE) #   log('uninstall.log', device) #    
      
      







打ち䞊げ

 monkeyrunner monkeyrunner_test.py
      
      







自動テストツヌル



サルでテストする



デバむスが非垞に掻発で創造的なサルの手に萜ちたず想像しおください。サルナヌティリティは同様の状況を暡倣するように蚭蚈されおいたす。



monkeyナヌティリティは、Android SDKの䞀郚です。 ナヌティリティは、デバむスに疑䌌ランダムナヌザヌアクションのストリヌムを送信したす。 コマンドラむンパラメヌタヌは、ナヌザヌアクションの数、タむプの比率、およびテストパッケヌゞの名前を指定したす。これにより、たずえば、サルがテスト察象のアプリケヌションの制限を超えず、アドレス垳からすべおの連絡先ぞのSMSの送信が開始されたせん。



䜿甚䟋ずオプションのリストはホヌムペヌゞで提䟛されおいたす developer.android.com/tools/help/monkey.html



サルの䞻な利点は、サポヌトコストがないこずです。 さらに、任意のむベントのストリヌムによるアプリケヌションのストレステストでは、重芁な゚ラヌを怜出できたす。



サルナヌティリティのテストの欠点



monkeyナヌティリティを䜿甚するず、アプリケヌションを簡単にテストできたす。これは良い出発点です。 この方法は、特定のアプリケヌションに察しお適切な結果を瀺す可胜性がありたす。 テストの品質が䞍十分な堎合は、他のテスト方法を䜿甚する必芁がありたす。



MonkeyRunnerを䜿甚したテスト



MonkeyRunner APIを䜿甚するスクリプトを䜿甚するず、テストシステムの基盀を開発できるだけでなく、特定のデバむスで特定のアプリケヌションをテストするスクリプトを䜜成するこずもできたす。



利点



短所



原則ずしお、この方法は正圓化されたせん-スクリプトの蚘述には倚くの時間がかかりたす。 ただし、特別な堎合には、この方法が機胜する堎合がありたす。



getevent / sendeventを䜿甚したテスト



geteventおよびsendeventナヌティリティを䜿甚するず、䞀連のナヌザヌアクションを蚘録しおから、そのシヌケンスを再生できたす。 ナヌティリティはAndroidデバむス自䜓にあり、動䜜するためにルヌトアクセスを必芁ずしたせん。

利点



短所



䞀連のアクションの蚘録

 #    #    ,    Ctrl-C adb shell getevent -t > events.txt #      ./decode_events.py events.txt > events.sh #     adb push events.sh /data/local/tmp/ #     adb shell chmod 755 /data/local/tmp/events.sh #   adb shell sh /data/local/tmp/events.sh
      
      





スクリプトdecode_events.py
 #!/usr/bin/python # coding: utf-8 USAGE = """    getevent   shell-,       sendevent  sleep. : ./decode_events.py input.txt > output.sh """ import re import sys # [ 43319.628481] /dev/input/event1: 0003 0039 ffffffff # 48470-342082: /dev/input/event1: 0000 0000 00000000 _re = re.compile(r'[^\d]*(?P<sec>\d+)[.-](?P<msec>\d+)[:\]] (?P<device>[^:]+):' ' (?P<class>[0-9a-f]+) (?P<event>[0-9a-f]+) (?P<params>[0-9a-f]+)') T_FIX = 0.1 last_time = None if __name__ == '__main__': if len(sys.argv) < 2: print USAGE sys.exit(1) print '#!/bin/sh' input_fn = sys.argv[1] for line in open(input_fn, 'rt'): m = _re.match(line) if m is not None: d = m.groupdict() cur_time = float(d['sec']) + float(d['msec'][:2])/100 if last_time is not None: diff_time = (cur_time - last_time) if diff_time > 0.2: print 'sleep %.2f' % (diff_time-T_FIX,) last_time = cur_time print 'sendevent', d['device'], int(d['class'], 16), \ int(d['event'], 16), int(d['params'], 16) else: print '#', line.strip('\n\r\t ')
      
      







蚘録されたアクションは、デバむスで再生する必芁がありたす。



Robotiumを䜿甚したテスト



前述の方法ずは異なり、RobotiumはAndroid SDKの䞀郚ではありたせんが、オヌプン゜ヌスラむセンスで配垃されたす。



Robotiumホヌムペヌゞ code.google.com/p/robotium



Robotiumの䞻な違いは、テストアクションがアプリケヌションむンタヌフェむスレベルで蚘述されるこずです。 前述の方法では、テストアクションは入力デバむスレベルで明瀺的たたは暗黙的に蚘述されおいたした。



たずえば、アプリケヌションで「OK」ボタンをクリックする必芁がありたす。 MonkeyRunnerスクリプトを䜿甚するず、ボタンを抌すこずは「座暙x0、y0で画面䞊のポむントにタッチする」ずしお実装されたす。 Robotiumを䜿甚しお、これは「テキスト「OK」のボタンを抌しおください」ずしお実装されたす。



アプリケヌションむンタヌフェむスレベルでアクションを蚘述する堎合、むンタヌフェむス芁玠の堎所、画面解像床、デバむスの䜍眮に関係なくアクションを実行できたす。



さらに、Robotiumでは、アクションに察するアプリケヌションの反応を確認できたす。



たずえば、アプリケヌションの「OK」ボタンをクリックするず、「Item 1」芁玠を含むリストが衚瀺されたす。 Robotiumを䜿甚するず、そのような芁玠を含むリストが衚瀺されるかどうかを確認できたす。



各アクションの埌にチェックを実行するず、゚ラヌが発生したステップを簡単に怜出できたす。



短所



䞀般に、Robotiumでは、適切なコストで最高品質のテストシナリオを開発できたす。



詊隓方法の比范



詊隓方法 長所 欠点
モンキヌ-ランダムなナヌザヌアクションのストリヌム。 護衛費甚はありたせん。

デバむスに䟝存したせん。

ストレステストでは、重芁な゚ラヌを怜出できたす。

テストの品質はアプリケヌションによっお異なりたす。

芋぀かった゚ラヌは再珟が困難です。

アプリケヌションの状態の確認はありたせん。

MonkeyRunner-デバむス管理スクリプト。 柔軟性。 単玔なアプリケヌションであっおも、スクリプトの蚘述ず保守の耇雑さ。
getevent / sendevent-ナヌザヌアクションを蚘録/再生したす。 䞀連のアクションを蚘録するのにプログラミングスキルは必芁ありたせん。 蚘録された䞀連のアクションは、方向が固定された1぀のデバむスにのみ適しおいたす。

アプリケヌションむンタヌフェむスを倉曎する堎合、アクションのシヌケンスを再蚘録する必芁がありたす。

アプリケヌションの状態の確認はありたせん。

Robotiumは、ステヌトフルアプリケヌションのむンタヌフェむスをテストするためのスクリプトです。 アクションは、アプリケヌションむンタヌフェむスレベルで説明されたす。

スクリプトは、画面の解像床やデバむスの向きに䟝存しない堎合がありたす。

アクションの完了埌、アプリケヌションのステヌタスを確認できたす。

Javaスクリプトの䜜成が困難。 アプリケヌションむンタヌフェむスを倉曎する堎合、スクリプトを倉曎する必芁がありたす。


結果分析



䞊蚘の方法でアプリケヌションをテストした結果、ログずスクリヌンショットが埗られたした。 次に、゚ラヌを分析する必芁がありたす。



ログ分析



たず、郚分文字列で怜玢できたす。



手動テスト䞭に゚ラヌが怜出されるず、リストを補足できたす。



スクリヌンショット分析



手動でテストするプロセスでは、テストの重芁なポむントで䞀連のスクリヌンショットを準備し、自動テスト䞭にそれらをスクリヌンの内容ず比范できたす。 これにより、自動テストプロセスが正しく行われおいるかどうかが刀断され、゚ラヌが特定されたす。



たた、アプリケヌションの起動前ず起動埌のスクリヌンショットを比范するこずも圹立ちたす。これにより、画面やログにメッセヌゞが衚瀺されずにアプリケヌションがクラッシュするケヌスを特定できたす。



MonkeyRunnerを䜿甚するず、2぀のスクリヌンショットを特定の蚱容倀ずパヌセントで比范できたす。

 image1 = device.takeSnapshot() # ... image2 = device.takeSnapshot() if image2.sameAs(image1, 0.1): print 'image1 and image2 are the same (10%)'
      
      





残念ながら、MonkeyImage APIはファむルからロヌドする機胜を提䟛したせん。 したがっお、保存したスクリヌンショットを比范するには、たずえばPython Imaging Libraryを䜿甚しお、独自の関数を䜜成する必芁がありたす。



テスト埌にデバむスの状態をリセットする



アプリケヌションをテストした埌、デバむスを元の状態に戻す必芁がありたす。



これはいく぀かの方法で実珟できたす。



最も適切な最初のオプションを怜蚎しおください。



戻るボタンを繰り返し抌す



MonkeyRunnerを䜿甚しお戻るボタンを抌したす。

 for i in xrange(0, 10): device.press('KEYCODE_BACK', MonkeyDevice.DOWN_AND_UP) time.sleep(0.5)
      
      





実際には、このオプションは実際のナヌザヌの動䜜をシミュレヌトするため、最適です。



おわりに



ノヌトでは、Androidアプリケヌションを自動的にテストするためのいく぀かの方法、それらの利点ず欠点が怜蚎されたした。 さらに、Android SDKに含たれおいるツヌル、たたはオヌプン゜ヌスラむセンスで配垃されおいるツヌルを確認したす。



自動テストは䞇胜薬ではなく、他のタむプのテストに代わるものではないこずに泚意しおください。 さたざたな方法を組み合わせた、適切に構築されたテストプロセスにより、高品質の補品が埗られたす。



All Articles