fix(wallet): stop disconnected reachability polling

Skip reachability requests and stale callbacks after the wallet closes. Keep fake account reads aligned with the provider contract by echoing the requested account ID.
This commit is contained in:
Ricardo Guilherme Schmidt 2026-07-15 15:06:44 -03:00
parent ebb1b87399
commit fa1b0fd3c3
No known key found for this signature in database
GPG Key ID: 1396EA17DE132FFE
3 changed files with 42 additions and 3 deletions

View File

@ -215,13 +215,17 @@ void WalletController::applySnapshot(const WalletSnapshot& snapshot)
void WalletController::checkReachability()
{
if (m_state.sequencerAddress.isEmpty())
if (!m_state.isWalletOpen || m_state.sequencerAddress.isEmpty())
return;
QNetworkRequest request{QUrl(m_state.sequencerAddress)};
request.setTransferTimeout(4000);
QNetworkReply* reply = m_network->get(request);
connect(reply, &QNetworkReply::finished, this, [this, reply]() {
if (!m_state.isWalletOpen) {
reply->deleteLater();
return;
}
const bool receivedHttp =
reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).isValid();
const bool reachable = receivedHttp || reply->error() == QNetworkReply::NoError;

View File

@ -1,9 +1,11 @@
#include <QFile>
#include <QJsonDocument>
#include <QJsonObject>
#include <QNetworkAccessManager>
#include <QSettings>
#include <QSignalSpy>
#include <QTemporaryDir>
#include <QTimer>
#include <QtTest>
#include "FakeWalletProvider.h"
@ -56,6 +58,7 @@ private slots:
void exposesStableAccountModelRoles();
void fakeProviderImplementsConsumerContract();
void controllerOwnsUiWalletFlow();
void controllerStopsReachabilityChecksAfterDisconnect();
};
void LogosWalletProviderTest::adoptsOpenWalletAndCachesSnapshots()
@ -358,6 +361,8 @@ void LogosWalletProviderTest::fakeProviderImplementsConsumerContract()
QCOMPARE(provider.snapshot(true).accounts.size(), 1);
QVERIFY(provider.lastForceRefresh);
QCOMPARE(provider.readPublicAccount(ACCOUNT_B).accountId, ACCOUNT_B);
QCOMPARE(provider.readCalls, 1);
WalletTransaction transaction { PROGRAM_ID, { ACCOUNT_A }, { true }, { 9 } };
QVERIFY(provider.submitPublicTransaction(transaction).accepted());
QCOMPARE(provider.lastTransaction.instruction, transaction.instruction);
@ -414,6 +419,34 @@ void LogosWalletProviderTest::controllerOwnsUiWalletFlow()
settings.clear();
}
void LogosWalletProviderTest::controllerStopsReachabilityChecksAfterDisconnect()
{
const QString settingsApplication = QStringLiteral("WalletReachabilityTest");
QSettings settings(QStringLiteral("Logos"), settingsApplication);
settings.clear();
FakeWalletProvider provider;
provider.connectResult.snapshot.sequencerAddress = QStringLiteral("http://127.0.0.1:1");
WalletController controller(provider, settingsApplication);
auto* network = controller.findChild<QNetworkAccessManager*>();
QVERIFY(network);
QSignalSpy finished(network, &QNetworkAccessManager::finished);
QVERIFY(controller.open());
QTRY_VERIFY_WITH_TIMEOUT(!finished.isEmpty(), 1000);
controller.disconnect();
finished.clear();
auto* timer = controller.findChild<QTimer*>();
QVERIFY(timer);
timer->setInterval(1);
controller.start();
QTest::qWait(50);
QCOMPARE(finished.count(), 0);
settings.clear();
}
QTEST_GUILESS_MAIN(LogosWalletProviderTest)
#include "LogosWalletProviderTest.moc"

View File

@ -55,10 +55,12 @@ public:
return createAccountResult;
}
WalletAccountRead readPublicAccount(const QString&) const override
WalletAccountRead readPublicAccount(const QString& accountId) const override
{
++readCalls;
return readResult;
WalletAccountRead result = readResult;
result.accountId = accountId;
return result;
}
WalletSubmission submitPublicTransaction(