1 /****************************************************************************
2 **
3 ** Copyright (C) 2015 The Qt Company Ltd.
4 ** Contact: http://www.qt.io/licensing/
5 **
6 ** This file is part of the test suite of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** Commercial License Usage
10 ** Licensees holding valid commercial Qt licenses may use this file in
11 ** accordance with the commercial license agreement provided with the
12 ** Software or, alternatively, in accordance with the terms contained in
13 ** a written agreement between you and The Qt Company. For licensing terms
14 ** and conditions see http://www.qt.io/terms-conditions. For further
15 ** information use the contact form at http://www.qt.io/contact-us.
16 **
17 ** GNU Lesser General Public License Usage
18 ** Alternatively, this file may be used under the terms of the GNU Lesser
19 ** General Public License version 2.1 or version 3 as published by the Free
20 ** Software Foundation and appearing in the file LICENSE.LGPLv21 and
21 ** LICENSE.LGPLv3 included in the packaging of this file. Please review the
22 ** following information to ensure the GNU Lesser General Public License
23 ** requirements will be met: https://www.gnu.org/licenses/lgpl.html and
24 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
25 **
26 ** As a special exception, The Qt Company gives you certain additional
27 ** rights. These rights are described in The Qt Company LGPL Exception
28 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
29 **
30 ** GNU General Public License Usage
31 ** Alternatively, this file may be used under the terms of the GNU
32 ** General Public License version 3.0 as published by the Free Software
33 ** Foundation and appearing in the file LICENSE.GPL included in the
34 ** packaging of this file. Please review the following information to
35 ** ensure the GNU General Public License version 3.0 requirements will be
36 ** met: http://www.gnu.org/copyleft/gpl.html.
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41
42 #include <QFileInfo>
43 #include <QVariant>
44 #include <QXmlInputSource>
45 #include <QXmlSimpleReader>
46 #include <QtDebug>
47
48 #include "Global.h"
49 #include "TestSuiteHandler.h"
50 #include "TestSuiteResult.h"
51 #include "XMLWriter.h"
52 #include "XSLTTestSuiteHandler.h"
53 #include "XSDTestSuiteHandler.h"
54 #include "qdebug_p.h"
55
56 #include "TestSuite.h"
57
58 using namespace QPatternistSDK;
59 using namespace QPatternist;
60
TestSuite()61 TestSuite::TestSuite()
62 {
63 }
64
data(const Qt::ItemDataRole role,int column) const65 QVariant TestSuite::data(const Qt::ItemDataRole role, int column) const
66 {
67 if(role != Qt::DisplayRole)
68 return QVariant();
69
70 switch(column)
71 {
72 case 0:
73 return title();
74 case 1:
75 return QString();
76 default:
77 {
78 Q_ASSERT(false);
79 return QString();
80 }
81 }
82 }
83
runSuite()84 TestSuiteResult *TestSuite::runSuite()
85 {
86 const QDate date(QDate::currentDate());
87 TestResult::List result(execute(CompileAndRun, this));
88
89 return new TestSuiteResult(version(), date, result);
90 }
91
openCatalog(const QUrl & catalogURI,QString & errorMsg,const bool useExclusionList,SuiteType suiteType)92 TestSuite *TestSuite::openCatalog(const QUrl &catalogURI,
93 QString &errorMsg,
94 const bool useExclusionList,
95 SuiteType suiteType)
96 {
97 pDebug() << "Opening catalog:" << catalogURI.toString();
98 QFile ts(catalogURI.toLocalFile());
99 Q_ASSERT(catalogURI.isValid());
100
101 if(!ts.exists())
102 {
103 errorMsg = QString::fromLatin1("The test suite catalog \"%1\" could not be found.\n")
104 .arg(ts.fileName());
105 return 0;
106 }
107
108 const QFileInfo info(ts);
109
110 if(!info.isReadable())
111 {
112 errorMsg = QString::fromLatin1("Cannot read the test suite catalog.\n");
113 return 0;
114 }
115 else if(!info.isFile())
116 {
117 errorMsg = QString::fromLatin1("The specified test suite catalog \"%1\" is not a file. "
118 "The test suite catalog must be a file, it cannot be "
119 "a directory, for example.\n")
120 .arg(ts.fileName());
121 return 0;
122 }
123 else if(!ts.open(QIODevice::ReadOnly | QIODevice::Text))
124 {
125 errorMsg = QString::fromLatin1("Failed to open the test suite catalog, \"%1\".\n")
126 .arg(ts.fileName());
127 return 0;
128 }
129
130 return openCatalog(&ts, errorMsg, catalogURI, useExclusionList, suiteType);
131 }
132
openCatalog(QIODevice * input,QString & errorMsg,const QUrl & fileName,const bool useExclusionList,SuiteType suiteType)133 TestSuite *TestSuite::openCatalog(QIODevice *input,
134 QString &errorMsg,
135 const QUrl &fileName,
136 const bool useExclusionList,
137 SuiteType suiteType)
138 {
139 Q_ASSERT(input);
140
141 QXmlSimpleReader reader;
142 typedef QPatternist::AutoPtr<QXmlDefaultHandler> HandlerPtr;
143
144 HandlerPtr loader;
145
146 switch (suiteType) {
147 case XQuerySuite: loader = HandlerPtr(new TestSuiteHandler(fileName, useExclusionList)); break;
148 case XsltSuite: loader = HandlerPtr(new XSLTTestSuiteHandler(fileName)); break;
149 case XsdSuite: loader = HandlerPtr(new XSDTestSuiteHandler(fileName)); break;
150 default: Q_ASSERT(false); break;
151 }
152
153 reader.setContentHandler(loader.data());
154 reader.setEntityResolver(loader.data());
155
156 QXmlInputSource source(input);
157
158 if(!reader.parse(source))
159 {
160 errorMsg = QString::fromLatin1("Couldn't parse %1").arg(fileName.toString());
161 return 0;
162 }
163
164 TestSuite *suite = 0;
165 switch (suiteType) {
166 case XQuerySuite: suite = static_cast<TestSuiteHandler *>(loader.data())->testSuite(); break;
167 case XsltSuite: suite = static_cast<XSLTTestSuiteHandler *>(loader.data())->testSuite(); break;
168 case XsdSuite: suite = static_cast<XSDTestSuiteHandler *>(loader.data())->testSuite(); break;
169 default: Q_ASSERT(false); break;
170 }
171
172 if(suite)
173 return suite;
174
175 errorMsg = QString::fromLatin1("Failed to load \"%1\". "
176 "It appears to have no test-suite element.\n").arg(fileName.toString());
177 return 0;
178 }
179
toXML(XMLWriter & receiver,TestCase * const tc) const180 void TestSuite::toXML(XMLWriter &receiver, TestCase *const tc) const
181 {
182 // TODO startElement() endElement() calls can be simplified.
183
184 Q_ASSERT(tc);
185
186 receiver.startDocument();
187 /* <test-suite> */
188 QXmlAttributes test_suiteAtts;
189 test_suiteAtts.append(QLatin1String("CatalogDesignDate"), QString(),
190 QLatin1String("CatalogDesignDate"), m_designDate.toString(Qt::ISODate));
191 test_suiteAtts.append(QLatin1String("version"), QString(),
192 QLatin1String("version"), m_version);
193 test_suiteAtts.append(QLatin1String("SourceOffsetPath"), QString(),
194 QLatin1String("SourceOffsetPath"), QString());
195 test_suiteAtts.append(QLatin1String("ResultOffsetPath"), QString(),
196 QLatin1String("ResultOffsetPath"), QString());
197 test_suiteAtts.append(QLatin1String("XQueryQueryOffsetPath"), QString(),
198 QLatin1String("XQueryQueryOffsetPath"), QString());
199 test_suiteAtts.append(QLatin1String("QueryXQueryOffsetPath"), QString(),
200 QLatin1String("QueryXQueryOffsetPath"), QString());
201 test_suiteAtts.append(QLatin1String("XQueryFileExtension"), QString(),
202 QLatin1String("XQueryFileExtension"), QString());
203 test_suiteAtts.append(QLatin1String("XQueryXFileExtension"), QString(),
204 QLatin1String("XQueryXFileExtension"), QString());
205
206 receiver.startPrefixMapping(QString(), Global::xqtsCatalogNS);
207 receiver.startElement(QLatin1String("test-suite"), test_suiteAtts);
208 receiver.endPrefixMapping(QString());
209
210 /* <test-group> */
211 QXmlAttributes test_groupAtts;
212 test_groupAtts.append(QLatin1String("GeneratedGroupByPatternistSDKRunSuite"), QString(),
213 QLatin1String("GeneratedGroupByPatternistSDKRunSuite"), QString());
214 receiver.startElement(QLatin1String("test-group"), test_groupAtts);
215
216 /* <GroupInfo> */
217 receiver.startElement(QLatin1String("GroupInfo"), test_groupAtts);
218
219 /* <title> */
220 receiver.startElement(QLatin1String("title"), test_groupAtts);
221 receiver.characters(QLatin1String("Contains the test case generated by PatternistSDKRunSuite."));
222
223 /* </title> */
224 receiver.endElement(QLatin1String("title"));
225
226 /* <description> */
227 receiver.startElement(QLatin1String("description"), test_groupAtts);
228 /* </description> */
229 receiver.endElement(QLatin1String("description"));
230
231 /* </GroupInfo> */
232 receiver.endElement(QLatin1String("GroupInfo"));
233
234 /* <test-case> */
235 tc->toXML(receiver);
236 /* </test-case> */
237
238 /* </test-group> */
239 receiver.endElement(QLatin1String("test-group"));
240
241 /* </test-suite> */
242 receiver.endElement(QLatin1String("test-suite"));
243 }
244
version() const245 QString TestSuite::version() const
246 {
247 return m_version;
248 }
249
designDate() const250 QDate TestSuite::designDate() const
251 {
252 return m_designDate;
253 }
254
setVersion(const QString & ver)255 void TestSuite::setVersion(const QString &ver)
256 {
257 m_version = ver;
258 }
259
setDesignDate(const QDate & date)260 void TestSuite::setDesignDate(const QDate &date)
261 {
262 m_designDate = date;
263 }
264
parent() const265 TestContainer *TestSuite::parent() const
266 {
267 return 0;
268 }
269
270 // vim: et:ts=4:sw=4:sts=4
271