Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(422)

Side by Side Diff: build/android/pylib/host_driven/instrumentation_test_case.py

Issue 19537004: [Android] Converts host driven tests to common test_dispatcher (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@sharding_refactoring
Patch Set: Several minor changes to variable names / comments Created 7 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 # Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 # Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be 2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file. 3 # found in the LICENSE file.
4 4
5 """Base class for Android Python-driven tests. 5 """Base class for host-driven instrumentation tests.
6 6
7 This test case is intended to serve as the base class for any Python-driven 7 This test case serves as the base class for any host-driven instrumentation
8 tests. It is similar to the Python unitttest module in that the user's tests 8 tests. The test method will call _RunJavaTests to run some instrumentation
9 inherit from this case and add their tests in that case. 9 tests, each one on a unique instrumentation TestRunner object.
frankf 2013/07/25 01:24:21 Still not there: Each test method in the derived
gkanwar1 2013/07/25 21:15:41 Done.
10
11 When a PythonTestBase object is instantiated, its purpose is to run only one of
12 its tests. The test runner gives it the name of the test the instance will
13 run. The test runner calls SetUp with the Android device ID which the test will
14 run against. The runner runs the test method itself, collecting the result,
15 and calls TearDown.
16
17 Tests can basically do whatever they want in the test methods, such as call
18 Java tests using _RunJavaTests. Those methods have the advantage of massaging
19 the Java test results into Python test results.
20 """ 10 """
21 11
22 import logging
23 import os 12 import os
24 import time 13 import time
25 14
26 from pylib import android_commands
27 from pylib.base import base_test_result 15 from pylib.base import base_test_result
28 from pylib.instrumentation import test_package 16 from pylib.instrumentation import test_package
29 from pylib.instrumentation import test_result 17 from pylib.instrumentation import test_result
30 from pylib.instrumentation import test_runner 18 from pylib.instrumentation import test_runner
31 19
20 import test_case
32 21
33 # aka the parent of com.google.android 22 # aka the parent of com.google.android
34 BASE_ROOT = 'src' + os.sep 23 BASE_ROOT = 'src' + os.sep
35 24
36 25
37 class PythonTestBase(object): 26 class InstrumentationHostDrivenTestCase(test_case.HostDrivenTestCase):
38 """Base class for Python-driven tests.""" 27 """Base class for host-driven instrumentation tests.
39 28
40 def __init__(self, test_name): 29 Raises:
41 # test_name must match one of the test methods defined on a subclass which 30 WaitForResponseTimedOutError: If timeout occurred while waiting for
42 # inherits from this class. 31 response to adb instrument command.
43 # It's stored so we can do the attr lookup on demand, allowing this class 32 DeviceUnresponsiveError: If device system process is not responding.
44 # to be pickled, a requirement for the multiprocessing module. 33 InstrumentationError: If instrumentation failed to run.
45 self.test_name = test_name 34 """
46 class_name = self.__class__.__name__
47 self.qualified_name = class_name + '.' + self.test_name
48 35
49 def SetUp(self, options): 36 def __init__(self, test_name, test_apk_path, test_apk_jar_path,
50 self.options = options 37 test_data, install_apk, save_perf_json, screenshot_failures,
51 self.shard_index = self.options.shard_index 38 tool, wait_for_debugger, disable_assertions):
52 self.device_id = self.options.device_id 39 """Create an InstrumentationHostDrivenTestCase object.
53 self.adb = android_commands.AndroidCommands(self.device_id)
54 self.ports_to_forward = []
55 40
56 def TearDown(self): 41 Args:
57 pass 42 test_name: The name of the method to run as the test.
43 test_apk_path: Path to the test apk file.
44 test_apk_jar_path: Path to the accompanying jar file.
45 other args: All passed through to the instrumentation test runner. See the
46 test runner docs for details.
47 """
58 48
59 def GetOutDir(self): 49 super(InstrumentationHostDrivenTestCase, self).__init__(test_name)
60 return os.path.join(os.environ['CHROME_SRC'], 'out', 50 self.test_apk_path = test_apk_path
61 self.options.build_type) 51 self.test_apk_jar_path = test_apk_jar_path
62 52 self.test_data = test_data
63 def Run(self): 53 self.install_apk = install_apk
64 logging.warning('Running Python-driven test: %s', self.test_name) 54 self.save_perf_json = save_perf_json
65 return getattr(self, self.test_name)() 55 self.screenshot_failures = screenshot_failures
56 self.wait_for_debugger = wait_for_debugger
57 self.tool = tool
58 self.disable_assertions = disable_assertions
66 59
67 def _RunJavaTest(self, fname, suite, test): 60 def _RunJavaTest(self, fname, suite, test):
68 """Runs a single Java test with a Java TestRunner. 61 """Runs a single Java test with a Java TestRunner.
69 62
70 Args: 63 Args:
71 fname: filename for the test (e.g. foo/bar/baz/tests/FooTest.py) 64 fname: filename for the test (e.g. foo/bar/baz/tests/FooTest.py)
72 suite: name of the Java test suite (e.g. FooTest) 65 suite: name of the Java test suite (e.g. FooTest)
73 test: name of the test method to run (e.g. testFooBar) 66 test: name of the test method to run (e.g. testFooBar)
74 67
75 Returns: 68 Returns:
76 TestRunResults object with a single test result. 69 TestRunResults object with a single test result.
77 """ 70 """
78 test = self._ComposeFullTestName(fname, suite, test) 71 test = self._ComposeFullTestName(fname, suite, test)
79 test_pkg = test_package.TestPackage( 72 test_pkg = test_package.TestPackage(
80 self.options.test_apk_path, self.options.test_apk_jar_path) 73 self.test_apk_path, self.test_apk_jar_path)
81 java_test_runner = test_runner.TestRunner(self.options.build_type, 74 java_test_runner = test_runner.TestRunner(self.build_type,
82 self.options.test_data, 75 self.test_data,
83 self.options.install_apk, 76 self.install_apk,
84 self.options.save_perf_json, 77 self.save_perf_json,
85 self.options.screenshot_failures, 78 self.screenshot_failures,
86 self.options.tool, 79 self.tool,
87 self.options.wait_for_debugger, 80 self.wait_for_debugger,
88 self.options.disable_assertions, 81 self.disable_assertions,
89 self.options.push_deps, 82 self.push_deps,
90 self.options.cleanup_test_files, 83 self.cleanup_test_files,
91 self.device_id, 84 self.device_id,
92 self.shard_index, test_pkg, 85 self.shard_index, test_pkg, [])
93 self.ports_to_forward)
94 try: 86 try:
95 java_test_runner.SetUp() 87 java_test_runner.SetUp()
96 return java_test_runner.RunTest(test)[0] 88 return java_test_runner.RunTest(test)[0]
97 finally: 89 finally:
98 java_test_runner.TearDown() 90 java_test_runner.TearDown()
99 91
100 def _RunJavaTests(self, fname, tests): 92 def _RunJavaTests(self, fname, tests):
101 """Calls a list of tests and stops at the first test failure. 93 """Calls a list of tests and stops at the first test failure.
102 94
103 This method iterates until either it encounters a non-passing test or it 95 This method iterates until either it encounters a non-passing test or it
104 exhausts the list of tests. Then it returns the appropriate Python result. 96 exhausts the list of tests. Then it returns the appropriate overall result.
105 97
106 Args: 98 Args:
107 fname: filename for the Python test 99 fname: filename for the host-driven test
108 tests: a list of Java test names which will be run 100 tests: a list of Java test names which will be run
109 101
110 Returns: 102 Returns:
111 A TestRunResults object containing a result for this Python test. 103 A TestRunResults object containing an overall result for this set of Java
104 tests. If any Java tests do not pass, this is a fail overall.
112 """ 105 """
113 test_type = base_test_result.ResultType.PASS 106 test_type = base_test_result.ResultType.PASS
114 log = '' 107 log = ''
115 108
116 start_ms = int(time.time()) * 1000 109 start_ms = int(time.time()) * 1000
117 for test in tests: 110 for test in tests:
118 # We're only running one test at a time, so this TestRunResults object 111 # We're only running one test at a time, so this TestRunResults object
119 # will hold only one result. 112 # will hold only one result.
120 suite, test_name = test.split('.') 113 suite, test_name = test.split('.')
121 java_results = self._RunJavaTest(fname, suite, test_name) 114 java_result = self._RunJavaTest(fname, suite, test_name)
122 assert len(java_results.GetAll()) == 1 115 assert len(java_result.GetAll()) == 1
123 if not java_results.DidRunPass(): 116 if not java_result.DidRunPass():
124 result = java_results.GetNotPass().pop() 117 result = java_result.GetNotPass().pop()
125 log = result.GetLog() 118 log = result.GetLog()
126 test_type = result.GetType() 119 test_type = result.GetType()
127 break 120 break
128 duration_ms = int(time.time()) * 1000 - start_ms 121 duration_ms = int(time.time()) * 1000 - start_ms
129 122
130 python_results = base_test_result.TestRunResults() 123 overall_result = base_test_result.TestRunResults()
131 python_results.AddResult( 124 overall_result.AddResult(
132 test_result.InstrumentationTestResult( 125 test_result.InstrumentationTestResult(
133 self.qualified_name, test_type, start_ms, duration_ms, log=log)) 126 self.qualified_name, test_type, start_ms, duration_ms, log=log))
134 return python_results 127 return overall_result
135 128
136 def _ComposeFullTestName(self, fname, suite, test): 129 def _ComposeFullTestName(self, fname, test_case, method):
137 package_name = self._GetPackageName(fname) 130 """Composes a fully-qualified name for the test method."""
138 return package_name + '.' + suite + '#' + test
139
140 def _GetPackageName(self, fname):
141 """Extracts the package name from the test file path."""
142 dirname = os.path.dirname(fname) 131 dirname = os.path.dirname(fname)
143 package = dirname[dirname.rfind(BASE_ROOT) + len(BASE_ROOT):] 132 package = dirname[dirname.rfind(BASE_ROOT) + len(BASE_ROOT):]
144 return package.replace(os.sep, '.') 133 package_name = package.replace(os.sep, '.')
134 return package_name + '.' + test_case + '#' + method
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698