blob: 931fd77d3aa960732cc412aeadc5d0ca35a9a4a6 [file] [log] [blame]
The Android Open Source Project5c118522008-10-21 07:00:00 -07001
2<html>
3<head>
4<meta http-equiv="content-type" content="text/html; charset=utf-8"/>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -08005<title>Android - Porting Guide</title>
The Android Open Source Project5c118522008-10-21 07:00:00 -07006<script src="http://www.google.com/uds/api?file=uds.js&amp;v=1.0&amp;key=internal-codesite" type="text/javascript"></script>
7<script src="http://code.google.com/js/jquery.js" type="text/javascript"></script>
8<script type="text/javascript">var _tocPath_ = 'http://code.google.com/android/_toc.ezt';</script>
9<script src="http://code.google.com/js/codesite.pack.01312008.js" type="text/javascript"></script>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080010<script language="JavaScript">
11function resizeHeight() {
12 if(document.getElementById && !(document.all)) {
13 height= document.getElementById('doxygen').contentDocument.body.scrollHeight + 20;
14 document.getElementById('doxygen').style.height = height;
15 }
16 else if(document.all) {
17 height= document.frames('doxygen').document.body.scrollHeight + 20;
18 document.all.doxygen.style.height = height;
19 }
20}
21</script>
The Android Open Source Project5c118522008-10-21 07:00:00 -070022<link href="http://code.google.com/css/codesite.pack.01312008.css" type="text/css" rel="stylesheet">
23</link>
24
25<!--[if IE]><link rel="stylesheet" type="text/css" href="/css/iehacks.css" /><![endif]-->
26<script src="http://code.google.com/android/assets/search_autocomplete.js"></script>
27<link rel="stylesheet" type="text/css" href="http://code.google.com/css/semantic_headers.css" />
28<link rel="stylesheet" type="text/css" href="http://code.google.com/android/assets/style.css" />
29<script>
30 jQuery(document).ready(function() {
31 jQuery("pre").addClass("prettyprint");
32 });
33 </script>
34<style type="text/css">
35<!--
36h1,h2,h3 {
37 color: #000000;
38}
39-->
40</style>
41</head>
42<body class="gc-documentation">
43<div id="gc-container">
44<a name="top"></a>
45<div id="skipto"> </div>
46<div id="langpref">
47 <!--<a class="dropdown" href="/">English</a> <span>|</span> <a href="/more/">Site Directory</a> -->
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080048
The Android Open Source Project5c118522008-10-21 07:00:00 -070049</div>
50<div id="gc-header">
51 <div id="logo"><a href="http://code.google.com/android/index.html"><img src="http://code.google.com/android/images/logo_android.gif" alt="Android"/></a></div>
52 <div id="search" style="inline">
53 <div id="searchForm" class="searchForm" style="height: 44px;">
54 <!--previously form was here-->
55 </div>
56 <!-- end searchForm -->
57 <noscript>
58 <style type="text/css">
59 .searchForm {
60 display : none !important;
61 }
62 .searchForm2 {
63 display : inline !important;
64 }
65 </style>
66 </noscript>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080067
The Android Open Source Project5c118522008-10-21 07:00:00 -070068 <div id="searchForm2" class="searchForm2" style="display:none">
69 <form id="searchbox_001456098540849067467:6whlsytkdqg" action="http://www.google.com/cse">
70 <input type="hidden" name="cx" value="001456098540849067467:6whlsytkdqg" />
71 <input type="hidden" name="cof" value="FORID:0" />
72 <input type="text" name="q" maxlength="2048" size="41" autocomplete="off" title="Google Code Search"/>
73 <input type="submit" name="sa" value="Search" title="Search"/>
74 <br/>
75 <div class="greytext">e.g. "ajax apis" or "open source"</div>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080076
The Android Open Source Project5c118522008-10-21 07:00:00 -070077 </form>
78 </div>
79 <!-- end searchForm2 -->
80 </div>
81 <!-- end search -->
82</div>
83<!-- end gc-header -->
84<div id="searchControl" class="search-control"></div>
85<!--[if IE]><iframe id="backiFrame" name="backiFrame" src='/dummy.html' style="display:none"></iframe><![endif]-->
86<div id="codesiteContent">
87<a name="gc-topnav-anchor"></a>
88<div id="gc-topnav">
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080089
The Android Open Source Project5c118522008-10-21 07:00:00 -070090 <h1>Android Platform Development Kit</h1>
91 <ul class="gc-topnav-tabs">
92 <li id="sdk_link"> <a href="http://code.google.com/android/index.html" title="Android Software Development Kit">SDK</a> </li>
93 <li id="docs_link"> <a href="index.html" title="Official Android documentation">Docs</a> </li>
94 <li id="faq_link"> <a href="http://code.google.com/android/kb/index.html" title="Answers to frequently asked questions about Android">FAQ</a> </li>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080095
The Android Open Source Project5c118522008-10-21 07:00:00 -070096 <li> <a href="http://android-developers.blogspot.com/" title="Official Android blog">Blog</a> </li>
97 <li> <a href="http://code.google.com/android/groups.html" title="Android developer forum">Group</a> </li>
98 <li> <a href="http://code.google.com/android/terms.html" title="Android terms of service">Terms</a> </li>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -080099 <li> <a href="mailto:android-pdk-feedback@google.com?subject=PDK%20Feedback&body=(filed%20from:%20instrumentation_framework.html%20v0.6%20-%2025%20November%202008)%0D%0A%0D%0ASUMMARY:%0D%0A%0D%0A%0D%0A%0D%0ASTEPS%20TO%20REPRODUCE:%0D%0A%0D%0A%0D%0A%0D%0AADDITIONAL%20NOTES:">Report a Problem</a> </li>
100
The Android Open Source Project5c118522008-10-21 07:00:00 -0700101 </ul>
102</div>
103<!-- end gc-topnav -->
104<div class="g-section g-tpl-180">
105<a name="gc-toc"></a>
106<div class="g-unit g-first" id="gc-toc">
107 <ul>
108 <li>
109 <h1><a href="index.html">Documentation</a></h1>
110 <ul>
111 <li> <strong>Introduction</strong>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800112
The Android Open Source Project5c118522008-10-21 07:00:00 -0700113 <ul>
114 <li><a href="system_requirements.html">Device Requirements</a></li>
115 </ul>
116 </li>
117 <li> <strong>Dev Environment Setup</strong>
118 <ul>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700119 <li><a href="build_system.html">Build System</a></li>
120 </ul>
121 </li>
122 <li> <strong>Basic Bring up</strong>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800123
The Android Open Source Project5c118522008-10-21 07:00:00 -0700124 <ul>
125 <li><a href="build_new_device.html">Building New Device</a></li>
126 <li><a href="bring_up.html">Bring up</a></li>
127 <li><a href="keymaps_keyboard_input.html">Keymaps and Keyboard</a></li>
128 <li><a href="display_drivers.html">Display Drivers</a></li>
129 </ul>
130 </li>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800131
The Android Open Source Project5c118522008-10-21 07:00:00 -0700132 <li> <strong>Multimedia</strong>
133 <ul>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800134 <li><a href="audio_sub_system.html">Audio</a></li>
135 <li><a href="camera.html">Camera</a></li>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700136 </ul>
137 </li>
138 <li> <strong>Power Management</strong>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800139
The Android Open Source Project5c118522008-10-21 07:00:00 -0700140 <ul>
141 <li><a href="power_management.html">Power Management</a></li>
142 </ul>
143 </li>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800144
145 <li> <strong>Networking</strong>
146 <ul>
147 <li><a href="wifi.html">Wi-Fi</a></li>
148 <li><a href="gps.html">GPS</a></li>
149 <li><a href="bluetooth.html">Bluetooth</a></li>
150 </ul>
151 </li>
152
The Android Open Source Project5c118522008-10-21 07:00:00 -0700153 <li> <strong>Telephony</strong>
154 <ul>
155 <li><a href="telephony.html">Radio Interface Layer</a></li>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800156
The Android Open Source Project5c118522008-10-21 07:00:00 -0700157 </ul>
158 </li>
159 <li> <strong>Testing</strong>
160 <ul>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700161 <li><a href="instrumentation_testing.html">Instrumentation Testing</a></li>
162 </ul>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800163
The Android Open Source Project5c118522008-10-21 07:00:00 -0700164 </li>
165 </ul>
166 </li>
167 </ul>
168</div>
169<a name="gc-pagecontent"></a>
170<div class="g-unit" id="gc-pagecontent">
171<div id="jd-content">
172<div class="jd-descr">
173
174
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800175<a name="androidTitleInstrumentationFramework"></a><h1>Instrumentation Testing</h1>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700176
177
178
179<a name="toc"/>
180<div style="padding:10px">
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800181<a href="#androidInstrumentationFrameworkIntro">Introduction</a><br/>
182<a href="#androidInstrumentationTestingFramework">Instrumentation Framework</a><br/><div style="padding-left:40px">
183
The Android Open Source Project5c118522008-10-21 07:00:00 -0700184<a href="#androidInstrumentationTestingClasses">Classes</a><br/>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800185<a href="#androidInstrumentationFrameworkamCommand">Understanding the am Command</a><br/></div>
186<a href="#androidInstrumentationFrameworkPlatform">Platform Test Suites</a><br/><div style="padding-left:40px">
The Android Open Source Project5c118522008-10-21 07:00:00 -0700187
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800188<a href="#androidTestingPlatformFramework">Framework Tests</a><br/>
189<a href="#androidTestingPlatformCoreLibrary">Core Library</a><br/></div>
190<a href="#androidInstrumentationFrameworkWritingRunning">Running Tests</a><br/><div style="padding-left:40px">
191
192<a href="#androidInstrumentationTestingRunningAll">All Tests with Default TestRunner behavior</a><br/>
193<a href="#androidTestingTestSinglePakcage">Running all Tests Under Single Package</a><br/>
194<a href="#androidTestingSingleTestSuite">Running a Single Test Suite</a><br/>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700195<a href="#androidInstrumentationTestingRunningSingleTestCase">A Single Test Case</a><br/>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800196<a href="#androidInstrumentationTestingRunningSingleTest">A Single Test</a><br/>
197<a href="#androidTestingDebugging">Attaching a debugger to your test</a><br/></div>
198<a href="#androidInstrumentationTestingCreating">Writing Tests</a><br/><div style="padding-left:40px">
The Android Open Source Project5c118522008-10-21 07:00:00 -0700199
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800200<a href="#androidTestingLocationFiles">Location of Files</a><br/>
201<a href="#androidTestingContentMakefile">Contents of makefile</a><br/>
202<a href="#androidTestingContentManifest">Content of Manifest</a><br/>
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800203<a href="#androidInstrumentationTestingCreatingTestRunner">New InstrumentationTestRunner</a><br/>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800204<a href="#androidInstrumentationTestingCreatingTestCase">New InstrumentationTestCase</a><br/>
205<a href="#androidInstrumentationFrameworkTestCase">Exploring a Test Case</a><br/>
206<a href="#androidTestingKindsofTests">Deciding Kinds of Tests to Write</a><br/></div>
207<a href="#androidInstrumentationFrameworkTroubleshooting">Troubleshooting</a><br/></div></font></div>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700208
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800209<a name="androidInstrumentationFrameworkIntro"></a><h2>Introduction</h2>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700210
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800211<p>This document describes how to use the Instrumentation Framework to write test cases. Instrumentation testing allows you to verify a particular feature or behavior with an automated JUnit TestCase. You can launch activities and providers within an application, send key events, and make assertions about various UI elements. </p>
212<p>You should have a working knowledge of the following:</p>
213<ul>
214 <li> Android Application Framework</li>
215 <li> Using <code>adb</code>, <code>am</code> and various logging functionality </li>
216 <li> A brief understanding of the application of interest, that is, the names of the classes which handle the intents etc. </li>
217 <li> JUnit testing.</li>
218</ul>
219<p> Each Android application runs in its own process. Instrumentation kills the application process and restarts the process with Instrumentation. Instrumentation gives a handle to the application context used to poke around the application to validate test assertions, allowing you to write test cases to test applications at a much lower level than UI screen shot tests. Note that Instrumentation cannot catch UI bugs. </p>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700220
221
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800222<a name="androidInstrumentationTestingFramework"></a><h2>Instrumentation Framework</h2>
223
224
225
226<a name="androidInstrumentationTestingClasses"></a><h3>Classes</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700227
228<p> The following classes help glue together <code>Instrumentation</code> with JUnit testing. </p>
229<table>
230 <tr>
231 <th scope="col">Class</th>
232 <th scope="col">Description</th></tr>
233 <tr>
234 <td valign="top"><code>InstrumentationTestCase</code></td>
235 <td valign="top">
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800236 <p>This extends the standard JUnit <code>TestCase</code> and offers access to an <code>Instrumentation</code> class. Write tests inside your instrumentation class any way you see fit. For example, your test might launch activities and send key events. For this to work properly, the instrumentation needs to be injected into the test case.</p> </td>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700237 </tr>
238 <tr>
239 <td valign="top"><code>InstrumentationTestRunner</code></td>
240 <td valign="top">The instrumentation test runner is an instrumentation that runs instrumentation test cases and injects itself into each test case. Instrumentation test cases need to be grouped together with an instrumentation test runner with the appropriate target package.</td>
241 </tr>
242 <tr>
243 <td valign="top"><code>InstrumentationTestSuite</code></td>
244 <td valign="top">The instrumentation test suite is a simple extension of the standard JUnit <code>TestSuite</code> that keeps a member <code>Instrumentation</code> variable on hand to inject into each <code>TestCase</code> before running them. It is used by <code>InstrumentationTestRunner</code>.</td>
245 </tr>
246</table>
247<p> Three additional base classes extend <code>InstrumentationTestCase</code> to allow you to test <code>Activity</code> and <code>Provider</code> classes:</p>
248<table>
249 <tr>
250 <th scope="col">Class</th>
251 <th scope="col">Description</th>
252 </tr>
253 <tr>
254 <td valign="top"><code>ActivityTestCase</code></td>
255 <td valign="top"><p>This class can be used to write tests for a specific activity. An activity is launched in its <code>setUp()</code> method and finished with <code>tearDown</code>. If you write a test case that extends <code>ActivityTestCase</code>, you can write tests that access the activity using <code>getActivity()</code> and assume it has been set up properly.</p></td>
256 </tr>
257 <tr>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800258 <td valign="top"><code>ServiceTestCase</code></td>
259 <td valign="top">This test case provides a framework in which you can test Service classes in a controlled environment. It provides basic support for the lifecycle of a Service, and hooks by which you can inject various dependencies and control the environment in which your Service is tested.</td>
260 </tr>
261 <tr>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700262 <td valign="top"><code>SingleLaunchActivityTestCase</code></td>
263 <td valign="top">This class is similar to <code>ActivityTestCase</code> except that the activity is launched once per class instead of every time the test case calls setup. </td>
264 </tr>
265 <tr>
266 <td valign="top"><code>ProviderTestCase</code></td>
267 <td valign="top">This class is similar to <code>ActivityTestCase</code> except that it will setup, tear down, and provide access to the <code>Provider</code> of your choice.</td>
268 </tr>
269</table>
270
271
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800272<a name="androidInstrumentationFrameworkamCommand"></a><h3>Understanding the am Command</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700273
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800274<p>The am command is a command-line interface to the ActivityManager (see <a href="http://code.google.com/android/reference/android/app/ActivityManager.html">http://code.google.com/android/reference/android/app/ActivityManager.html</a> for details). <code>am</code> is used to start and instrument activities using the adb shell command, as shown in the snippet below:</p>
275<pre class="prettify">
276&gt; adb shell am
277usage: am [start|instrument]
278 am start [-a &lt;ACTION&gt;] [-d &lt;DATA_URI&gt;] [-t &lt;MIME_TYPE&gt;]
279 [-c &lt;CATEGORY&gt; [-c &lt;CATEGORY&gt;] ...]
280 [-e &lt;EXTRA_KEY&gt; &lt;EXTRA_VALUE&gt; [-e &lt;EXTRA_KEY&gt; &lt;EXTRA_VALUE&gt; ...]
281 [-n &lt;COMPONENT&gt;] [-D] [&lt;URI&gt;]
282 am instrument [-e &lt;ARG_NAME&gt; &lt;ARG_VALUE&gt;] [-p &lt;PROF_FILE&gt;]
283 [-w] &lt;COMPONENT&gt;
284For example, to start the Contacts application you can use
285&gt; adb shell am start -n com.google.android.contacts/.ContactsActivity
286</pre>
287
288
289<a name="androidInstrumentationFrameworkPlatform"></a><h2>Platform Test Suites</h2>
290
291<p>This section provides an overview for various unit and functional test cases that can be executed through the instrumentation framework.</p>
292
293
294<a name="androidTestingPlatformFramework"></a><h3>Framework Tests</h3>
295
296<p>Framework test cases test the Android application framework or specific Android application functionality that requires an Android runtime context. These tests can be found in <code>//device/tests</code> and <code>//device/apps/AndroidTests</code>.</p>
297
298
299<a name="androidTestingPlatformCoreLibrary"></a><h3>Core Library</h3>
300
301<p>Core library test cases test the Android library functionality that does not require an Android runtime context. These tests are split into Android library (android.* package space) tests at <code>//device/java/tests</code> and Java library (java.*, javax.*, etc. packages) tests at <code>//device/dalvik/libcore/.../tests</code>.</p>
302
303
304<a name="androidInstrumentationFrameworkWritingRunning"></a><h2>Running Tests</h2>
305
306<p>Each instrumentation test case is similar to an Android application with the distinction that it starts another application. For example, have a look in the <code>tests/Contacts</code> directory. </p>
307<ul>
308 <li> There should be a Makefile and an Android Manifest file. </li>
309 <li> Tests are located in <code>tests/Contacts/src/com/google/android/contactstests</code>. </li>
310 <li> The Instrumentation Test Runner is located at <code>tests/Contacts/src/com/google/android/contactstests/functional/ContactsInstrumentationTestRunner.java</code>.</li>
311</ul>
312<p>Suppose you have a makefile with <code>Contactstests</code> as the target. </p>
313<ul>
314 <li> <code>make Contactstests</code>: Compiles the test cases. </li>
315 <li> <code>adb install Contactstests.apk</code>: Installs the apk on the device. </li>
316 <li> Use the adb shell <code>am</code> command to run them. </li>
317</ul>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700318<p> To run your tests, use the <code>am instrument</code> command with your <code>InstrumentationTestRunner</code> as its argument. Results are printed as a result of the instrumentation. For example, the following snippet displays the output after running the framework tests with one test failing (note the unusual syntax caused by how instrumentations are run via <code>am</code>):</p>
319<pre class="prettify">
320$ adb shell am instrument -w com.google.android.frameworktest/.tests.FrameworkInstrumentationTestRunner
321INSTRUMENTATION_RESULT: test results:=.......F.......
322Time: 6.837
323There was 1 failure:
3241) testSetUpConditions(com.google.android.frameworktest.tests.focus.RequestFocusTest)junit.framework.AssertionFailedError: requestFocus() should work from onCreate.
325 at com.google.android.frameworktest.tests.focus.RequestFocusTest.testSetUpConditions(RequestFocusTest.java:66)
326 at java.lang.reflect.Method.invokeNative(Native Method)
327 at android.test.InstrumentationTestSuite.runTest(InstrumentationTestSuite.java:73)
328 at android.test.InstrumentationTestSuite.runTest(InstrumentationTestSuite.java:73)
329 at android.test.InstrumentationTestRunner.onStart(InstrumentationTestRunner.java:151)
330 at android.app.Instrumentation$InstrumentationThread.run(Instrumentation.java:1088)
331
332FAILURES!!!
333Tests run: 14, Failures: 1, Errors: 0
334
335&lt;RETURN&gt; to continue
336
337INSTRUMENTATION_CODE: -1
338$
339</pre>
340
341
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800342<a name="androidInstrumentationTestingRunningAll"></a><h3>All Tests with Default TestRunner behavior</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700343
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800344<p>If no class or package is passed in to run, InstrumentationTestRunner will automatically find and run all tests under the package of the test application (as defined by the <code>android:targetPackage</code> attribute of the instrumentation defined in its manifest file).
345</p>
346<pre>
347$ adb shell am instrument -w \
348 com.android.samples.tests/android.test.InstrumentationTestRunner
349
350INSTRUMENTATION_RESULT: Test results for InstrumentationTestRunner=..........
351Time: 2.317
352
353OK (10 tests)
354
355
356INSTRUMENTATION_CODE: -1
The Android Open Source Project5c118522008-10-21 07:00:00 -0700357</pre>
358
359
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800360<a name="androidTestingTestSinglePakcage"></a><h3>Running all Tests Under Single Package</h3>
361
362<p>If you have many tests under one package, use the <code>-e package &lt;packagename&gt;</code> option to run all tests under that package without having to manually create a test suite.</p>
363<pre>
364$ adb shell am instrument -w \
365 -e package com.android.samples.view \
366 com.android.samples.tests/android.test.InstrumentationTestRunner
367INSTRUMENTATION_RESULT: Test results for InstrumentationTestRunner=........
368Time: 1.587
369
370OK (8 tests)
371</pre>
372
373
374<a name="androidTestingSingleTestSuite"></a><h3>Running a Single Test Suite</h3>
375
376<p>If you prefer to explicitly state which tests comprise all of your tests, you can define a test suite and run that directly. By convention, all test packages in your system should have at least one suite called <code>AllTests</code> (see <code>AllTests.java</code>). To run all of the tests using the <code>AllTests</code> suite for the api demos test app:</p>
377
378<pre>
379$ adb shell am instrument -w \
380 -e class com.android.samples.AllTests \
381 com.android.samples.tests/android.test.InstrumentationTestRunner
382
383INSTRUMENTATION_RESULT: Test results for AllTests=..........
384Time: 2.286
385
386OK (10 tests)
387
388
389INSTRUMENTATION_CODE: -1
390</pre>
391
392
The Android Open Source Project5c118522008-10-21 07:00:00 -0700393<a name="androidInstrumentationTestingRunningSingleTestCase"></a><h3>A Single Test Case</h3>
394
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800395<pre>
396$ adb shell am instrument -w \
397 -e class com.android.samples.view.Focus2ActivityTest \
398 com.android.samples.tests/android.test.InstrumentationTestRunner
399
400INSTRUMENTATION_RESULT: Test results for Focus2ActivityTest=....
401Time: 1.359
402
403OK (4 tests)
404
405
406INSTRUMENTATION_CODE: -1
407</pre>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700408
409
410<a name="androidInstrumentationTestingRunningSingleTest"></a><h3>A Single Test</h3>
411
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800412<pre>
413$ adb shell am instrument -w \
414 -e class com.android.samples.view.Focus2ActivityTest#testGoingLeftFromRightButtonGoesToCenter \
415 com.android.samples.tests/android.test.InstrumentationTestRunner
416
417INSTRUMENTATION_RESULT: Test results for Focus2ActivityTest=.
418Time: 0.51
419
420OK (1 test)
421
422
423INSTRUMENTATION_CODE: -1
424</pre>
425
426
427<a name="androidTestingDebugging"></a><h3>Attaching a debugger to your test</h3>
428
429<p>In order to debug your test code, instruct the controller to stop and wait for the debugger by adding <code>-e debug true</code> to your
430command line. This causes the test runner to stop and wait for the debugger just before calling your <code>setUp()</code> method. For example,</p>
431
432<pre>
433$ adb shell am instrument -w \
434 -e debug true \
435 com.android.samples.tests/android.test.InstrumentationTestRunner
436</pre>
437
438
439<a name="androidInstrumentationTestingCreating"></a><h2>Writing Tests</h2>
440
441<p>When writing tests, refer to the ApiDemos tests as models (located at <code>//device/samples/ApiDemos</code>). This section provides an overview of the test structure with ApiDemos.</p>
442
443
444<a name="androidTestingLocationFiles"></a><h3>Location of Files</h3>
445
446<p>Test packages should use the following structure and include <code>Android.mk</code>, <code>AndroidManifest.xml</code>, <code>AllTests.java</code>, and a src directory that mirrors the src directory of the tested application.</p>
447<p>Files are located within a <code>tests</code> directory found in the root directory:</p>
448<pre>
449$ find samples/ApiDemos/tests
450samples/ApiDemos/tests
451samples/ApiDemos/tests/Android.mk
452samples/ApiDemos/tests/AndroidManifest.xml
453samples/ApiDemos/tests/src
454samples/ApiDemos/tests/src/com
455samples/ApiDemos/tests/src/com/google
456samples/ApiDemos/tests/src/com/google/android
457samples/ApiDemos/tests/src/com/google/android/samples
458samples/ApiDemos/tests/src/com/google/android/samples/AllTests.java
459samples/ApiDemos/tests/src/com/google/android/samples/ApiDemosTest.java
460samples/ApiDemos/tests/src/com/google/android/samples/os
461samples/ApiDemos/tests/src/com/google/android/samples/os/MorseCodeConverterTest.java
462samples/ApiDemos/tests/src/com/google/android/samples/view
463samples/ApiDemos/tests/src/com/google/android/samples/view/Focus2ActivityTest.java
464samples/ApiDemos/tests/src/com/google/android/samples/view/Focus2AndroidTest.java
The Android Open Source Project5c118522008-10-21 07:00:00 -0700465</pre>
466
467
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800468<a name="androidTestingContentMakefile"></a><h3>Contents of makefile</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700469
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800470<p>The contents of the makefile are similar to a normal application with the addition of a <code>LOCAL_INSTRUMENTATION_FOR</code> declaration.<p />
471<pre>
472# Add appropriate copyright banner here
473LOCAL_PATH:= $(call my-dir)
474include $(CLEAR_VARS)
475
476# We only want this apk build for tests.
477LOCAL_MODULE_TAGS := tests
478
479# Include all test java files.
480LOCAL_SRC_FILES := $(call all-java-files-under, src)
481
482# Notice that we don't have to include the src files of ApiDemos because, by
483# running the tests using an instrumentation targeting ApiDemos, we
484# automatically get all of its classes loaded into our environment.
485
486LOCAL_PACKAGE_NAME := ApiDemosTests
487
488LOCAL_INSTRUMENTATION_FOR := ApiDemos
489
490include $(BUILD_PACKAGE)
491</pre>
492
493
494<a name="androidTestingContentManifest"></a><h3>Content of Manifest</h3>
495
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800496<p>Use the following example to create an <code>AndroidManifest.xml</code> file that declares the instrumentation. Specify that the framework supplied InstrumentationTestRunner targets the package of your application, allowing the tests that are run with the instrumentation to get access to all of the classes of your application without having to build the source into the test app. The name of the test application is typically the same as your target application with <code>.tests</code> appended. </p>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800497<pre>
498# Add appropriate copyright banner here
499&lt;manifest xmlns:android="http://schemas.android.com/apk/res/android"
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800500 package="com.example.android.apis.tests"&gt;
501
502 &lt;!-- We add an application tag here just so that we can indicate that
503 this package needs to link against the android.test library,
504 which is needed when building test cases. -->
505 &lt;application>
506 &lt;uses-library android:name="android.test.runner" />
507 &lt;/application>
508
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800509 &lt;!--
510 This declares that this app uses the instrumentation test runner targeting
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800511 the package of com.example.android.apis. To run the tests use the command:
512 "adb shell am instrument -w com.example.android.apis.tests/android.test.InstrumentationTestRunner"
513 -->
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800514 &lt;instrumentation android:name="android.test.InstrumentationTestRunner"
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800515 android:targetPackage="com.example.android.apis"
516 android:label="Tests for Api Demos."/>
517
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800518&lt;/manifest&gt;
519</pre>
520<p>&nbsp;</p>
521<p>The following snippet will prefix the <code>/android.test.InstrumentationTestRunner</code> when running tests from the command line:</p>
522<pre>
523$ adb shell am instrument -w \
524 com.android.samples.tests/android.test.InstrumentationTestRunner
525</pre>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700526
527
The Android Open Source Projecte3c57662009-02-10 15:43:58 -0800528<a name="androidInstrumentationTestingCreatingTestRunner"></a><h3>New InstrumentationTestRunner</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700529
530<p>Create a class that derives from this class. You must override two abstract methods; one that returns the class loader of the target package, and another that defines all of the tests within the package. For example, the snippet below displays the test runner for the framework tests.</p>
531<pre class="prettify">
532public class FrameworkInstrumentationTestRunner extends InstrumentationTestRunner {
533
534 @Override
535 public TestSuite getAllTests() {
536 InstrumentationTestSuite suite = new InstrumentationTestSuite(this);
537
538 suite.addTestSuite(FocusAfterRemovalTest.class);
539 suite.addTestSuite(RequestFocusTest.class);
540 suite.addTestSuite(RequestRectangleVisibleTest.class);
541 return suite;
542 }
543
544 @Override
545 public ClassLoader getLoader() {
546 return FrameworkInstrumentationTestRunner.class.getClassLoader();
547 }
548}
549</pre>
550<p> Next, in an appropriate <code>AndroidManifest.xml</code>, define the instrumentation for the derived class with the appropriate <code>android:targetPackage</code> set. For example, the snippet below defines the instrumentation runner for the framework tests.</p>
551<pre class="prettify">
The Android Open Source Project5c118522008-10-21 07:00:00 -0700552&lt;instrumentation android:name="android.tests.FrameworkInstrumentationTestRunner"
553 android:targetPackage="com.google.android.frameworktest"
554 android:label="framework instrumentation test runner" /&gt;
555</pre>
556
557
558<a name="androidInstrumentationTestingCreatingTestCase"></a><h3>New InstrumentationTestCase</h3>
559
560<p> To create a new test case, write a class that extends <code>InstrumentationTestCase</code> in the same application as your test runner. The following snippet illustrates an example <code>ActivityTestCase</code> that tests an activity named <code>MyActivity</code>.</p>
561<pre class="prettify">
562public class ButtonPressTest extends ActivityTestCase&lt;MyActivity&gt; {
563
564 Button mLeftButton;
565
566 public ButtonPressTest() {
567 super("com.example", MyActivity.class);
568 }
569
570 @Override
571 public void setUp() throws Exception {
572 super.setUp();
573 mLeftButton = (Button) getActivity().findViewById(R.id.leftButton);
574 }
575
576 public void testFocusMovesToRight() throws Exception {
577 assertTrue(mLeftButton.hasFocus());
578 getInstrumentation().sendCharacterSync(KeyEvent.KEYCODE_DPAD_RIGHT);
579
580 Button rightButton = (Button) getActivity().findViewById(R.id.rightButton);
581 assertTrue(rightButton.hasFocus());
582 }
583
584 // could have several more tests...
585}
586</pre>
587
588
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800589<a name="androidInstrumentationFrameworkTestCase"></a><h3>Exploring a Test Case</h3>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700590
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800591<p> The test case described in this section adds and tests a new Contact. Note that you can send intents, register intent receivers, etc. </p>
592<p><code>Instrumentation.java</code> has helper functions that send key events and strings, for example: </p>
593<ul>
594 <li><code>getInstrumentation()</code>: Returns the handle to the instrumentation </li>
595 <li><code>sendCharacterSync</code>: Sends a character. </li>
596 <li><code>sendStringSync</code>: Sends a string to an input box. </li>
597 <li><code>sendKeyDownUpSync</code>: Sends a specific keyevent. </li>
598 <li><code>sendTrackballEventSync</code>: Sends a trackball event.</li>
599</ul>
600<p> You can find the test case below at <code>device/tests/Contacts.</code></p>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700601<pre class="prettify">
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800602private void addNewContact(String name, int star, int phoneType, String number, String label,
603 String email, int emailType){
604 ContentValues values = new ContentValues();
605 Uri phoneUri = null;
606 Uri emailUri = null;
The Android Open Source Project5c118522008-10-21 07:00:00 -0700607
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800608 values.put(Contacts.People.NAME, name);
609 values.put(Contacts.People.STARRED, star);
The Android Open Source Project5c118522008-10-21 07:00:00 -0700610
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800611 //Add Phone Numbers
612 Uri uri = mActivity.getContentResolver().insert(Contacts.People.CONTENT_URI, values);
613 phoneUri = Uri.withAppendedPath(uri, Contacts.People.Phones.CONTENT_DIRECTORY);
614
615 values.clear();
616 values.put(Contacts.Phones.TYPE, phoneType);
617 values.put(Contacts.Phones.NUMBER, number);
618 values.put(Contacts.Phones.LABEL, label);
619 mActivity.getContentResolver().insert(phoneUri, values);
620
621 //Add Email
622 emailUri = Uri.withAppendedPath(uri, ContactMethods.CONTENT_DIRECTORY);
623
624 values.clear();
625 values.put(ContactMethods.KIND, Contacts.KIND_EMAIL);
626 values.put(ContactMethods.DATA, email);
627 values.put(ContactMethods.LABEL, "");
628 values.put(ContactMethods.TYPE, emailType);
629 mActivity.getContentResolver().insert(emailUri, values);
The Android Open Source Project5c118522008-10-21 07:00:00 -0700630}
631
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800632
633 public void testAddSaveSingleContact(){
634 int previousCount = mActivity.getListView().getCount();
635 String message;
636
637 addNewContact(INPUT_NAME_1 + "1", "5435754532", "1" + INPUT_EMAIL_1, CONFIRM_OPTION);
638
639 message = "Added 1 to initial length=" + previousCount + ", but resulted with a count=" +
640 mActivity.getListView().getCount();
641 assertEquals(message, ++previousCount, mActivity.getListView().getCount());
642
643 // Check Content; Name; Num; Starred
644 assertEquals(INPUT_NAME_1 + "1", getTextFromView(0, android.R.id.text1));
645 assertEquals("5435754532", getTextFromView(0, android.R.id.text2));
646
647 //Check email is saved
648 //cursor = returnEmailCursorAtId("1");
649 Uri uri = Uri.parse("content://contacts/people/1");
650 uri = Uri.withAppendedPath(uri, ContactMethods.CONTENT_DIRECTORY);
651 Cursor cursor = mActivity.getContentResolver().query(uri, CONTACTS_COLUMNS, null, null, null);
652 assertTrue("returnEmailCursorAtId: Moving cursor to first row has failed", cursor.first());
653
654 int dataIndex = cursor.getColumnIndexOrThrow("data");
655 assertEquals("1" + INPUT_EMAIL_1, cursor.getString(dataIndex));
656 cursor.deactivate();
The Android Open Source Project5c118522008-10-21 07:00:00 -0700657}
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800658 </pre>
659
660
661<a name="androidTestingKindsofTests"></a><h3>Deciding Kinds of Tests to Write</h3>
662
663<p>Once you are bootstrapped with your test application, you can start writing tests. There are three of types of tests you may wish to write:</p>
664<p><ul>
665<li> <strong>TestCase</strong>: The standard junit test case.
666</li>
667<li> <strong>AndroidTestCase</strong>: A test case with access to a Context object that is injected for you by the instrumentation test runner.
668</li>
669<li> <strong>InstrumentationTestCase</strong>: A test case with access to an Instrumentation, which can be used to launch activities, content providers, send key events, etc.
670</li>
671</ul>
672</p>
673<p>The API Demos test suite includes examples of all three styles and can be used as a guideline for writing each type of test.</p>
674<p>There are two utility classes available for the most common uses of InstrumentationTestCase: ActivityTestCase and ProviderTestCase. See their javadoc for more information.
675</p>
676
677
678<a name="androidInstrumentationFrameworkTroubleshooting"></a><h2>Troubleshooting</h2>
679
680<p>If you run your test cases and nothing appears to happen, have a look at <code>adb logcat</code>. The following is a common problem:</p>
681<pre class="prettify">
682I/dalvikvm( 688): threadid=11: attached from native, name=Binder Thread #1
683I/dalvikvm( 688): threadid=13: attached from native, name=Binder Thread #2
684W/ActivityManager( 469): Unable to find instrumentation info for: ComponentInfo{com.google.android.browser_instrumentation/com.google.android.browser_instrumentation.BrowserWebkitLayoutInstrumentation}
685D/AndroidRuntime( 688): Shutting down VM
686E/AndroidRuntime( 688): ERROR: thread attach failed
687</pre>
688<p>It's possible that the instrumentation apk isn't installed on your device or that the package name is incorrect in the Manifest file. </p>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700689
690
691<p><span class="lh2"><a name="androidFooter"></a></span>
692
693 </div>
694 </div>
695 <!-- end gc-pagecontent -->
696 </div>
697 <!-- end gooey wrapper -->
698 </div>
699 <!-- end codesearchresults -->
700 <div id="gc-footer" dir="ltr">
701 <div class="text"> &copy;2008 Google<!-- - <a href="/">Code Home</a> - <a href="http://www.google.com/accounts/TOS">Site Terms of Service</a> - <a href="http://www.google.com/privacy.html">Privacy Policy</a> - <a href="/more">Site Directory</a> --></div>
702 </div>
703 <!-- end gc-footer -->
704</div>
705<!-- end gc-containter -->
706<script src="http://www.google-analytics.com/ga.js" type="text/javascript">
707</script>
708<script type="text/javascript">
709 try {
710 var pageTracker = _gat._getTracker("UA-18071-1");
711 pageTracker._setAllowAnchor(true);
712 pageTracker._initData();
713 pageTracker._trackPageview();
714 } catch(e) {}
715</script>
The Android Open Source Projecte943f2f2008-12-17 18:04:04 -0800716<div id="jd-build-id"> v0.6 - 25 November 2008</div>
The Android Open Source Project5c118522008-10-21 07:00:00 -0700717</div></div></div></body>
718</html>
719