1import sys
2import warnings
3
4import unittest2
5
6
7def resultFactory(*_):
8    return unittest2.TestResult()
9
10class OldTestResult(object):
11    """An object honouring TestResult before startTestRun/stopTestRun."""
12
13    def __init__(self, *_):
14        self.failures = []
15        self.errors = []
16        self.testsRun = 0
17        self.shouldStop = False
18
19    def startTest(self, test):
20        pass
21
22    def stopTest(self, test):
23        pass
24
25    def addError(self, test, err):
26        self.errors.append((test, err))
27
28    def addFailure(self, test, err):
29        self.failures.append((test, err))
30
31    def addSuccess(self, test):
32        pass
33
34    def wasSuccessful(self):
35        return True
36
37    def printErrors(self):
38        pass
39
40class LoggingResult(unittest2.TestResult):
41    def __init__(self, log):
42        self._events = log
43        super(LoggingResult, self).__init__()
44
45    def startTest(self, test):
46        self._events.append('startTest')
47        super(LoggingResult, self).startTest(test)
48
49    def startTestRun(self):
50        self._events.append('startTestRun')
51        super(LoggingResult, self).startTestRun()
52
53    def stopTest(self, test):
54        self._events.append('stopTest')
55        super(LoggingResult, self).stopTest(test)
56
57    def stopTestRun(self):
58        self._events.append('stopTestRun')
59        super(LoggingResult, self).stopTestRun()
60
61    def addFailure(self, *args):
62        self._events.append('addFailure')
63        super(LoggingResult, self).addFailure(*args)
64
65    def addSuccess(self, *args):
66        self._events.append('addSuccess')
67        super(LoggingResult, self).addSuccess(*args)
68
69    def addError(self, *args):
70        self._events.append('addError')
71        super(LoggingResult, self).addError(*args)
72
73    def addSkip(self, *args):
74        self._events.append('addSkip')
75        super(LoggingResult, self).addSkip(*args)
76
77    def addExpectedFailure(self, *args):
78        self._events.append('addExpectedFailure')
79        super(LoggingResult, self).addExpectedFailure(*args)
80
81    def addUnexpectedSuccess(self, *args):
82        self._events.append('addUnexpectedSuccess')
83        super(LoggingResult, self).addUnexpectedSuccess(*args)
84
85
86class EqualityMixin(object):
87    """Used as a mixin for TestCase"""
88
89    # Check for a valid __eq__ implementation
90    def test_eq(self):
91        for obj_1, obj_2 in self.eq_pairs:
92            self.assertEqual(obj_1, obj_2)
93            self.assertEqual(obj_2, obj_1)
94
95    # Check for a valid __ne__ implementation
96    def test_ne(self):
97        for obj_1, obj_2 in self.ne_pairs:
98            self.assertNotEqual(obj_1, obj_2)
99            self.assertNotEqual(obj_2, obj_1)
100
101class HashingMixin(object):
102    """Used as a mixin for TestCase"""
103
104    # Check for a valid __hash__ implementation
105    def test_hash(self):
106        for obj_1, obj_2 in self.eq_pairs:
107            try:
108                if not hash(obj_1) == hash(obj_2):
109                    self.fail("%r and %r do not hash equal" % (obj_1, obj_2))
110            except KeyboardInterrupt:
111                raise
112            except Exception, e:
113                self.fail("Problem hashing %r and %r: %s" % (obj_1, obj_2, e))
114
115        for obj_1, obj_2 in self.ne_pairs:
116            try:
117                if hash(obj_1) == hash(obj_2):
118                    self.fail("%s and %s hash equal, but shouldn't" %
119                              (obj_1, obj_2))
120            except KeyboardInterrupt:
121                raise
122            except Exception, e:
123                self.fail("Problem hashing %s and %s: %s" % (obj_1, obj_2, e))
124
125
126
127# copied from Python 2.6
128try:
129    from warnings import catch_warnings
130except ImportError:
131    class catch_warnings(object):
132        def __init__(self, record=False, module=None):
133            self._record = record
134            self._module = sys.modules['warnings']
135            self._entered = False
136
137        def __repr__(self):
138            args = []
139            if self._record:
140                args.append("record=True")
141            name = type(self).__name__
142            return "%s(%s)" % (name, ", ".join(args))
143
144        def __enter__(self):
145            if self._entered:
146                raise RuntimeError("Cannot enter %r twice" % self)
147            self._entered = True
148            self._filters = self._module.filters
149            self._module.filters = self._filters[:]
150            self._showwarning = self._module.showwarning
151            if self._record:
152                log = []
153                def showwarning(*args, **kwargs):
154                    log.append(WarningMessage(*args, **kwargs))
155                self._module.showwarning = showwarning
156                return log
157            else:
158                return None
159
160        def __exit__(self, *exc_info):
161            if not self._entered:
162                raise RuntimeError("Cannot exit %r without entering first" % self)
163            self._module.filters = self._filters
164            self._module.showwarning = self._showwarning
165
166    class WarningMessage(object):
167        _WARNING_DETAILS = ("message", "category", "filename", "lineno", "file",
168                            "line")
169        def __init__(self, message, category, filename, lineno, file=None,
170                        line=None):
171            local_values = locals()
172            for attr in self._WARNING_DETAILS:
173                setattr(self, attr, local_values[attr])
174            self._category_name = None
175            if category.__name__:
176                self._category_name = category.__name__
177
178