- add sources.
[platform/framework/web/crosswalk.git] / src / build / util / lib / common / unittest_util.py
1 # Copyright 2013 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
5 """Utilities for dealing with the python unittest module."""
6
7 import fnmatch
8 import sys
9 import unittest
10
11
12 class _TextTestResult(unittest._TextTestResult):
13   """A test result class that can print formatted text results to a stream.
14
15   Results printed in conformance with gtest output format, like:
16   [ RUN        ] autofill.AutofillTest.testAutofillInvalid: "test desc."
17   [         OK ] autofill.AutofillTest.testAutofillInvalid
18   [ RUN        ] autofill.AutofillTest.testFillProfile: "test desc."
19   [         OK ] autofill.AutofillTest.testFillProfile
20   [ RUN        ] autofill.AutofillTest.testFillProfileCrazyCharacters: "Test."
21   [         OK ] autofill.AutofillTest.testFillProfileCrazyCharacters
22   """
23   def __init__(self, stream, descriptions, verbosity):
24     unittest._TextTestResult.__init__(self, stream, descriptions, verbosity)
25     self._fails = set()
26
27   def _GetTestURI(self, test):
28     return '%s.%s.%s' % (test.__class__.__module__,
29                          test.__class__.__name__,
30                          test._testMethodName)
31
32   def getDescription(self, test):
33     return '%s: "%s"' % (self._GetTestURI(test), test.shortDescription())
34
35   def startTest(self, test):
36     unittest.TestResult.startTest(self, test)
37     self.stream.writeln('[ RUN        ] %s' % self.getDescription(test))
38
39   def addSuccess(self, test):
40     unittest.TestResult.addSuccess(self, test)
41     self.stream.writeln('[         OK ] %s' % self._GetTestURI(test))
42
43   def addError(self, test, err):
44     unittest.TestResult.addError(self, test, err)
45     self.stream.writeln('[      ERROR ] %s' % self._GetTestURI(test))
46     self._fails.add(self._GetTestURI(test))
47
48   def addFailure(self, test, err):
49     unittest.TestResult.addFailure(self, test, err)
50     self.stream.writeln('[     FAILED ] %s' % self._GetTestURI(test))
51     self._fails.add(self._GetTestURI(test))
52
53   def getRetestFilter(self):
54     return ':'.join(self._fails)
55
56
57 class TextTestRunner(unittest.TextTestRunner):
58   """Test Runner for displaying test results in textual format.
59
60   Results are displayed in conformance with google test output.
61   """
62
63   def __init__(self, verbosity=1):
64     unittest.TextTestRunner.__init__(self, stream=sys.stderr,
65                                      verbosity=verbosity)
66
67   def _makeResult(self):
68     return _TextTestResult(self.stream, self.descriptions, self.verbosity)
69
70
71 def GetTestsFromSuite(suite):
72   """Returns all the tests from a given test suite."""
73   tests = []
74   for x in suite:
75     if isinstance(x, unittest.TestSuite):
76       tests += GetTestsFromSuite(x)
77     else:
78       tests += [x]
79   return tests
80
81
82 def GetTestNamesFromSuite(suite):
83   """Returns a list of every test name in the given suite."""
84   return map(lambda x: GetTestName(x), GetTestsFromSuite(suite))
85
86
87 def GetTestName(test):
88   """Gets the test name of the given unittest test."""
89   return '.'.join([test.__class__.__module__,
90                    test.__class__.__name__,
91                    test._testMethodName])
92
93
94 def FilterTestSuite(suite, gtest_filter):
95   """Returns a new filtered tests suite based on the given gtest filter.
96
97   See http://code.google.com/p/googletest/wiki/AdvancedGuide
98   for gtest_filter specification.
99   """
100   return unittest.TestSuite(FilterTests(GetTestsFromSuite(suite), gtest_filter))
101
102
103 def FilterTests(all_tests, gtest_filter):
104   """Filter a list of tests based on the given gtest filter.
105
106   Args:
107     all_tests: List of tests (unittest.TestSuite)
108     gtest_filter: Filter to apply.
109
110   Returns:
111     Filtered subset of the given list of tests.
112   """
113   test_names = [GetTestName(test) for test in all_tests]
114   filtered_names = FilterTestNames(test_names, gtest_filter)
115   return [test for test in all_tests if GetTestName(test) in filtered_names]
116
117
118 def FilterTestNames(all_tests, gtest_filter):
119   """Filter a list of test names based on the given gtest filter.
120
121   See http://code.google.com/p/googletest/wiki/AdvancedGuide
122   for gtest_filter specification.
123
124   Args:
125     all_tests: List of test names.
126     gtest_filter: Filter to apply.
127
128   Returns:
129     Filtered subset of the given list of test names.
130   """
131   pattern_groups = gtest_filter.split('-')
132   positive_patterns = pattern_groups[0].split(':')
133   negative_patterns = None
134   if len(pattern_groups) > 1:
135     negative_patterns = pattern_groups[1].split(':')
136
137   tests = []
138   for test in all_tests:
139     # Test name must by matched by one positive pattern.
140     for pattern in positive_patterns:
141       if fnmatch.fnmatch(test, pattern):
142         break
143     else:
144       continue
145     # Test name must not be matched by any negative patterns.
146     for pattern in negative_patterns or []:
147       if fnmatch.fnmatch(test, pattern):
148         break
149     else:
150       tests += [test]
151   return tests