- add sources.
[platform/framework/web/crosswalk.git] / src / tools / telemetry / telemetry / unittest / run_tests.py
1 # Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 # Use of this source code is governed by a BSD-style license that can be
3 # found in the LICENSE file.
4 import logging
5 import unittest
6
7 from telemetry.core import browser_options
8 from telemetry.core import discover
9 from telemetry.core import util
10 from telemetry.unittest import gtest_testrunner
11 from telemetry.unittest import options_for_unittests
12
13 def Discover(start_dir, top_level_dir=None, pattern='test*.py'):
14   loader = unittest.defaultTestLoader
15   loader.suiteClass = gtest_testrunner.GTestTestSuite
16   subsuites = []
17
18   modules = discover.DiscoverModules(start_dir, top_level_dir, pattern)
19   for module in modules:
20     if hasattr(module, 'suite'):
21       new_suite = module.suite()
22     else:
23       new_suite = loader.loadTestsFromModule(module)
24     if new_suite.countTestCases():
25       subsuites.append(new_suite)
26   return gtest_testrunner.GTestTestSuite(subsuites)
27
28
29 def FilterSuite(suite, predicate):
30   new_suite = suite.__class__()
31   for x in suite:
32     if isinstance(x, unittest.TestSuite):
33       subsuite = FilterSuite(x, predicate)
34       if subsuite.countTestCases() == 0:
35         continue
36
37       new_suite.addTest(subsuite)
38       continue
39
40     assert isinstance(x, unittest.TestCase)
41     if predicate(x):
42       new_suite.addTest(x)
43
44   return new_suite
45
46
47 def DiscoverAndRunTests(
48     dir_name, args, top_level_dir,
49     runner=None, run_disabled_tests=False):
50   if not runner:
51     runner = gtest_testrunner.GTestTestRunner(inner=True)
52
53   suite = Discover(dir_name, top_level_dir, '*_unittest.py')
54
55   def IsTestSelected(test):
56     if len(args) != 0:
57       found = False
58       for name in args:
59         if name in test.id():
60           found = True
61       if not found:
62         return False
63
64     if hasattr(test, '_testMethodName'):
65       method = getattr(test, test._testMethodName) # pylint: disable=W0212
66       if hasattr(method, '_requires_browser_types'):
67         types = method._requires_browser_types # pylint: disable=W0212
68         if options_for_unittests.GetBrowserType() not in types:
69           logging.debug('Skipping test %s because it requires %s' %
70                         (test.id(), types))
71           return False
72       if hasattr(method, '_disabled_test'):
73         if not run_disabled_tests:
74           return False
75
76     return True
77
78   filtered_suite = FilterSuite(suite, IsTestSelected)
79   test_result = runner.run(filtered_suite)
80   return test_result
81
82
83 def RestoreLoggingLevel(func):
84   def _LoggingRestoreWrapper(*args, **kwargs):
85     # Cache the current logging level, this needs to be done before calling
86     # parser.parse_args, which changes logging level based on verbosity
87     # setting.
88     logging_level = logging.getLogger().getEffectiveLevel()
89     try:
90       return func(*args, **kwargs)
91     finally:
92       # Restore logging level, which may be changed in parser.parse_args.
93       logging.getLogger().setLevel(logging_level)
94
95   return _LoggingRestoreWrapper
96
97
98 @RestoreLoggingLevel
99 def Main(args, start_dir, top_level_dir, runner=None):
100   """Unit test suite that collects all test cases for telemetry."""
101   # Add unittest_data to the path so we can import packages from it.
102   util.AddDirToPythonPath(util.GetUnittestDataDir())
103
104   default_options = browser_options.BrowserFinderOptions()
105   default_options.browser_type = 'any'
106
107   parser = default_options.CreateParser('run_tests [options] [test names]')
108   parser.add_option('--repeat-count', dest='run_test_repeat_count',
109                     type='int', default=1,
110                     help='Repeats each a provided number of times.')
111   parser.add_option('-d', '--also-run-disabled-tests',
112                     dest='run_disabled_tests',
113                     action='store_true', default=False,
114                     help='Also run tests decorated with @DisabledTest.')
115
116   _, args = parser.parse_args(args)
117
118   if default_options.verbosity == 0:
119     logging.getLogger().setLevel(logging.WARN)
120
121   from telemetry.core import browser_finder
122   try:
123     browser_to_create = browser_finder.FindBrowser(default_options)
124   except browser_finder.BrowserFinderException, ex:
125     logging.error(str(ex))
126     return 1
127
128   if browser_to_create == None:
129     logging.error('No browser found of type %s. Cannot run tests.',
130                   default_options.browser_type)
131     logging.error('Re-run with --browser=list to see available browser types.')
132     return 1
133
134   options_for_unittests.Set(default_options,
135                             browser_to_create.browser_type)
136   try:
137     success = True
138     for _ in range(
139         default_options.run_test_repeat_count): # pylint: disable=E1101
140       success = success and DiscoverAndRunTests(
141         start_dir, args, top_level_dir,
142         runner, default_options.run_disabled_tests)
143     if success:
144       return 0
145   finally:
146     options_for_unittests.Set(None, None)
147
148   return 1