#include #include #include #include #include #include #include #include #include #include #include #include #include #include using namespace NAMESPACE; /** @page junitXml Test Output XML Format The test output XML format emulates JUnit's format, so that JUnit tools can be used to evaluate ist, namely on tools like jenkins. @code{.xml} ... ... ... @endcode The default name for a testsuite is the name of the test script file. it can be overwritten using the @c testsuite statement. The attribute @c failures contains the number of failed test cases. The default classname for a testcase is @c testsuite-preparation before the script runs, then in the script it is the name of the current command and the classname equals to the testsuite's name. If you specify testsuites, testcases in your script file, then this overwrites the defaults. Here @c testsuite maps to the testsuite's name, @c testcase maps to the next testcase's classname. */ QString format(QString txt, int indent = 2, int cpl = 80) { QStringList res; QStringList lines(txt.split('\n')); QString ind(indent, ' '); for (QString line: lines) { line.insert(0, ind); for (int pos(indent); line.size()-pos>cpl; ++pos) { int pos2=line.lastIndexOf(' ', pos+cpl); if (pos2>pos) pos=pos2; else pos=line.indexOf(' ', pos+1); if (pos<0) break; line.remove(pos, 1); line.insert(pos, "\n"+ind); } res+=line; } return res.join('\n'); } QString format(std::string txt, int indent = 2, int cpl = 60) { return format(QString::fromStdString(txt), indent, cpl); } QString help(const Script& s) { std::ostringstream ss; ss<<"Synopsis"<] [ [ [...]]]"< within the test scripts", "path")); parser.addOption(QCommandLineOption (QStringList()<<"x"<<"xml", "store XML output in ", "xmlfile")); parser.addOption(QCommandLineOption (QStringList()<<"r"<<"retries", "on error retry up to times", "maxretries", "0")); parser.addOption(QCommandLineOption (QStringList()<<"timeout", "set default timeout in seconds", "timeout", "40")); parser.addOption(QCommandLineOption (QStringList()<<"W"<<"width", "set screenshot size to pixel", "width", "2048")); parser.addOption(QCommandLineOption (QStringList()<<"H"<<"height", "set screenshot size to pixel", "height", "2048")); parser.addOption(QCommandLineOption (QStringList()<<"v"<<"version", "show version information")); parser.addOption(QCommandLineOption (QStringList()<<"s"<<"skipped", "treat skipped test cases as failure in XML output file")); parser.addOption(QCommandLineOption (QStringList()<<"t"<<"target-path", "set screenshot target path to ", "path", QDir().absolutePath()+QDir::separator()+"attachments")); parser.process(a); if (parser.isSet("version")) { std::cout<<*argv< testsuites(new xml::Node("testsuites")); for (QString file: parser.positionalArguments()) { int expectedtestcases(-1); xml::Node testsuite("testsuite"); testsuite.attr("name") = QFileInfo(file).baseName().toStdString(); testsuite.attr("timestamp") = QDateTime::currentDateTime().toString(Qt::ISODate).toStdString(); xml::Node testcase("testcase"); testcase.attr("classname") = "testsuite-preparation"; try { script.reset(); script.log("====================="); script.log("TEST: "+file); script.log("---------------------"); testcase.attr("name") = "open test suite file"; testsuite<mainFrame(), testsuites, target+QDir::separator()+QFileInfo(file).baseName(), true, retries); script.log("SUCCESS: "+file); } } catch (std::exception& e) { failed = true; script.log("FAILED: "+file+" with "+e.what()); xml::Node failure("failure"); failure.attr("message") = Script::xmlattr(e.what()).toStdString(); testsuites->last().last()<last().attr("failures") = "1"; else testsuites->last().attr("failures") = mrw::string(expectedtestcases+1-testsuites->last().children()); if (parser.isSet("skipped")) { testcase.attr("name") = "skipped test case"; failure.attr("message") = "skipped due to previous failure"; testcase<last().children()); ilast()<last().attr("tests") = mrw::string(testsuites->last().children()); } else { testsuites->last().attr("tests") = mrw::string(expectedtestcases); } if (script.cout().size()) testsuites->last()<<(xml::String("system-out") = script.xmlattr(script.cout()).toStdString()); if (script.cerr().size()) testsuites->last()<<(xml::String("system-err") = script.xmlattr(script.cerr()).toStdString()); } if (parser.isSet("xml")) { // todo: write xml file std::ofstream xmlfile(parser.value("xml").toStdString()); xmlfile<<(*testsuites)<