QNetworkReply* KVNetworkAccessManager::createRequest(Operation op, const QNetworkRequest &req, QIODevice *outgoingData) { QNetworkRequest request = req; request.setRawHeader("User-Agent", "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:28.0) Gecko/20100101 Firefox/28.0"); if(op == PostOperation) { //qDebug() << "POST" << request.url().path(); // If the request addressed to API - translate this request if(request.url().host() != "localhost" && request.url().host() != "127.0.0.1" && !request.url().host().contains(".dmm.com")) { QNetworkReply *r = QNetworkAccessManager::createRequest(op, request, outgoingData); KVNetworkReply *reply = new KVNetworkReply(r->parent(), r, this, translation); return reply; } } else if(op == GetOperation) { // If the request addressed to DMM - create hacked cookies if(request.url().host().contains(".dmm.com")) { QNetworkCookie languageCookie; languageCookie.setDomain(".dmm.com"); languageCookie.setPath("/"); languageCookie.setName("cklg"); languageCookie.setValue("ja"); languageCookie.setExpirationDate(QDateTime::currentDateTime().addYears(1)); QNetworkCookie locationCookie; locationCookie.setDomain(".dmm.com"); locationCookie.setPath("/"); locationCookie.setName("ckcy"); locationCookie.setValue("1"); locationCookie.setExpirationDate(QDateTime::currentDateTime().addYears(1)); if(cookieHack) { cookieJar()->insertCookie(languageCookie); cookieJar()->insertCookie(locationCookie); } else { cookieJar()->deleteCookie(languageCookie); cookieJar()->deleteCookie(locationCookie); } } } QNetworkReply *reply = QNetworkAccessManager::createRequest(op, request, outgoingData); // If the request if for an SWF or MP3 file, track it and report progress if(req.url().path().endsWith(".swf") || req.url().path().endsWith(".mp3")) { connect(reply, SIGNAL(metaDataChanged()), this, SLOT(trackedGETMetaDataChanged())); connect(reply, SIGNAL(readyRead()), this, SLOT(trackedGETReadyRead())); connect(reply, SIGNAL(finished()), this, SLOT(trackedGETFinished())); } return reply; }
void CookieJar::loadCookies() { QString fName = m_appPath; fName += "cookies"; QSettings cnFile(fName, QSettings::IniFormat); setVkLogin(cnFile.value("login").toString()); QList<QNetworkCookie> cookies; int size = cnFile.beginReadArray("cookies"); for(int i=0; i<size; i++) { QNetworkCookie cook; cnFile.setArrayIndex(i); cook.setName(cnFile.value("name").toByteArray()); cook.setValue(cnFile.value("value").toByteArray()); cook.setDomain(cnFile.value("domain").toByteArray()); cook.setPath(cnFile.value("path").toByteArray()); cookies.insert(i, cook); } cnFile.endArray(); setAllCookies(cookies); }
QNetworkCookie CookieDialog::cookie() { QNetworkCookie cookie; cookie.setDomain(m_domainLineEdit->text()); cookie.setName(m_nameLineEdit->text().toLatin1()); cookie.setValue(m_valueLineEdit->text().toLatin1()); cookie.setExpirationDate(QDateTime(m_dateEdit->date())); cookie.setPath(m_pathLineEdit->text()); cookie.setSecure(m_isSecureComboBox->currentText() == tr("yes")); cookie.setHttpOnly(m_isHttpOnlyComboBox->currentText() == tr("yes")); return cookie; }
void CookieJar::setCookies(const QVariantList &cookies) { QList<QNetworkCookie> newCookies; for (int i = 0; i < cookies.size(); ++i) { QNetworkCookie nc; QVariantMap cookie = cookies.at(i).toMap(); // // The field of domain and cookie name/value MUST be set, otherwise skip it. // if (cookie["domain"].isNull() || cookie["domain"].toString().isEmpty() || cookie["name"].isNull() || cookie["name"].toString().isEmpty() || cookie["value"].isNull() ) { continue; } else { nc.setDomain(cookie["domain"].toString()); nc.setName(cookie["name"].toByteArray()); nc.setValue(cookie["value"].toByteArray()); } if (cookie["path"].isNull() || cookie["path"].toString().isEmpty()) { nc.setPath("/"); } else { nc.setPath(cookie["path"].toString()); } if (cookie["httponly"].isNull()) { nc.setHttpOnly(false); } else { nc.setHttpOnly(cookie["httponly"].toBool()); } if (cookie["secure"].isNull()) { nc.setSecure(false); } else { nc.setSecure(cookie["secure"].toBool()); } if (!cookie["expires"].isNull()) { QString datetime = cookie["expires"].toString().replace(" GMT", ""); QDateTime expires = QDateTime::fromString(datetime, "ddd, dd MMM yyyy hh:mm:ss"); if (expires.isValid()) { nc.setExpirationDate(expires); } } newCookies.append(nc); } this->setAllCookies(newCookies); }
void HttpWriterTest::writeSetCookieValue_data () { QTest::addColumn< QNetworkCookie > ("input"); QTest::addColumn< QString > ("result"); QNetworkCookie normal ("foo", "bar"); QNetworkCookie encoded ("foo", "b a;r"); QNetworkCookie maxAge ("foo", "bar"); QNetworkCookie maxAgePast ("foo", "bar"); QNetworkCookie domain ("foo", "bar"); QNetworkCookie path ("foo", "bar"); QNetworkCookie secure ("foo", "bar"); QNetworkCookie httpOnly ("foo", "bar"); QNetworkCookie complex ("foo", "b a;r"); maxAge.setExpirationDate (QDateTime::currentDateTime ().addSecs (123)); maxAgePast.setExpirationDate (QDateTime::currentDateTime ().addSecs (-100)); domain.setDomain ("nuriaproject.org"); path.setPath ("/foo/bar"); secure.setSecure (true); httpOnly.setHttpOnly (true); complex.setExpirationDate (QDateTime::currentDateTime ().addSecs (123)); complex.setDomain ("nuriaproject.org"); complex.setPath ("/foo/bar"); complex.setSecure (true); complex.setHttpOnly (true); QTest::newRow ("normal") << normal << "foo=bar"; QTest::newRow ("encoded") << encoded << "foo=b%20a%3Br"; QTest::newRow ("maxAge") << maxAge << "foo=bar; Max-Age=123"; QTest::newRow ("maxAge in past") << maxAgePast << "foo=bar; Max-Age=0"; QTest::newRow ("domain") << domain << "foo=bar; Domain=nuriaproject.org"; QTest::newRow ("path") << path << "foo=bar; Path=/foo/bar"; QTest::newRow ("secure") << secure << "foo=bar; Secure"; QTest::newRow ("httpOnly") << httpOnly << "foo=bar; HttpOnly"; QTest::newRow ("complex") << complex << "foo=b%20a%3Br; Domain=nuriaproject.org; " "Path=/foo/bar; Max-Age=123; Secure; HttpOnly"; }
void CookieJar::read() { qDebug() << Q_FUNC_INFO; qDebug() << COOKIE_PATH; QFile f(COOKIE); if(!f.exists()) { return; } if (!f.open(QIODevice::ReadOnly | QIODevice::Text)) { return; } QList<QNetworkCookie> list; while(!f.atEnd()) { QList<QByteArray> spl = f.readLine().split(';'); QList<QByteArray> cookie = spl[0].split('='); if(cookie.length() < 2 || cookie[0].isEmpty() || cookie[1].isEmpty()) { continue; } QMap<QByteArray, QByteArray> add; for(int cnt = 1; spl.length() > cnt; cnt++) { QList<QByteArray> t = spl[cnt].split('='); if(t.count() > 1) { add[t[0].trimmed()] = t[1].trimmed(); } } QNetworkCookie c; c.setName(cookie[0]); c.setValue(cookie[1]); c.setPath(add["path"]); c.setDomain(add["domain"]); c.setExpirationDate(QDateTime::fromString(add["expires"])); list.append(c); } setAllCookies(list); }
void ChatService::startLoginRequest() { _buddylist_poll_timer->stop(); qDebug() << _network->cookieJar()->cookiesForUrl(QUrl(FACEBOOK_URL)).count() << " cookies"; QList<QNetworkCookie> cookies; QMap<QString, QString> params; QUrl url(FACEBOOK_LOGIN_URL); QNetworkCookie cookie; cookie.setDomain(".facebook.com"); cookie.setPath("/"); // facebook uses this cookie to test for cookie support // if we dont set it it thinks we don't support cookies. cookie.setName("test_cookie"); cookie.setValue("1"); cookies << cookie; cookie.setName("isfbe"); cookie.setValue("false"); cookies << cookie; _network->cookieJar()->setCookiesFromUrl(cookies, QUrl(FACEBOOK_URL)); qDebug() << _network->cookieJar()->cookiesForUrl(QUrl(FACEBOOK_URL)).count() << " cookies"; // it seems those are not really needed, until I figure what // are they for //params.insert("md5pass", "0"); //params.insert("noerror", "1"); params.insert("email", _login); params.insert("pass", _password); params.insert("persistent", "1"); params.insert("login", "Login"); params.insert("charset_test", "€,´,€,´,水,Д,Є"); QString data = encodePostParams(params); qDebug() << data; QNetworkReply *reply = _network->post(QNetworkRequest(url), data.toAscii()); reply->setParent(this); QObject::connect(reply, SIGNAL(finished()), this, SLOT(slotLoginRequestFinished())); QObject::connect(reply, SIGNAL(error(QNetworkReply::NetworkError)), this, SLOT(slotLoginRequestError(QNetworkReply::NetworkError))); }
QList<QNetworkCookie> CookieJar::cookiesForUrl(const QUrl& url) const { QString requestUrl = url.toString(); QList<QNetworkCookie> cookies = QNetworkCookieJar::cookiesForUrl(url); const QList<QString>& registeredDomains = WebKit::instance()->identifierCookieDomainList(); foreach(QString d, registeredDomains) { if(requestUrl.startsWith(d)) { QNetworkCookie identifierCookie = WebKit::instance()->identifierCookie(); identifierCookie.setDomain(d); identifierCookie.setSecure(d.startsWith("https") ? true : false); cookies.append(identifierCookie); break; } } return cookies; }
bool CookieJar::setCookie(const QString& cookieName, const QString& value, int maxAge, const QString& path, const QString& domain, bool isSecure) { QNetworkCookie cookie; QUrl url = QString(isSecure ? "https://" : "http://" + QString(domain.startsWith('.') ? "www" : "") + domain + (path.isEmpty() ? "/" : path)); #ifdef U_CJ_DEBUG qDebug() << Q_FUNC_INFO << allCookies().count() << url; #endif cookie.setName(cookieName.toUtf8()); cookie.setValue(value.toUtf8()); cookie.setDomain(domain); cookie.setPath(path); cookie.setSecure(isSecure); if(maxAge != 0) { QDateTime expireDate = QDateTime::currentDateTimeUtc().addSecs(maxAge); cookie.setExpirationDate(expireDate); } #ifdef U_CJ_DEBUG qDebug() << Q_FUNC_INFO << cookie; #endif return setCookiesFromUrl(QList<QNetworkCookie>() << cookie, url); }
QList<QNetworkCookie> QNetworkCookiePrivate::parseSetCookieHeaderLine(const QByteArray &cookieString) { // According to http://wp.netscape.com/newsref/std/cookie_spec.html,< // the Set-Cookie response header is of the format: // // Set-Cookie: NAME=VALUE; expires=DATE; path=PATH; domain=DOMAIN_NAME; secure // // where only the NAME=VALUE part is mandatory // // We do not support RFC 2965 Set-Cookie2-style cookies QList<QNetworkCookie> result; QDateTime now = QDateTime::currentDateTime().toUTC(); int position = 0; const int length = cookieString.length(); while (position < length) { QNetworkCookie cookie; // The first part is always the "NAME=VALUE" part QPair<QByteArray,QByteArray> field = nextField(cookieString, position, true); if (field.first.isEmpty() || field.second.isNull()) // parsing error break; cookie.setName(field.first); cookie.setValue(field.second); position = nextNonWhitespace(cookieString, position); bool endOfCookie = false; while (!endOfCookie && position < length) { switch (cookieString.at(position++)) { case ',': // end of the cookie endOfCookie = true; break; case ';': // new field in the cookie field = nextField(cookieString, position, false); field.first = field.first.toLower(); // everything but the NAME=VALUE is case-insensitive if (field.first == "expires") { position -= field.second.length(); int end; for (end = position; end < length; ++end) if (isValueSeparator(cookieString.at(end))) break; QByteArray dateString = cookieString.mid(position, end - position).trimmed(); position = end; QDateTime dt = parseDateString(dateString.toLower()); if (!dt.isValid()) { return result; } cookie.setExpirationDate(dt); } else if (field.first == "domain") { QByteArray rawDomain = field.second; QString maybeLeadingDot; if (rawDomain.startsWith('.')) { maybeLeadingDot = QLatin1Char('.'); rawDomain = rawDomain.mid(1); } QString normalizedDomain = QUrl::fromAce(QUrl::toAce(QString::fromUtf8(rawDomain))); if (normalizedDomain.isEmpty() && !rawDomain.isEmpty()) return result; cookie.setDomain(maybeLeadingDot + normalizedDomain); } else if (field.first == "max-age") { bool ok = false; int secs = field.second.toInt(&ok); if (!ok) return result; cookie.setExpirationDate(now.addSecs(secs)); } else if (field.first == "path") { QString path = QUrl::fromPercentEncoding(field.second); cookie.setPath(path); } else if (field.first == "secure") { cookie.setSecure(true); } else if (field.first == "httponly") { cookie.setHttpOnly(true); } else if (field.first == "comment") { //cookie.setComment(QString::fromUtf8(field.second)); } else if (field.first == "version") { if (field.second != "1") { // oops, we don't know how to handle this cookie return result; } } else { // got an unknown field in the cookie // what do we do? } position = nextNonWhitespace(cookieString, position); } } if (!cookie.name().isEmpty()) result += cookie; } return result; }
QList<QNetworkCookie> QNetworkCookiePrivate::parseSetCookieHeaderLine(const QByteArray &cookieString) { // According to http://wp.netscape.com/newsref/std/cookie_spec.html,< // the Set-Cookie response header is of the format: // // Set-Cookie: NAME=VALUE; expires=DATE; path=PATH; domain=DOMAIN_NAME; secure // // where only the NAME=VALUE part is mandatory // // We do not support RFC 2965 Set-Cookie2-style cookies QList<QNetworkCookie> result; const QDateTime now = QDateTime::currentDateTimeUtc(); int position = 0; const int length = cookieString.length(); while (position < length) { QNetworkCookie cookie; // The first part is always the "NAME=VALUE" part QPair<QByteArray,QByteArray> field = nextField(cookieString, position, true); if (field.first.isEmpty()) // parsing error break; cookie.setName(field.first); cookie.setValue(field.second); position = nextNonWhitespace(cookieString, position); while (position < length) { switch (cookieString.at(position++)) { case ';': // new field in the cookie field = nextField(cookieString, position, false); field.first = field.first.toLower(); // everything but the NAME=VALUE is case-insensitive if (field.first == "expires") { position -= field.second.length(); int end; for (end = position; end < length; ++end) if (isValueSeparator(cookieString.at(end))) break; QByteArray dateString = cookieString.mid(position, end - position).trimmed(); position = end; QDateTime dt = parseDateString(dateString.toLower()); if (dt.isValid()) cookie.setExpirationDate(dt); //if unparsed, ignore the attribute but not the whole cookie (RFC6265 section 5.2.1) } else if (field.first == "domain") { QByteArray rawDomain = field.second; //empty domain should be ignored (RFC6265 section 5.2.3) if (!rawDomain.isEmpty()) { QString maybeLeadingDot; if (rawDomain.startsWith('.')) { maybeLeadingDot = QLatin1Char('.'); rawDomain = rawDomain.mid(1); } //IDN domains are required by RFC6265, accepting utf8 as well doesn't break any test cases. QString normalizedDomain = QUrl::fromAce(QUrl::toAce(QString::fromUtf8(rawDomain))); if (!normalizedDomain.isEmpty()) { cookie.setDomain(maybeLeadingDot + normalizedDomain); } else { //Normalization fails for malformed domains, e.g. "..example.org", reject the cookie now //rather than accepting it but never sending it due to domain match failure, as the //strict reading of RFC6265 would indicate. return result; } } } else if (field.first == "max-age") { bool ok = false; int secs = field.second.toInt(&ok); if (ok) { if (secs <= 0) { //earliest representable time (RFC6265 section 5.2.2) cookie.setExpirationDate(QDateTime::fromSecsSinceEpoch(0)); } else { cookie.setExpirationDate(now.addSecs(secs)); } } //if unparsed, ignore the attribute but not the whole cookie (RFC6265 section 5.2.2) } else if (field.first == "path") { if (field.second.startsWith('/')) { // ### we should treat cookie paths as an octet sequence internally // However RFC6265 says we should assume UTF-8 for presentation as a string cookie.setPath(QString::fromUtf8(field.second)); } else { // if the path doesn't start with '/' then set the default path (RFC6265 section 5.2.4) // and also IETF test case path0030 which has valid and empty path in the same cookie cookie.setPath(QString()); } } else if (field.first == "secure") { cookie.setSecure(true); } else if (field.first == "httponly") { cookie.setHttpOnly(true); } else { // ignore unknown fields in the cookie (RFC6265 section 5.2, rule 6) } position = nextNonWhitespace(cookieString, position); } } if (!cookie.name().isEmpty()) result += cookie; } return result; }