Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 1 | #!/usr/bin/python |
| 2 | # |
| 3 | # |
| 4 | # Copyright 2011, The Android Open Source Project |
| 5 | # |
| 6 | # Licensed under the Apache License, Version 2.0 (the "License"); |
| 7 | # you may not use this file except in compliance with the License. |
| 8 | # You may obtain a copy of the License at |
| 9 | # |
| 10 | # http://www.apache.org/licenses/LICENSE-2.0 |
| 11 | # |
| 12 | # Unless required by applicable law or agreed to in writing, software |
| 13 | # distributed under the License is distributed on an "AS IS" BASIS, |
| 14 | # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 15 | # See the License for the specific language governing permissions and |
| 16 | # limitations under the License. |
| 17 | |
| 18 | """TestSuite for running C/C++ Android tests using gtest framework.""" |
| 19 | |
| 20 | # python imports |
| 21 | import os |
| 22 | import re |
| 23 | |
| 24 | # local imports |
| 25 | import logger |
| 26 | import run_command |
| 27 | import test_suite |
| 28 | |
| 29 | |
| 30 | class GTestSuite(test_suite.AbstractTestSuite): |
| 31 | """A test suite for running gtest on device.""" |
| 32 | |
| 33 | def __init__(self): |
| 34 | test_suite.AbstractTestSuite.__init__(self) |
| 35 | self._target_exec_path = None |
| 36 | |
| 37 | def GetTargetExecPath(self): |
| 38 | """Get the target path to gtest executable.""" |
| 39 | return self._target_exec_path |
| 40 | |
| 41 | def SetTargetExecPath(self, path): |
| 42 | self._target_exec_path = path |
| 43 | return self |
| 44 | |
| 45 | def Run(self, options, adb): |
| 46 | """Run the provided gtest test suite. |
| 47 | |
| 48 | Args: |
| 49 | options: command line options |
| 50 | adb: adb interface |
| 51 | """ |
Jonathan Basseri | f6051de | 2017-09-15 17:03:10 -0700 | [diff] [blame] | 52 | |
| 53 | test_class = "*" |
| 54 | test_method = "*" |
| 55 | if options.test_class is not None: |
| 56 | test_class = options.test_class.lstrip() |
| 57 | if options.test_method is not None: |
| 58 | test_method = options.test_method.lstrip() |
| 59 | filter_arg = "" |
| 60 | if test_class != "*" or test_method != "*": |
| 61 | filter_arg = "--gtest_filter=%s.%s" % (test_class, test_method) |
| 62 | |
| 63 | shell_cmd = adb.PreviewShellCommand( |
| 64 | " ".join((self.GetTargetExecPath(), filter_arg))) |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 65 | logger.Log(shell_cmd) |
| 66 | if not options.preview: |
| 67 | # gtest will log to test results to stdout, so no need to do any |
| 68 | # extra processing |
| 69 | run_command.RunCommand(shell_cmd, return_output=False) |
| 70 | |
| 71 | |
| 72 | class GTestFactory(test_suite.AbstractTestFactory): |
| 73 | |
Brett Chabot | b0fd2cf | 2011-08-01 16:11:43 -0700 | [diff] [blame] | 74 | def __init__(self, test_root_path, build_path): |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 75 | test_suite.AbstractTestFactory.__init__(self, test_root_path, |
Brett Chabot | b0fd2cf | 2011-08-01 16:11:43 -0700 | [diff] [blame] | 76 | build_path) |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 77 | |
| 78 | def CreateTests(self, sub_tests_path=None): |
| 79 | """Create tests found in sub_tests_path. |
| 80 | |
| 81 | Looks for test files matching a pattern, and assumes each one is a separate |
| 82 | binary on target. |
| 83 | |
| 84 | Test files must match one of the following pattern: |
| 85 | - test_*.[c|cc|cpp] |
| 86 | - *_test.[c|cc|cpp] |
| 87 | - *_unittest.[c|cc|cpp] |
Igor Murashkin | f9cfbd3 | 2014-01-23 18:48:17 -0800 | [diff] [blame] | 88 | - *Tests.[cc|cpp] |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 89 | |
| 90 | """ |
| 91 | if not sub_tests_path: |
| 92 | sub_tests_path = self.GetTestRootPath() |
| 93 | test_file_list = [] |
| 94 | if os.path.isfile(sub_tests_path): |
| 95 | self._EvaluateFile(test_file_list, os.path.basename(sub_tests_path)) |
| 96 | else: |
| 97 | os.path.walk(sub_tests_path, self._CollectTestSources, test_file_list) |
| 98 | # TODO: obtain this from makefile instead of hardcoding |
| 99 | target_root_path = os.path.join('/data', 'nativetest') |
| 100 | test_suites = [] |
| 101 | for test_file in test_file_list: |
| 102 | logger.SilentLog('Creating gtest suite for file %s' % test_file) |
| 103 | suite = GTestSuite() |
| 104 | suite.SetBuildPath(self.GetBuildPath()) |
Brett Chabot | e607d3a | 2013-05-16 23:00:43 -0700 | [diff] [blame] | 105 | # expect tests in /data/nativetest/test_file/test_file |
| 106 | suite.SetTargetExecPath(os.path.join(target_root_path, test_file, test_file)) |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 107 | test_suites.append(suite) |
| 108 | return test_suites |
| 109 | |
| 110 | def _CollectTestSources(self, test_list, dirname, files): |
| 111 | """For each directory, find tests source file and add them to the list. |
| 112 | |
| 113 | Test files must match one of the following pattern: |
| 114 | - test_*.[cc|cpp] |
| 115 | - *_test.[cc|cpp] |
| 116 | - *_unittest.[cc|cpp] |
Igor Murashkin | f9cfbd3 | 2014-01-23 18:48:17 -0800 | [diff] [blame] | 117 | - *Tests.[cc|cpp] |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 118 | |
| 119 | This method is a callback for os.path.walk. |
| 120 | |
| 121 | Args: |
| 122 | test_list: Where new tests should be inserted. |
| 123 | dirname: Current directory. |
| 124 | files: List of files in the current directory. |
| 125 | """ |
| 126 | for f in files: |
| 127 | self._EvaluateFile(test_list, f) |
| 128 | |
| 129 | def _EvaluateFile(self, test_list, file): |
| 130 | (name, ext) = os.path.splitext(file) |
| 131 | if ext == ".cc" or ext == ".cpp" or ext == ".c": |
Igor Murashkin | f9cfbd3 | 2014-01-23 18:48:17 -0800 | [diff] [blame] | 132 | if re.search("_test$|_test_$|_unittest$|_unittest_$|^test_|Tests$", name): |
Brett Chabot | bb5918e | 2011-06-17 17:07:12 -0700 | [diff] [blame] | 133 | logger.SilentLog("Found native test file %s" % file) |
| 134 | test_list.append(name) |