From be6644c1f254cce796c43d7c1eae3ae794bb77be Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?M=C3=A5rten=20Nordheim?= Date: Tue, 5 Mar 2024 14:36:09 +0100 Subject: Http: fix issues after early abort() There were a few issues to deal with. One of them was that we would print a warning about an internal error if we tried to *set* an error on the reply after it had been cancelled. That's kind of unavoidable since these things happen in different threads, so just ignore the error if we have been cancelled. The other issue was that, for a request with data, we will buffer the data to send, and _only then_ do we start the request. This happens asynchronously, so the user can abort the request before it has finished buffering. Once it finished buffering it would set the state of the request to "Working", ignoring that it was already marked "Finished". Fixes: QTBUG-118209 Fixes: QTBUG-36127 Pick-to: 6.7 6.6 Change-Id: Idbf1fd8a80530d802bee04c4b0a6783cba4992d3 Reviewed-by: Edward Welbourne --- .../access/qnetworkreply/tst_qnetworkreply.cpp | 35 ++++++++++++++++++++++ 1 file changed, 35 insertions(+) (limited to 'tests/auto/network/access/qnetworkreply/tst_qnetworkreply.cpp') diff --git a/tests/auto/network/access/qnetworkreply/tst_qnetworkreply.cpp b/tests/auto/network/access/qnetworkreply/tst_qnetworkreply.cpp index 8d2a5b7a61..2ecccb0019 100644 --- a/tests/auto/network/access/qnetworkreply/tst_qnetworkreply.cpp +++ b/tests/auto/network/access/qnetworkreply/tst_qnetworkreply.cpp @@ -559,6 +559,8 @@ private Q_SLOTS: void qtbug68821proxyError_data(); void qtbug68821proxyError(); + void abortAndError(); + // NOTE: This test must be last! void parentingRepliesToTheApp(); private: @@ -10421,6 +10423,39 @@ void tst_QNetworkReply::qtbug68821proxyError() QCOMPARE(spy.at(0).at(0), error); } +void tst_QNetworkReply::abortAndError() +{ + const QByteArray response = + R"(HTTP/1.0 500 Internal Server Error +Content-Length: 12 +Content-Type: text/plain + +Hello World!)"_ba; + + MiniHttpServer server(response); + + QNetworkAccessManager manager; + QNetworkRequest req(QUrl("http://127.0.0.1:" + QString::number(server.serverPort()))); + std::unique_ptr reply(manager.post(req, "my data goes here"_ba)); + QSignalSpy errorSignal(reply.get(), &QNetworkReply::errorOccurred); + QSignalSpy finishedSignal(reply.get(), &QNetworkReply::finished); + + reply->abort(); + + // We don't want to print this warning in this case because it is impossible + // for users to avoid it. + QTest::failOnWarning("QNetworkReplyImplPrivate::error: Internal problem, this method must only " + "be called once."); + // Process any signals from the http thread: + QTest::qWait(1s); + if (QTest::currentTestFailed()) + return; + + QCOMPARE(finishedSignal.count(), 1); + QCOMPARE(errorSignal.count(), 1); + QCOMPARE(reply->error(), QNetworkReply::OperationCanceledError); +} + // NOTE: This test must be last testcase in tst_qnetworkreply! void tst_QNetworkReply::parentingRepliesToTheApp() { -- cgit v1.2.3