From 08cb84701a1e2b3c161fad0e60836e6b183e2454 Mon Sep 17 00:00:00 2001 From: Uwe Klotz Date: Fri, 9 Sep 2022 20:26:41 +0200 Subject: [PATCH 1/2] WebTask: Document intermediate state change --- src/network/webtask.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/network/webtask.cpp b/src/network/webtask.cpp index 725f570f1f5..16a008eaaac 100644 --- a/src/network/webtask.cpp +++ b/src/network/webtask.cpp @@ -205,11 +205,15 @@ void WebTask::slotStart(int timeoutMillis, int delayMillis) { auto* const pNetworkAccessManager = m_networkAccessManagerWeakPtr.data(); VERIFY_OR_DEBUG_ASSERT(pNetworkAccessManager) { + // Internally switch the state to pending as a prerequisite before + // invoking onNetworkError(). This is only required for technical + // reasons and the intermediate state will never become visible. m_state = State::Pending; onNetworkError( QNetworkReply::NetworkSessionFailedError, tr("No network access"), WebResponseWithContent{}); + DEBUG_ASSERT(m_state == State::Failed); return; } DEBUG_ASSERT_QOBJECT_THREAD_AFFINITY(pNetworkAccessManager); From bf31e6a0c2d4b15ae9fbb000a2fb31f32c1efae3 Mon Sep 17 00:00:00 2001 From: Uwe Klotz Date: Fri, 9 Sep 2022 21:04:12 +0200 Subject: [PATCH 2/2] NetworkTask: Distinguish implicit abort by timeout from explicit abort --- src/network/networktask.cpp | 7 ++++--- src/network/networktask.h | 6 +++++- src/network/webtask.cpp | 6 +++--- src/network/webtask.h | 10 ++++++++-- 4 files changed, 20 insertions(+), 9 deletions(-) diff --git a/src/network/networktask.cpp b/src/network/networktask.cpp index a78eb57dfc0..f651eb99bca 100644 --- a/src/network/networktask.cpp +++ b/src/network/networktask.cpp @@ -51,10 +51,11 @@ void NetworkTask::invokeAbort() { QMetaObject::invokeMethod( this, #if QT_VERSION < QT_VERSION_CHECK(5, 10, 0) - "slotAbort" + "slotAbort", + Q_ARG(bool, false) #else [this] { - this->slotAbort(); + this->slotAbort(false); } #endif ); @@ -62,7 +63,7 @@ void NetworkTask::invokeAbort() { void NetworkTask::abort() { DEBUG_ASSERT_QOBJECT_THREAD_AFFINITY(this); - slotAbort(); + slotAbort(false); } void NetworkTask::emitAborted( diff --git a/src/network/networktask.h b/src/network/networktask.h index 16156ae2f91..90e9946777a 100644 --- a/src/network/networktask.h +++ b/src/network/networktask.h @@ -85,7 +85,11 @@ class NetworkTask : public QObject { int timeoutMillis = kNoTimeout, int delayMillis = kNoStartDelay) = 0; /// See also: invokeAbort() - virtual void slotAbort() = 0; + /// + /// timedOut = false: The abort has been triggered explicitly. + /// timedOut = true: The abort has been triggered implicitly + /// after a client-side timeout expired. + virtual void slotAbort(bool timedOut) = 0; signals: /// The receiver is responsible for deleting the task in the diff --git a/src/network/webtask.cpp b/src/network/webtask.cpp index 16a008eaaac..6b9242a7c5e 100644 --- a/src/network/webtask.cpp +++ b/src/network/webtask.cpp @@ -260,7 +260,7 @@ void WebTask::slotStart(int timeoutMillis, int delayMillis) { Qt::UniqueConnection); } -void WebTask::slotAbort() { +void WebTask::slotAbort(bool timedOut) { DEBUG_ASSERT_QOBJECT_THREAD_AFFINITY(this); if (!isBusy()) { DEBUG_ASSERT(m_timeoutTimerId == kInvalidTimerId); @@ -316,7 +316,7 @@ void WebTask::slotAbort() { // this scope. const auto pendingNetworkReplyDeleter = ScopedDeleteLater(pPendingNetworkReply); m_pendingNetworkReplyWeakPtr.clear(); - doNetworkReplyAborted(pPendingNetworkReply); + doNetworkReplyAborted(pPendingNetworkReply, timedOut); } m_state = State::Aborted; @@ -352,7 +352,7 @@ void WebTask::timerEvent(QTimerEvent* event) { << "Aborting after timed out"; // Trigger the regular abort workflow after a client-side // timeout occurred - slotAbort(); + slotAbort(true); } void WebTask::slotNetworkReplyFinished() { diff --git a/src/network/webtask.h b/src/network/webtask.h index da9662ca9df..4e3ea27b522 100644 --- a/src/network/webtask.h +++ b/src/network/webtask.h @@ -138,7 +138,7 @@ class WebTask : public NetworkTask { void slotStart( int timeoutMillis = kNoTimeout, int delayMillis = kNoStartDelay) override; - void slotAbort() override; + void slotAbort(bool timedOut) override; private slots: void slotNetworkReplyFinished(); @@ -192,8 +192,14 @@ class WebTask : public NetworkTask { int parentTimeoutMillis) = 0; /// Optional: Do something after aborted. + /// + /// The parameter `timedOut` is set to `true` if the abort has + /// been triggered implicitly by a client-side timeout. + /// + /// See also: `NetworkTask::slotAbort()` virtual void doNetworkReplyAborted( - QNetworkReply* abortedNetworkReply) { + QNetworkReply* abortedNetworkReply, + bool timedOut) { Q_UNUSED(abortedNetworkReply); }