/**************************************************************************** ** ** Copyright (C) 2012 Intel Corporation. ** Contact: http://www.qt-project.org/legal ** ** This file is part of the test suite of the Qt Toolkit. ** ** $QT_BEGIN_LICENSE:LGPL$ ** Commercial License Usage ** Licensees holding valid commercial Qt licenses may use this file in ** accordance with the commercial license agreement provided with the ** Software or, alternatively, in accordance with the terms contained in ** a written agreement between you and Digia. For licensing terms and ** conditions see http://qt.digia.com/licensing. For further information ** use the contact form at http://qt.digia.com/contact-us. ** ** GNU Lesser General Public License Usage ** Alternatively, this file may be used under the terms of the GNU Lesser ** General Public License version 2.1 as published by the Free Software ** Foundation and appearing in the file LICENSE.LGPL included in the ** packaging of this file. Please review the following information to ** ensure the GNU Lesser General Public License version 2.1 requirements ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. ** ** In addition, as a special exception, Digia gives you certain additional ** rights. These rights are described in the Digia Qt LGPL Exception ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. ** ** GNU General Public License Usage ** Alternatively, this file may be used under the terms of the GNU ** General Public License version 3.0 as published by the Free Software ** Foundation and appearing in the file LICENSE.GPL included in the ** packaging of this file. Please review the following information to ** ensure the GNU General Public License version 3.0 requirements will be ** met: http://www.gnu.org/copyleft/gpl.html. ** ** ** $QT_END_LICENSE$ ** ****************************************************************************/ #include #include typedef QList > QueryItems; Q_DECLARE_METATYPE(QueryItems) Q_DECLARE_METATYPE(QUrl::ComponentFormattingOptions) class tst_QUrlQuery : public QObject { Q_OBJECT public: tst_QUrlQuery() { qRegisterMetaType(); } private Q_SLOTS: void constructing(); void addRemove(); void multiAddRemove(); void multiplyAddSamePair(); void setQueryItems_data(); void setQueryItems(); void basicParsing_data(); void basicParsing(); void reconstructQuery_data(); void reconstructQuery(); void encodedSetQueryItems_data(); void encodedSetQueryItems(); void encodedParsing_data(); void encodedParsing(); void differentDelimiters(); // old tests from tst_qurl.cpp // add new tests above void old_queryItems(); void old_hasQueryItem_data(); void old_hasQueryItem(); }; static QString prettyElement(const QString &key, const QString &value) { QString result; if (key.isNull()) result += "null -> "; else result += '"' % key % "\" -> "; if (value.isNull()) result += "null"; else result += '"' % value % '"'; return result; } static QString prettyPair(QList >::const_iterator it) { return prettyElement(it->first, it->second); } template static QByteArray prettyList(const T &items) { QString result = "("; bool first = true; typename T::const_iterator it = items.constBegin(); for ( ; it != items.constEnd(); ++it) { if (!first) result += ", "; first = false; result += prettyPair(it); } result += ")"; return result.toLocal8Bit(); } static bool compare(const QList > &actual, const QueryItems &expected, const char *actualStr, const char *expectedStr, const char *file, int line) { return QTest::compare_helper(actual == expected, "Compared values are not the same", qstrdup(prettyList(actual)), qstrdup(prettyList(expected).data()), actualStr, expectedStr, file, line); } #define COMPARE_ITEMS(actual, expected) \ do { \ if (!compare(actual, expected, #actual, #expected, __FILE__, __LINE__)) \ return; \ } while (0) inline QueryItems operator+(QueryItems items, const QPair &pair) { // items is already a copy items.append(pair); return items; } inline QueryItems operator+(const QPair &pair, QueryItems items) { // items is already a copy items.prepend(pair); return items; } inline QPair qItem(const QString &first, const QString &second) { return qMakePair(first, second); } inline QPair qItem(const char *first, const QString &second) { return qMakePair(QString::fromUtf8(first), second); } inline QPair qItem(const char *first, const char *second) { return qMakePair(QString::fromUtf8(first), QString::fromUtf8(second)); } inline QPair qItem(const QString &first, const char *second) { return qMakePair(first, QString::fromUtf8(second)); } static QUrlQuery emptyQuery() { return QUrlQuery(); } void tst_QUrlQuery::constructing() { QUrlQuery empty; QVERIFY(empty.isEmpty()); QCOMPARE(empty.queryPairDelimiter(), QUrlQuery::defaultQueryPairDelimiter()); QCOMPARE(empty.queryValueDelimiter(), QUrlQuery::defaultQueryValueDelimiter()); // undefined whether it is detached, but don't crash QVERIFY(empty.isDetached() || !empty.isDetached()); empty.clear(); QVERIFY(empty.isEmpty()); { QUrlQuery copy(empty); QVERIFY(copy.isEmpty()); QVERIFY(!copy.isDetached()); QVERIFY(copy == empty); QVERIFY(!(copy != empty)); copy = empty; QVERIFY(copy == empty); copy = QUrlQuery(); QVERIFY(copy == empty); } { QUrlQuery copy(emptyQuery()); QVERIFY(copy == empty); } QVERIFY(!empty.hasQueryItem("a")); QVERIFY(empty.queryItemValue("a").isEmpty()); QVERIFY(empty.allQueryItemValues("a").isEmpty()); QVERIFY(!empty.hasQueryItem("")); QVERIFY(empty.queryItemValue("").isEmpty()); QVERIFY(empty.allQueryItemValues("").isEmpty()); QVERIFY(!empty.hasQueryItem(QString())); QVERIFY(empty.queryItemValue(QString()).isEmpty()); QVERIFY(empty.allQueryItemValues(QString()).isEmpty()); QVERIFY(empty.queryItems().isEmpty()); QUrlQuery other; other.addQueryItem("a", "b"); QVERIFY(!other.isEmpty()); QVERIFY(other.isDetached()); QVERIFY(other != empty); QVERIFY(!(other == empty)); QUrlQuery copy(other); QVERIFY(copy == other); copy.clear(); QVERIFY(copy.isEmpty()); QVERIFY(copy != other); copy = other; QVERIFY(!copy.isEmpty()); QVERIFY(copy == other); copy = QUrlQuery(); QVERIFY(copy.isEmpty()); empty.setQueryDelimiters('(', ')'); QCOMPARE(empty.queryValueDelimiter(), QChar(QLatin1Char('('))); QCOMPARE(empty.queryPairDelimiter(), QChar(QLatin1Char(')'))); QList > query; query += qMakePair(QString("type"), QString("login")); query += qMakePair(QString("name"), QString::fromUtf8("åge nissemannsen")); query += qMakePair(QString("ole&du"), QString::fromUtf8("anne+jørgen=sant")); query += qMakePair(QString("prosent"), QString("%")); copy.setQueryItems(query); QVERIFY(!copy.isEmpty()); } void tst_QUrlQuery::addRemove() { QUrlQuery query; { // one item query.addQueryItem("a", "b"); QVERIFY(!query.isEmpty()); QVERIFY(query.hasQueryItem("a")); QCOMPARE(query.queryItemValue("a"), QString("b")); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "b"); QList > allItems = query.queryItems(); QCOMPARE(allItems.count(), 1); QCOMPARE(allItems.at(0).first, QString("a")); QCOMPARE(allItems.at(0).second, QString("b")); } QUrlQuery original = query; { // two items query.addQueryItem("c", "d"); QVERIFY(query.hasQueryItem("a")); QCOMPARE(query.queryItemValue("a"), QString("b")); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "b"); QVERIFY(query.hasQueryItem("c")); QCOMPARE(query.queryItemValue("c"), QString("d")); QCOMPARE(query.allQueryItemValues("c"), QStringList() << "d"); QList > allItems = query.queryItems(); QCOMPARE(allItems.count(), 2); QVERIFY(allItems.contains(qItem("a", "b"))); QVERIFY(allItems.contains(qItem("c", "d"))); QVERIFY(query != original); QVERIFY(!(query == original)); } { // remove an item that isn't there QUrlQuery copy = query; query.removeQueryItem("e"); QCOMPARE(query, copy); } { // remove an item query.removeQueryItem("c"); QVERIFY(query.hasQueryItem("a")); QCOMPARE(query.queryItemValue("a"), QString("b")); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "b"); QList > allItems = query.queryItems(); QCOMPARE(allItems.count(), 1); QCOMPARE(allItems.at(0).first, QString("a")); QCOMPARE(allItems.at(0).second, QString("b")); QVERIFY(query == original); QVERIFY(!(query != original)); } { // add an item with en empty value QString emptyButNotNull(0, Qt::Uninitialized); QVERIFY(emptyButNotNull.isEmpty()); QVERIFY(!emptyButNotNull.isNull()); query.addQueryItem("e", ""); QVERIFY(query.hasQueryItem("a")); QCOMPARE(query.queryItemValue("a"), QString("b")); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "b"); QVERIFY(query.hasQueryItem("e")); QCOMPARE(query.queryItemValue("e"), emptyButNotNull); QCOMPARE(query.allQueryItemValues("e"), QStringList() << emptyButNotNull); QList > allItems = query.queryItems(); QCOMPARE(allItems.count(), 2); QVERIFY(allItems.contains(qItem("a", "b"))); QVERIFY(allItems.contains(qItem("e", emptyButNotNull))); QVERIFY(query != original); QVERIFY(!(query == original)); } { // remove the items query.removeQueryItem("a"); query.removeQueryItem("e"); QVERIFY(query.isEmpty()); } } void tst_QUrlQuery::multiAddRemove() { QUrlQuery query; { // one item, two values query.addQueryItem("a", "b"); query.addQueryItem("a", "c"); QVERIFY(!query.isEmpty()); QVERIFY(query.hasQueryItem("a")); // returns the first one QVERIFY(query.queryItemValue("a") == "b"); // order is the order we set them in QVERIFY(query.allQueryItemValues("a") == QStringList() << "b" << "c"); } { // add another item, two values query.addQueryItem("A", "B"); query.addQueryItem("A", "C"); QVERIFY(query.hasQueryItem("A")); QVERIFY(query.hasQueryItem("a")); QVERIFY(query.queryItemValue("a") == "b"); QVERIFY(query.allQueryItemValues("a") == QStringList() << "b" << "c"); QVERIFY(query.queryItemValue("A") == "B"); QVERIFY(query.allQueryItemValues("A") == QStringList() << "B" << "C"); } { // remove one of the original items query.removeQueryItem("a"); QVERIFY(query.hasQueryItem("a")); // it must have removed the first one QVERIFY(query.queryItemValue("a") == "c"); } { // remove the items we added later query.removeAllQueryItems("A"); QVERIFY(!query.isEmpty()); QVERIFY(!query.hasQueryItem("A")); } { // add one element to the current, then remove them query.addQueryItem("a", "d"); query.removeAllQueryItems("a"); QVERIFY(!query.hasQueryItem("a")); QVERIFY(query.isEmpty()); } } void tst_QUrlQuery::multiplyAddSamePair() { QUrlQuery query; query.addQueryItem("a", "a"); query.addQueryItem("a", "a"); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "a" << "a"); query.addQueryItem("a", "a"); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "a" << "a" << "a"); query.removeQueryItem("a"); QCOMPARE(query.allQueryItemValues("a"), QStringList() << "a" << "a"); } void tst_QUrlQuery::setQueryItems_data() { QTest::addColumn("items"); QString emptyButNotNull(0, Qt::Uninitialized); QTest::newRow("empty") << QueryItems(); QTest::newRow("1-novalue") << (QueryItems() << qItem("a", QString())); QTest::newRow("1-emptyvalue") << (QueryItems() << qItem("a", emptyButNotNull)); QueryItems list; list << qItem("a", "b"); QTest::newRow("1-value") << list; QTest::newRow("1-multi") << (list + qItem("a", "c")); QTest::newRow("1-duplicated") << (list + qItem("a", "b")); list << qItem("c", "d"); QTest::newRow("2") << list; list << qItem("c", "e"); QTest::newRow("2-multi") << list; } void tst_QUrlQuery::setQueryItems() { QFETCH(QueryItems, items); QUrlQuery query; QueryItems::const_iterator it = items.constBegin(); for ( ; it != items.constEnd(); ++it) query.addQueryItem(it->first, it->second); COMPARE_ITEMS(query.queryItems(), items); query.clear(); query.setQueryItems(items); COMPARE_ITEMS(query.queryItems(), items); } void tst_QUrlQuery::basicParsing_data() { QTest::addColumn("queryString"); QTest::addColumn("items"); QString emptyButNotNull(0, Qt::Uninitialized); QTest::newRow("null") << QString() << QueryItems(); QTest::newRow("empty") << "" << QueryItems(); QTest::newRow("1-novalue") << "a" << (QueryItems() << qItem("a", QString())); QTest::newRow("1-emptyvalue") << "a=" << (QueryItems() << qItem("a", emptyButNotNull)); QTest::newRow("1-value") << "a=b" << (QueryItems() << qItem("a", "b")); // some longer keys QTest::newRow("1-longkey-novalue") << "thisisalongkey" << (QueryItems() << qItem("thisisalongkey", QString())); QTest::newRow("1-longkey-emptyvalue") << "thisisalongkey=" << (QueryItems() << qItem("thisisalongkey", emptyButNotNull)); QTest::newRow("1-longkey-value") << "thisisalongkey=b" << (QueryItems() << qItem("thisisalongkey", "b")); // longer values QTest::newRow("1-longvalue-value") << "a=thisisalongreasonablyvalue" << (QueryItems() << qItem("a", "thisisalongreasonablyvalue")); QTest::newRow("1-longboth-value") << "thisisalongkey=thisisalongreasonablyvalue" << (QueryItems() << qItem("thisisalongkey", "thisisalongreasonablyvalue")); // two or more entries QueryItems baselist; baselist << qItem("a", "b") << qItem("c", "d"); QTest::newRow("2-ab-cd") << "a=b&c=d" << baselist; QTest::newRow("2-cd-ab") << "c=d&a=b" << (QueryItems() << qItem("c", "d") << qItem("a", "b")); // the same entry multiply defined QTest::newRow("2-a-a") << "a&a" << (QueryItems() << qItem("a", QString()) << qItem("a", QString())); QTest::newRow("2-ab-a") << "a=b&a" << (QueryItems() << qItem("a", "b") << qItem("a", QString())); QTest::newRow("2-ab-ab") << "a=b&a=b" << (QueryItems() << qItem("a", "b") << qItem("a", "b")); QTest::newRow("2-ab-ac") << "a=b&a=c" << (QueryItems() << qItem("a", "b") << qItem("a", "c")); QPair novalue = qItem("somekey", QString()); QueryItems list2 = baselist + novalue; QTest::newRow("3-novalue-ab-cd") << "somekey&a=b&c=d" << (novalue + baselist); QTest::newRow("3-ab-novalue-cd") << "a=b&somekey&c=d" << (QueryItems() << qItem("a", "b") << novalue << qItem("c", "d")); QTest::newRow("3-ab-cd-novalue") << "a=b&c=d&somekey" << list2; list2 << qItem("otherkeynovalue", QString()); QTest::newRow("4-ab-cd-novalue-novalue") << "a=b&c=d&somekey&otherkeynovalue" << list2; QPair emptyvalue = qItem("somekey", emptyButNotNull); list2 = baselist + emptyvalue; QTest::newRow("3-emptyvalue-ab-cd") << "somekey=&a=b&c=d" << (emptyvalue + baselist); QTest::newRow("3-ab-emptyvalue-cd") << "a=b&somekey=&c=d" << (QueryItems() << qItem("a", "b") << emptyvalue << qItem("c", "d")); QTest::newRow("3-ab-cd-emptyvalue") << "a=b&c=d&somekey=" << list2; } void tst_QUrlQuery::basicParsing() { QFETCH(QString, queryString); QFETCH(QueryItems, items); QUrlQuery query(queryString); QCOMPARE(query.isEmpty(), items.isEmpty()); COMPARE_ITEMS(query.queryItems(), items); } void tst_QUrlQuery::reconstructQuery_data() { QTest::addColumn("queryString"); QTest::addColumn("items"); QString emptyButNotNull(0, Qt::Uninitialized); QTest::newRow("null") << QString() << QueryItems(); QTest::newRow("empty") << "" << QueryItems(); QTest::newRow("1-novalue") << "a" << (QueryItems() << qItem("a", QString())); QTest::newRow("1-emptyvalue") << "a=" << (QueryItems() << qItem("a", emptyButNotNull)); QTest::newRow("1-value") << "a=b" << (QueryItems() << qItem("a", "b")); // some longer keys QTest::newRow("1-longkey-novalue") << "thisisalongkey" << (QueryItems() << qItem("thisisalongkey", QString())); QTest::newRow("1-longkey-emptyvalue") << "thisisalongkey=" << (QueryItems() << qItem("thisisalongkey", emptyButNotNull)); QTest::newRow("1-longkey-value") << "thisisalongkey=b" << (QueryItems() << qItem("thisisalongkey", "b")); // longer values QTest::newRow("1-longvalue-value") << "a=thisisalongreasonablyvalue" << (QueryItems() << qItem("a", "thisisalongreasonablyvalue")); QTest::newRow("1-longboth-value") << "thisisalongkey=thisisalongreasonablyvalue" << (QueryItems() << qItem("thisisalongkey", "thisisalongreasonablyvalue")); // two or more entries QueryItems baselist; baselist << qItem("a", "b") << qItem("c", "d"); QTest::newRow("2-ab-cd") << "a=b&c=d" << baselist; // the same entry multiply defined QTest::newRow("2-a-a") << "a&a" << (QueryItems() << qItem("a", QString()) << qItem("a", QString())); QTest::newRow("2-ab-ab") << "a=b&a=b" << (QueryItems() << qItem("a", "b") << qItem("a", "b")); QTest::newRow("2-ab-ac") << "a=b&a=c" << (QueryItems() << qItem("a", "b") << qItem("a", "c")); QTest::newRow("2-ac-ab") << "a=c&a=b" << (QueryItems() << qItem("a", "c") << qItem("a", "b")); QTest::newRow("2-ab-cd") << "a=b&c=d" << (QueryItems() << qItem("a", "b") << qItem("c", "d")); QTest::newRow("2-cd-ab") << "c=d&a=b" << (QueryItems() << qItem("c", "d") << qItem("a", "b")); QueryItems list2 = baselist + qItem("somekey", QString()); QTest::newRow("3-ab-cd-novalue") << "a=b&c=d&somekey" << list2; list2 << qItem("otherkeynovalue", QString()); QTest::newRow("4-ab-cd-novalue-novalue") << "a=b&c=d&somekey&otherkeynovalue" << list2; list2 = baselist + qItem("somekey", emptyButNotNull); QTest::newRow("3-ab-cd-emptyvalue") << "a=b&c=d&somekey=" << list2; } void tst_QUrlQuery::reconstructQuery() { QFETCH(QString, queryString); QFETCH(QueryItems, items); QUrlQuery query; // add the items for (QueryItems::ConstIterator it = items.constBegin(); it != items.constEnd(); ++it) { query.addQueryItem(it->first, it->second); } QCOMPARE(query.query(), queryString); } void tst_QUrlQuery::encodedSetQueryItems_data() { QTest::addColumn("queryString"); QTest::addColumn("key"); QTest::addColumn("value"); QTest::addColumn("encoding"); QTest::addColumn("expectedQuery"); QTest::addColumn("expectedKey"); QTest::addColumn("expectedValue"); typedef QUrl::ComponentFormattingOptions F; QTest::newRow("nul") << "f%00=bar%00" << "f%00" << "bar%00" << F(QUrl::PrettyDecoded) << "f%00=bar%00" << "f%00" << "bar%00"; QTest::newRow("non-decodable-1") << "foo%01%7f=b%1ar" << "foo%01%7f" << "b%1ar" << F(QUrl::PrettyDecoded) << "foo%01%7F=b%1Ar" << "foo%01%7F" << "b%1Ar"; QTest::newRow("non-decodable-2") << "foo\x01\x7f=b\x1ar" << "foo\x01\x7f" << "b\x1Ar" << F(QUrl::PrettyDecoded) << "foo%01%7F=b%1Ar" << "foo%01%7F" << "b%1Ar"; QTest::newRow("space") << "%20=%20" << "%20" << "%20" << F(QUrl::PrettyDecoded) << " = " << " " << " "; QTest::newRow("encode-space") << " = " << " " << " " << F(QUrl::FullyEncoded) << "%20=%20" << "%20" << "%20"; // tri-state QTest::newRow("decode-non-delimiters") << "%3C%5C%3E=%7B%7C%7D%5E%60" << "%3C%5C%3E" << "%7B%7C%7D%5E%60" << F(QUrl::DecodeReserved) << "<\\>={|}^`" << "<\\>" << "{|}^`"; QTest::newRow("encode-non-delimiters") << "<\\>={|}^`" << "<\\>" << "{|}^`" << F(QUrl::EncodeReserved) << "%3C%5C%3E=%7B%7C%7D%5E%60" << "%3C%5C%3E" << "%7B%7C%7D%5E%60"; QTest::newRow("pretty-non-delimiters") << "<\\>={|}^`" << "<\\>" << "{|}^`" << F(QUrl::PrettyDecoded) << "%3C%5C%3E=%7B%7C%7D%5E%60" << "<\\>" << "{|}^`"; QTest::newRow("equals") << "%3D=%3D" << "%3D" << "%3D" << F(QUrl::PrettyDecoded) << "%3D=%3D" << "=" << "="; QTest::newRow("equals-2") << "%3D==" << "=" << "=" << F(QUrl::PrettyDecoded) << "%3D=%3D" << "=" << "="; QTest::newRow("ampersand") << "%26=%26" << "%26" << "%26" << F(QUrl::PrettyDecoded) << "%26=%26" << "&" << "&"; QTest::newRow("hash") << "#=#" << "%23" << "%23" << F(QUrl::PrettyDecoded) << "#=#" << "#" << "#"; QTest::newRow("decode-hash") << "%23=%23" << "%23" << "%23" << F(QUrl::PrettyDecoded) << "#=#" << "#" << "#"; QTest::newRow("percent") << "%25=%25" << "%25" << "%25" << F(QUrl::PrettyDecoded) << "%25=%25" << "%25" << "%25"; QTest::newRow("bad-percent-1") << "%=%" << "%" << "%" << F(QUrl::PrettyDecoded) << "%25=%25" << "%25" << "%25"; QTest::newRow("bad-percent-2") << "%2=%2" << "%2" << "%2" << F(QUrl::PrettyDecoded) << "%252=%252" << "%252" << "%252"; QTest::newRow("plus") << "+=+" << "+" << "+" << F(QUrl::PrettyDecoded) << "+=+" << "+" << "+"; QTest::newRow("2b") << "%2b=%2b" << "%2b" << "%2b" << F(QUrl::PrettyDecoded) << "%2B=%2B" << "%2B" << "%2B"; // plus signs must not be touched QTest::newRow("encode-plus") << "+=+" << "+" << "+" << F(QUrl::FullyEncoded) << "+=+" << "+" << "+"; QTest::newRow("decode-2b") << "%2b=%2b" << "%2b" << "%2b" << F(QUrl::PrettyDecoded) << "%2B=%2B" << "%2B" << "%2B"; QTest::newRow("unicode") << "q=R%C3%a9sum%c3%A9" << "q" << "R%C3%a9sum%c3%A9" << F(QUrl::PrettyDecoded) << QString::fromUtf8("q=R\xc3\xa9sum\xc3\xa9") << "q" << QString::fromUtf8("R\xc3\xa9sum\xc3\xa9"); QTest::newRow("encode-unicode") << QString::fromUtf8("q=R\xc3\xa9sum\xc3\xa9") << "q" << QString::fromUtf8("R\xc3\xa9sum\xc3\xa9") << F(QUrl::FullyEncoded) << "q=R%C3%A9sum%C3%A9" << "q" << "R%C3%A9sum%C3%A9"; } void tst_QUrlQuery::encodedSetQueryItems() { QFETCH(QString, key); QFETCH(QString, value); QFETCH(QString, expectedQuery); QFETCH(QString, expectedKey); QFETCH(QString, expectedValue); QFETCH(QUrl::ComponentFormattingOptions, encoding); QUrlQuery query; query.addQueryItem(key, value); COMPARE_ITEMS(query.queryItems(encoding), QueryItems() << qItem(expectedKey, expectedValue)); QCOMPARE(query.query(encoding), expectedQuery); } void tst_QUrlQuery::encodedParsing_data() { encodedSetQueryItems_data(); } void tst_QUrlQuery::encodedParsing() { QFETCH(QString, queryString); QFETCH(QString, expectedQuery); QFETCH(QString, expectedKey); QFETCH(QString, expectedValue); QFETCH(QUrl::ComponentFormattingOptions, encoding); QUrlQuery query(queryString); COMPARE_ITEMS(query.queryItems(encoding), QueryItems() << qItem(expectedKey, expectedValue)); QCOMPARE(query.query(encoding), expectedQuery); } void tst_QUrlQuery::differentDelimiters() { QUrlQuery query; query.setQueryDelimiters('(', ')'); { // parse: query.setQuery("foo(bar)hello(world)"); QueryItems expected; expected << qItem("foo", "bar") << qItem("hello", "world"); COMPARE_ITEMS(query.queryItems(), expected); COMPARE_ITEMS(query.queryItems(QUrl::FullyEncoded), expected); COMPARE_ITEMS(query.queryItems(QUrl::PrettyDecoded), expected); } { // reconstruct: // note the final ')' is missing because there are no further items QCOMPARE(query.query(), QString("foo(bar)hello(world")); } { // set items containing the new delimiters and the old ones query.clear(); query.addQueryItem("z(=)", "y(&)"); QCOMPARE(query.query(), QString("z%28=%29(y%28&%29")); QUrlQuery copy = query; QCOMPARE(query.query(), QString("z%28=%29(y%28&%29")); copy.setQueryDelimiters(QUrlQuery::defaultQueryValueDelimiter(), QUrlQuery::defaultQueryPairDelimiter()); QCOMPARE(copy.query(), QString("z(%3D)=y(%26)")); } } void tst_QUrlQuery::old_queryItems() { // test imported from old tst_qurl.cpp QUrlQuery url; QList > newItems; newItems += qMakePair(QString("1"), QString("a")); newItems += qMakePair(QString("2"), QString("b")); newItems += qMakePair(QString("3"), QString("c")); newItems += qMakePair(QString("4"), QString("a b")); newItems += qMakePair(QString("5"), QString("&")); newItems += qMakePair(QString("foo bar"), QString("hello world")); newItems += qMakePair(QString("foo+bar"), QString("hello+world")); newItems += qMakePair(QString("tex"), QString("a + b = c")); url.setQueryItems(newItems); QVERIFY(!url.isEmpty()); QList > setItems = url.queryItems(); QVERIFY(newItems == setItems); url.addQueryItem("1", "z"); #if 0 // undefined behaviour in the new QUrlQuery QVERIFY(url.hasQueryItem("1")); QCOMPARE(url.queryItemValue("1").toLatin1().constData(), "a"); url.addQueryItem("1", "zz"); QStringList expected; expected += "a"; expected += "z"; expected += "zz"; QCOMPARE(url.allQueryItemValues("1"), expected); url.removeQueryItem("1"); QCOMPARE(url.allQueryItemValues("1").size(), 2); QCOMPARE(url.queryItemValue("1").toLatin1().constData(), "z"); #endif url.removeAllQueryItems("1"); QVERIFY(!url.hasQueryItem("1")); QCOMPARE(url.queryItemValue("4").toLatin1().constData(), "a b"); QCOMPARE(url.queryItemValue("5").toLatin1().constData(), "&"); QCOMPARE(url.queryItemValue("tex").toLatin1().constData(), "a + b = c"); QCOMPARE(url.queryItemValue("foo bar").toLatin1().constData(), "hello world"); //url.setUrl("http://www.google.com/search?q=a+b"); url.setQuery("q=a+b"); QCOMPARE(url.queryItemValue("q"), QString("a+b")); //url.setUrl("http://www.google.com/search?q=a=b"); // invalid, but should be tolerated url.setQuery("q=a=b"); QCOMPARE(url.queryItemValue("q"), QString("a=b")); } void tst_QUrlQuery::old_hasQueryItem_data() { QTest::addColumn("url"); QTest::addColumn("item"); QTest::addColumn("trueFalse"); // the old tests started with "http://www.foo.bar" QTest::newRow("no query items") << "" << "baz" << false; QTest::newRow("query item: hello") << "hello=world" << "hello" << true; QTest::newRow("no query item: world") << "hello=world" << "world" << false; QTest::newRow("query item: qt") << "hello=world&qt=rocks" << "qt" << true; } void tst_QUrlQuery::old_hasQueryItem() { QFETCH(QString, url); QFETCH(QString, item); QFETCH(bool, trueFalse); QCOMPARE(QUrlQuery(url).hasQueryItem(item), trueFalse); } #if 0 // this test doesn't make sense anymore void tst_QUrl::removeAllEncodedQueryItems_data() { QTest::addColumn("url"); QTest::addColumn("key"); QTest::addColumn("result"); QTest::newRow("test1") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b&ccc=c") << QByteArray("bbb") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&ccc=c"); QTest::newRow("test2") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b&ccc=c") << QByteArray("aaa") << QUrl::fromEncoded("http://qt-project.org/foo?bbb=b&ccc=c"); // QTest::newRow("test3") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b&ccc=c") << QByteArray("ccc") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b"); QTest::newRow("test4") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b&ccc=c") << QByteArray("b%62b") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&bbb=b&ccc=c"); QTest::newRow("test5") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&b%62b=b&ccc=c") << QByteArray("b%62b") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&ccc=c"); QTest::newRow("test6") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&b%62b=b&ccc=c") << QByteArray("bbb") << QUrl::fromEncoded("http://qt-project.org/foo?aaa=a&b%62b=b&ccc=c"); } void tst_QUrl::removeAllEncodedQueryItems() { QFETCH(QUrl, url); QFETCH(QByteArray, key); QFETCH(QUrl, result); url.removeAllEncodedQueryItems(key); QCOMPARE(url, result); } #endif QTEST_APPLESS_MAIN(tst_QUrlQuery) #include "tst_qurlquery.moc"