1 | // |
---|---|
2 | // TestResult.h |
3 | // |
4 | |
5 | |
6 | #ifndef Poco_CppUnit_TestResult_INCLUDED |
7 | #define Poco_CppUnit_TestResult_INCLUDED |
8 | |
9 | |
10 | #include "Poco/CppUnit/CppUnit.h" |
11 | #include "Poco/CppUnit/Guards.h" |
12 | #include "Poco/CppUnit/TestFailure.h" |
13 | #include <vector> |
14 | |
15 | |
16 | namespace CppUnit { |
17 | |
18 | |
19 | class CppUnitException; |
20 | class Test; |
21 | |
22 | |
23 | /* |
24 | * A TestResult collects the results of executing a test case. It is an |
25 | * instance of the Collecting Parameter pattern. |
26 | * |
27 | * The test framework distinguishes between failures and errors. |
28 | * A failure is anticipated and checked for with assertions. Errors are |
29 | * unanticipated problems signified by exceptions that are not generated |
30 | * by the framework. |
31 | * |
32 | * TestResult supplies a template method 'setSynchronizationObject ()' |
33 | * so that subclasses can provide mutual exclusion in the face of multiple |
34 | * threads. This can be useful when tests execute in one thread and |
35 | * they fill a subclass of TestResult which effects change in another |
36 | * thread. To have mutual exclusion, override setSynchronizationObject () |
37 | * and make sure that you create an instance of ExclusiveZone at the |
38 | * beginning of each method. |
39 | * |
40 | * see Test |
41 | */ |
42 | class CppUnit_API TestResult |
43 | { |
44 | REFERENCEOBJECT (TestResult) |
45 | |
46 | public: |
47 | TestResult(); |
48 | virtual ~TestResult(); |
49 | |
50 | virtual void addError(Test* test, CppUnitException* e); |
51 | virtual void addFailure(Test* test, CppUnitException* e); |
52 | virtual void startTest(Test* test); |
53 | virtual void endTest(Test* test); |
54 | virtual int runTests(); |
55 | virtual int testErrors(); |
56 | virtual int testFailures(); |
57 | virtual bool wasSuccessful(); |
58 | virtual bool shouldStop(); |
59 | virtual void stop(); |
60 | |
61 | virtual std::vector<TestFailure*>& errors(); |
62 | virtual std::vector<TestFailure*>& failures(); |
63 | |
64 | class SynchronizationObject |
65 | { |
66 | public: |
67 | SynchronizationObject() |
68 | { |
69 | } |
70 | |
71 | virtual ~SynchronizationObject() |
72 | { |
73 | } |
74 | |
75 | virtual void lock() |
76 | { |
77 | } |
78 | |
79 | virtual void unlock() |
80 | { |
81 | } |
82 | }; |
83 | |
84 | class ExclusiveZone |
85 | { |
86 | SynchronizationObject* m_syncObject; |
87 | |
88 | public: |
89 | ExclusiveZone(SynchronizationObject* syncObject): m_syncObject(syncObject) |
90 | { |
91 | m_syncObject->lock(); |
92 | } |
93 | |
94 | ~ExclusiveZone() |
95 | { |
96 | m_syncObject->unlock(); |
97 | } |
98 | }; |
99 | |
100 | protected: |
101 | virtual void setSynchronizationObject(SynchronizationObject* syncObject); |
102 | |
103 | std::vector<TestFailure*> _errors; |
104 | std::vector<TestFailure*> _failures; |
105 | int _runTests; |
106 | bool _stop; |
107 | SynchronizationObject* _syncObject; |
108 | |
109 | }; |
110 | |
111 | |
112 | // Construct a TestResult |
113 | inline TestResult::TestResult(): _syncObject(new SynchronizationObject()) |
114 | { |
115 | _runTests = 0; |
116 | _stop = false; |
117 | } |
118 | |
119 | |
120 | // Adds an error to the list of errors. The passed in exception |
121 | // caused the error |
122 | inline void TestResult::addError(Test* test, CppUnitException* e) |
123 | { |
124 | ExclusiveZone zone(_syncObject); |
125 | _errors.push_back(new TestFailure(test, e)); |
126 | } |
127 | |
128 | |
129 | // Adds a failure to the list of failures. The passed in exception |
130 | // caused the failure. |
131 | inline void TestResult::addFailure(Test* test, CppUnitException* e) |
132 | { |
133 | ExclusiveZone zone(_syncObject); |
134 | _failures.push_back(new TestFailure(test, e)); |
135 | } |
136 | |
137 | |
138 | // Informs the result that a test will be started. |
139 | inline void TestResult::startTest(Test* /*test*/) |
140 | { |
141 | ExclusiveZone zone(_syncObject); |
142 | _runTests++; |
143 | } |
144 | |
145 | |
146 | // Informs the result that a test was completed. |
147 | inline void TestResult::endTest(Test* /*test*/) |
148 | { |
149 | ExclusiveZone zone(_syncObject); |
150 | } |
151 | |
152 | |
153 | // Gets the number of run tests. |
154 | inline int TestResult::runTests() |
155 | { |
156 | ExclusiveZone zone(_syncObject); |
157 | return _runTests; |
158 | } |
159 | |
160 | |
161 | // Gets the number of detected errors. |
162 | inline int TestResult::testErrors() |
163 | { |
164 | ExclusiveZone zone(_syncObject); |
165 | return (int) _errors.size(); |
166 | } |
167 | |
168 | |
169 | // Gets the number of detected failures. |
170 | inline int TestResult::testFailures() |
171 | { |
172 | ExclusiveZone zone(_syncObject); |
173 | return (int) _failures.size(); |
174 | } |
175 | |
176 | |
177 | // Returns whether the entire test was successful or not. |
178 | inline bool TestResult::wasSuccessful() |
179 | { |
180 | ExclusiveZone zone(_syncObject); |
181 | return _failures.size() == 0 && _errors.size () == 0; |
182 | } |
183 | |
184 | |
185 | // Returns a std::vector of the errors. |
186 | inline std::vector<TestFailure*>& TestResult::errors() |
187 | { |
188 | ExclusiveZone zone(_syncObject); |
189 | return _errors; |
190 | } |
191 | |
192 | |
193 | // Returns a std::vector of the failures. |
194 | inline std::vector<TestFailure*>& TestResult::failures() |
195 | { |
196 | ExclusiveZone zone(_syncObject); |
197 | return _failures; |
198 | } |
199 | |
200 | |
201 | // Returns whether testing should be stopped |
202 | inline bool TestResult::shouldStop() |
203 | { |
204 | ExclusiveZone zone(_syncObject); |
205 | return _stop; |
206 | } |
207 | |
208 | |
209 | // Stop testing |
210 | inline void TestResult::stop() |
211 | { |
212 | ExclusiveZone zone(_syncObject); |
213 | _stop = true; |
214 | } |
215 | |
216 | |
217 | // Accept a new synchronization object for protection of this instance |
218 | // TestResult assumes ownership of the object |
219 | inline void TestResult::setSynchronizationObject(SynchronizationObject* syncObject) |
220 | { |
221 | delete _syncObject; |
222 | _syncObject = syncObject; |
223 | } |
224 | |
225 | |
226 | } // namespace CppUnit |
227 | |
228 | |
229 | #endif // Poco_CppUnit_TestResult_INCLUDED |
230 |