Merge branch 'master' of scm.dev.nokia.troll.no:qt/oslo-staging-1 into master-integration
[qt-netbsd.git] / src / testlib / qtestlogger.cpp
blob6c76388397ee4e4924875822c03d2534819a198d
1 /****************************************************************************
2 **
3 ** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: Nokia Corporation (qt-info@nokia.com)
6 **
7 ** This file is part of the QtTest module of the Qt Toolkit.
8 **
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** No Commercial Usage
11 ** This file contains pre-release code and may not be distributed.
12 ** You may use this file in accordance with the terms and conditions
13 ** contained in the Technology Preview License Agreement accompanying
14 ** this package.
16 ** GNU Lesser General Public License Usage
17 ** Alternatively, this file may be used under the terms of the GNU Lesser
18 ** General Public License version 2.1 as published by the Free Software
19 ** Foundation and appearing in the file LICENSE.LGPL included in the
20 ** packaging of this file. Please review the following information to
21 ** ensure the GNU Lesser General Public License version 2.1 requirements
22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
24 ** In addition, as a special exception, Nokia gives you certain additional
25 ** rights. These rights are described in the Nokia Qt LGPL Exception
26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
28 ** If you have questions regarding the use of this file, please contact
29 ** Nokia at qt-info@nokia.com.
38 ** $QT_END_LICENSE$
40 ****************************************************************************/
42 #include "qtestlogger_p.h"
43 #include "qtestelement.h"
44 #include "qtestxunitstreamer.h"
45 #include "qtestxmlstreamer.h"
46 #include "qtestlightxmlstreamer.h"
47 #include "qtestfilelogger.h"
49 #include "QtTest/qtestcase.h"
50 #include "QtTest/private/qtestresult_p.h"
51 #include "QtTest/private/qbenchmark_p.h"
53 #include <string.h>
55 QT_BEGIN_NAMESPACE
57 QTestLogger::QTestLogger(int fm)
58 :listOfTestcases(0), currentLogElement(0), errorLogElement(0),
59 logFormatter(0), format( (TestLoggerFormat)fm ), filelogger(new QTestFileLogger),
60 testCounter(0), passCounter(0),
61 failureCounter(0), errorCounter(0),
62 warningCounter(0), skipCounter(0),
63 systemCounter(0), qdebugCounter(0),
64 qwarnCounter(0), qfatalCounter(0),
65 infoCounter(0)
69 QTestLogger::~QTestLogger()
71 if(format == TLF_XunitXml)
72 delete currentLogElement;
73 else
74 delete listOfTestcases;
76 delete logFormatter;
77 delete filelogger;
80 void QTestLogger::startLogging()
82 switch(format){
83 case TLF_LightXml:{
84 logFormatter = new QTestLightXmlStreamer;
85 filelogger->init();
86 break;
87 }case TLF_XML:{
88 logFormatter = new QTestXmlStreamer;
89 filelogger->init();
90 break;
91 }case TLF_XunitXml:{
92 logFormatter = new QTestXunitStreamer;
93 delete errorLogElement;
94 errorLogElement = new QTestElement(QTest::LET_SystemError);
95 filelogger->init();
96 break;
100 logFormatter->setLogger(this);
101 logFormatter->startStreaming();
104 void QTestLogger::stopLogging()
106 QTestElement *iterator = listOfTestcases;
108 if(format == TLF_XunitXml ){
109 char buf[10];
111 currentLogElement = new QTestElement(QTest::LET_TestSuite);
112 currentLogElement->addAttribute(QTest::AI_Name, QTestResult::currentTestObjectName());
114 QTest::qt_snprintf(buf, sizeof(buf), "%i", testCounter);
115 currentLogElement->addAttribute(QTest::AI_Tests, buf);
117 QTest::qt_snprintf(buf, sizeof(buf), "%i", failureCounter);
118 currentLogElement->addAttribute(QTest::AI_Failures, buf);
120 QTest::qt_snprintf(buf, sizeof(buf), "%i", errorCounter);
121 currentLogElement->addAttribute(QTest::AI_Errors, buf);
123 QTestElement *property;
124 QTestElement *properties = new QTestElement(QTest::LET_Properties);
126 property = new QTestElement(QTest::LET_Property);
127 property->addAttribute(QTest::AI_Name, "QTestVersion");
128 property->addAttribute(QTest::AI_PropertyValue, QTEST_VERSION_STR);
129 properties->addLogElement(property);
131 property = new QTestElement(QTest::LET_Property);
132 property->addAttribute(QTest::AI_Name, "QtVersion");
133 property->addAttribute(QTest::AI_PropertyValue, qVersion());
134 properties->addLogElement(property);
136 currentLogElement->addLogElement(properties);
138 currentLogElement->addLogElement(iterator);
140 /* For correct indenting, make sure every testcase knows its parent */
141 QTestElement* testcase = iterator;
142 while (testcase) {
143 testcase->setParent(currentLogElement);
144 testcase = testcase->nextElement();
147 currentLogElement->addLogElement(errorLogElement);
149 QTestElement *it = currentLogElement;
150 logFormatter->output(it);
151 }else{
152 logFormatter->output(iterator);
155 logFormatter->stopStreaming();
158 void QTestLogger::enterTestFunction(const char *function)
160 char buf[1024];
161 QTest::qt_snprintf(buf, sizeof(buf), "Entered test-function: %s\n", function);
162 filelogger->flush(buf);
164 currentLogElement = new QTestElement(QTest::LET_TestCase);
165 currentLogElement->addAttribute(QTest::AI_Name, function);
166 currentLogElement->addToList(&listOfTestcases);
168 ++testCounter;
171 void QTestLogger::leaveTestFunction()
175 void QTestLogger::addIncident(IncidentTypes type, const char *description,
176 const char *file, int line)
178 const char *typeBuf = 0;
179 char buf[100];
181 switch (type) {
182 case QAbstractTestLogger::XPass:
183 ++failureCounter;
184 typeBuf = "xpass";
185 break;
186 case QAbstractTestLogger::Pass:
187 ++passCounter;
188 typeBuf = "pass";
189 break;
190 case QAbstractTestLogger::XFail:
191 ++passCounter;
192 typeBuf = "xfail";
193 break;
194 case QAbstractTestLogger::Fail:
195 ++failureCounter;
196 typeBuf = "fail";
197 break;
198 default:
199 typeBuf = "??????";
200 break;
203 if (type == QAbstractTestLogger::Fail || type == QAbstractTestLogger::XPass
204 || ((format != TLF_XunitXml) && (type == QAbstractTestLogger::XFail))) {
205 QTestElement *failureElement = new QTestElement(QTest::LET_Failure);
206 failureElement->addAttribute(QTest::AI_Result, typeBuf);
207 if(file)
208 failureElement->addAttribute(QTest::AI_File, file);
209 else
210 failureElement->addAttribute(QTest::AI_File, "");
211 QTest::qt_snprintf(buf, sizeof(buf), "%i", line);
212 failureElement->addAttribute(QTest::AI_Line, buf);
213 failureElement->addAttribute(QTest::AI_Description, description);
214 const char* tag = QTestResult::currentDataTag();
215 if (tag) {
216 failureElement->addAttribute(QTest::AI_Tag, tag);
218 currentLogElement->addLogElement(failureElement);
222 Only one result can be shown for the whole testfunction.
223 Check if we currently have a result, and if so, overwrite it
224 iff the new result is worse.
226 QTestElementAttribute* resultAttr =
227 const_cast<QTestElementAttribute*>(currentLogElement->attribute(QTest::AI_Result));
228 if (resultAttr) {
229 const char* oldResult = resultAttr->value();
230 bool overwrite = false;
231 if (!strcmp(oldResult, "pass")) {
232 overwrite = true;
234 else if (!strcmp(oldResult, "xfail")) {
235 overwrite = (type == QAbstractTestLogger::XPass || type == QAbstractTestLogger::Fail);
237 else if (!strcmp(oldResult, "xpass")) {
238 overwrite = (type == QAbstractTestLogger::Fail);
240 if (overwrite) {
241 resultAttr->setPair(QTest::AI_Result, typeBuf);
244 else {
245 currentLogElement->addAttribute(QTest::AI_Result, typeBuf);
248 if(file)
249 currentLogElement->addAttribute(QTest::AI_File, file);
250 else
251 currentLogElement->addAttribute(QTest::AI_File, "");
253 QTest::qt_snprintf(buf, sizeof(buf), "%i", line);
254 currentLogElement->addAttribute(QTest::AI_Line, buf);
257 Since XFAIL does not add a failure to the testlog in xunitxml, add a message, so we still
258 have some information about the expected failure.
260 if (format == TLF_XunitXml && type == QAbstractTestLogger::XFail) {
261 QTestLogger::addMessage(QAbstractTestLogger::Info, description, file, line);
265 void QTestLogger::addBenchmarkResult(const QBenchmarkResult &result)
267 QTestElement *benchmarkElement = new QTestElement(QTest::LET_Benchmark);
268 // printf("element %i", benchmarkElement->elementType());
270 benchmarkElement->addAttribute(
271 QTest::AI_Metric,
272 QTest::benchmarkMetricName(QBenchmarkTestMethodData::current->result.metric));
273 benchmarkElement->addAttribute(QTest::AI_Tag, result.context.tag.toAscii().data());
274 benchmarkElement->addAttribute(QTest::AI_Value, QByteArray::number(result.value).constData());
276 char buf[100];
277 QTest::qt_snprintf(buf, sizeof(buf), "%i", result.iterations);
278 benchmarkElement->addAttribute(QTest::AI_Iterations, buf);
279 currentLogElement->addLogElement(benchmarkElement);
282 void QTestLogger::addMessage(MessageTypes type, const char *message, const char *file, int line)
284 QTestElement *errorElement = new QTestElement(QTest::LET_Error);
285 const char *typeBuf = 0;
287 switch (type) {
288 case QAbstractTestLogger::Warn:
289 ++warningCounter;
290 typeBuf = "warn";
291 break;
292 case QAbstractTestLogger::QSystem:
293 ++systemCounter;
294 typeBuf = "system";
295 break;
296 case QAbstractTestLogger::QDebug:
297 ++qdebugCounter;
298 typeBuf = "qdebug";
299 break;
300 case QAbstractTestLogger::QWarning:
301 ++qwarnCounter;
302 typeBuf = "qwarning";
303 break;
304 case QAbstractTestLogger::QFatal:
305 ++qfatalCounter;
306 typeBuf = "qfatal";
307 break;
308 case QAbstractTestLogger::Skip:
309 ++skipCounter;
310 typeBuf = "skip";
311 break;
312 case QAbstractTestLogger::Info:
313 ++infoCounter;
314 typeBuf = "info";
315 break;
316 default:
317 typeBuf = "??????";
318 break;
321 errorElement->addAttribute(QTest::AI_Type, typeBuf);
322 errorElement->addAttribute(QTest::AI_Description, message);
324 if(file)
325 errorElement->addAttribute(QTest::AI_File, file);
326 else
327 errorElement->addAttribute(QTest::AI_File, "");
329 char buf[100];
330 QTest::qt_snprintf(buf, sizeof(buf), "%i", line);
331 errorElement->addAttribute(QTest::AI_Line, buf);
333 currentLogElement->addLogElement(errorElement);
334 ++errorCounter;
336 // Also add the message to the system error log (i.e. stderr), if one exists
337 if (errorLogElement) {
338 QTestElement *systemErrorElement = new QTestElement(QTest::LET_Error);
339 systemErrorElement->addAttribute(QTest::AI_Description, message);
340 errorLogElement->addLogElement(systemErrorElement);
344 void QTestLogger::setLogFormat(TestLoggerFormat fm)
346 format = fm;
349 QTestLogger::TestLoggerFormat QTestLogger::logFormat()
351 return format;
354 int QTestLogger::passCount() const
356 return passCounter;
359 int QTestLogger::failureCount() const
361 return failureCounter;
364 int QTestLogger::errorCount() const
366 return errorCounter;
369 int QTestLogger::warningCount() const
371 return warningCounter;
374 int QTestLogger::skipCount() const
376 return skipCounter;
379 int QTestLogger::systemCount() const
381 return systemCounter;
384 int QTestLogger::qdebugCount() const
386 return qdebugCounter;
389 int QTestLogger::qwarnCount() const
391 return qwarnCounter;
394 int QTestLogger::qfatalCount() const
396 return qfatalCounter;
399 int QTestLogger::infoCount() const
401 return infoCounter;
404 QT_END_NAMESPACE