summaryrefslogtreecommitdiffstats
path: root/src/network/access/qhttpthreaddelegate.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/network/access/qhttpthreaddelegate.cpp')
-rw-r--r--src/network/access/qhttpthreaddelegate.cpp67
1 files changed, 64 insertions, 3 deletions
diff --git a/src/network/access/qhttpthreaddelegate.cpp b/src/network/access/qhttpthreaddelegate.cpp
index 81410a4635..99f9376766 100644
--- a/src/network/access/qhttpthreaddelegate.cpp
+++ b/src/network/access/qhttpthreaddelegate.cpp
@@ -39,6 +39,7 @@
**
****************************************************************************/
+//#define QHTTPTHREADDELEGATE_DEBUG
#include "qhttpthreaddelegate_p.h"
#include <QThread>
@@ -78,6 +79,11 @@ static QNetworkReply::NetworkError statusCodeFromHttp(int httpStatusCode, const
code = QNetworkReply::ProxyAuthenticationRequiredError;
break;
+ case 418: // I'm a teapot
+ code = QNetworkReply::ProtocolInvalidOperationError;
+ break;
+
+
default:
if (httpStatusCode > 500) {
// some kind of server error
@@ -131,6 +137,8 @@ static QByteArray makeCacheKey(QUrl &url, QNetworkProxy *proxy)
result = key.toEncoded();
}
}
+#else
+ Q_UNUSED(proxy)
#endif
return "http-connection:" + result;
@@ -141,8 +149,13 @@ class QNetworkAccessCachedHttpConnection: public QHttpNetworkConnection,
{
// Q_OBJECT
public:
+#ifdef QT_NO_BEARERMANAGEMENT
QNetworkAccessCachedHttpConnection(const QString &hostName, quint16 port, bool encrypt)
: QHttpNetworkConnection(hostName, port, encrypt)
+#else
+ QNetworkAccessCachedHttpConnection(const QString &hostName, quint16 port, bool encrypt, QSharedPointer<QNetworkSession> networkSession)
+ : QHttpNetworkConnection(hostName, port, encrypt, /*parent=*/0, networkSession)
+#endif
{
setExpires(true);
setShareable(true);
@@ -190,12 +203,16 @@ QHttpThreadDelegate::QHttpThreadDelegate(QObject *parent) :
, downloadBuffer(0)
, httpConnection(0)
, httpReply(0)
+ , synchronousRequestLoop(0)
{
}
// This is invoked as BlockingQueuedConnection from QNetworkAccessHttpBackend in the user thread
void QHttpThreadDelegate::startRequestSynchronously()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::startRequestSynchronously() thread=" << QThread::currentThreadId();
+#endif
synchronous = true;
QEventLoop synchronousRequestLoop;
@@ -210,12 +227,18 @@ void QHttpThreadDelegate::startRequestSynchronously()
connections.localData()->releaseEntry(cacheKey);
connections.setLocalData(0);
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::startRequestSynchronously() thread=" << QThread::currentThreadId() << "finished";
+#endif
}
// This is invoked as QueuedConnection from QNetworkAccessHttpBackend in the user thread
void QHttpThreadDelegate::startRequest()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::startRequest() thread=" << QThread::currentThreadId();
+#endif
// Check QThreadStorage for the QNetworkAccessCache
// If not there, create this connection cache
if (!connections.hasLocalData()) {
@@ -226,11 +249,13 @@ void QHttpThreadDelegate::startRequest()
QUrl urlCopy = httpRequest.url();
urlCopy.setPort(urlCopy.port(ssl ? 443 : 80));
+#ifndef QT_NO_NETWORKPROXY
if (transparentProxy.type() != QNetworkProxy::NoProxy)
cacheKey = makeCacheKey(urlCopy, &transparentProxy);
else if (cacheProxy.type() != QNetworkProxy::NoProxy)
cacheKey = makeCacheKey(urlCopy, &cacheProxy);
else
+#endif
cacheKey = makeCacheKey(urlCopy, 0);
@@ -239,10 +264,14 @@ void QHttpThreadDelegate::startRequest()
if (httpConnection == 0) {
// no entry in cache; create an object
// the http object is actually a QHttpNetworkConnection
+#ifdef QT_NO_BEARERMANAGEMENT
httpConnection = new QNetworkAccessCachedHttpConnection(urlCopy.host(), urlCopy.port(), ssl);
+#else
+ httpConnection = new QNetworkAccessCachedHttpConnection(urlCopy.host(), urlCopy.port(), ssl, networkSession);
+#endif
#ifndef QT_NO_OPENSSL
// Set the QSslConfiguration from this QNetworkRequest.
- if (ssl) {
+ if (ssl && incomingSslConfiguration != QSslConfiguration::defaultConfiguration()) {
httpConnection->setSslConfiguration(incomingSslConfiguration);
}
#endif
@@ -300,15 +329,22 @@ void QHttpThreadDelegate::startRequest()
// This gets called from the user thread or by the synchronous HTTP timeout timer
void QHttpThreadDelegate::abortRequest()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::abortRequest() thread=" << QThread::currentThreadId() << "sync=" << synchronous;
+#endif
if (httpReply) {
delete httpReply;
httpReply = 0;
- this->deleteLater();
}
// Got aborted by the timeout timer
- if (synchronous)
+ if (synchronous) {
incomingErrorCode = QNetworkReply::TimeoutError;
+ QMetaObject::invokeMethod(synchronousRequestLoop, "quit", Qt::QueuedConnection);
+ } else {
+ //only delete this for asynchronous mode or QNetworkAccessHttpBackend will crash - see QNetworkAccessHttpBackend::postRequest()
+ this->deleteLater();
+ }
}
void QHttpThreadDelegate::readyReadSlot()
@@ -329,6 +365,9 @@ void QHttpThreadDelegate::finishedSlot()
qWarning() << "QHttpThreadDelegate::finishedSlot: HTTP reply had already been deleted, internal problem. Please report.";
return;
}
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::finishedSlot() thread=" << QThread::currentThreadId() << "result=" << httpReply->statusCode();
+#endif
// If there is still some data left emit that now
while (httpReply->readAnyAvailable()) {
@@ -358,6 +397,9 @@ void QHttpThreadDelegate::finishedSlot()
void QHttpThreadDelegate::synchronousFinishedSlot()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::synchronousFinishedSlot() thread=" << QThread::currentThreadId() << "result=" << httpReply->statusCode();
+#endif
if (httpReply->statusCode() >= 400) {
// it's an error reply
QString msg = QLatin1String(QT_TRANSLATE_NOOP("QNetworkReply",
@@ -379,6 +421,9 @@ void QHttpThreadDelegate::finishedWithErrorSlot(QNetworkReply::NetworkError erro
qWarning() << "QHttpThreadDelegate::finishedWithErrorSlot: HTTP reply had already been deleted, internal problem. Please report.";
return;
}
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::finishedWithErrorSlot() thread=" << QThread::currentThreadId() << "error=" << errorCode << detail;
+#endif
#ifndef QT_NO_OPENSSL
if (ssl)
@@ -396,6 +441,9 @@ void QHttpThreadDelegate::finishedWithErrorSlot(QNetworkReply::NetworkError erro
void QHttpThreadDelegate::synchronousFinishedWithErrorSlot(QNetworkReply::NetworkError errorCode, const QString &detail)
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::synchronousFinishedWithErrorSlot() thread=" << QThread::currentThreadId() << "error=" << errorCode << detail;
+#endif
incomingErrorCode = errorCode;
incomingErrorDetail = detail;
@@ -411,6 +459,10 @@ static void downloadBufferDeleter(char *ptr)
void QHttpThreadDelegate::headerChangedSlot()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::headerChangedSlot() thread=" << QThread::currentThreadId();
+#endif
+
#ifndef QT_NO_OPENSSL
if (ssl)
emit sslConfigurationChanged(httpReply->sslConfiguration());
@@ -443,6 +495,9 @@ void QHttpThreadDelegate::headerChangedSlot()
void QHttpThreadDelegate::synchronousHeaderChangedSlot()
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::synchronousHeaderChangedSlot() thread=" << QThread::currentThreadId();
+#endif
// Store the information we need in this object, the QNetworkAccessHttpBackend will later read it
incomingHeaders = httpReply->header();
incomingStatusCode = httpReply->statusCode();
@@ -487,6 +542,9 @@ void QHttpThreadDelegate::sslErrorsSlot(const QList<QSslError> &errors)
void QHttpThreadDelegate::synchronousAuthenticationRequiredSlot(const QHttpNetworkRequest &request, QAuthenticator *a)
{
Q_UNUSED(request);
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::synchronousAuthenticationRequiredSlot() thread=" << QThread::currentThreadId();
+#endif
// Ask the credential cache
QNetworkAuthenticationCredential credential = authenticationManager->fetchCachedCredentials(httpRequest.url(), a);
@@ -502,6 +560,9 @@ void QHttpThreadDelegate::synchronousAuthenticationRequiredSlot(const QHttpNetwo
#ifndef QT_NO_NETWORKPROXY
void QHttpThreadDelegate::synchronousProxyAuthenticationRequiredSlot(const QNetworkProxy &p, QAuthenticator *a)
{
+#ifdef QHTTPTHREADDELEGATE_DEBUG
+ qDebug() << "QHttpThreadDelegate::synchronousProxyAuthenticationRequiredSlot() thread=" << QThread::currentThreadId();
+#endif
// Ask the credential cache
QNetworkAuthenticationCredential credential = authenticationManager->fetchCachedProxyCredentials(p, a);
if (!credential.isNull()) {