feat(lite): M2b-1/2 — shared-bridge refactor + sync/refresh into WalletState
Shared-bridge refactor (litelib is a global singleton; every LiteClientBridge calls litelib_shutdown() on destruction, so services must not each own one): - LiteWalletLifecycleService, LiteWalletGateway, LiteSyncService now take a non-owning LiteClientBridge*; LiteWalletController owns the single bridge and passes &bridge_. Sync + controller refresh: - LiteSyncService::startSync executes the real "sync" command (was a stub). - LiteWalletController: startSync() (auto-fires when a wallet becomes ready) and refreshWalletState(WalletState&) — polls syncstatus, runs gateway.refresh(), maps the bundle, applies balances/addresses/transactions/sync into WalletState. Tests: - fake_lite_backend.h returns command-shaped JSON (per tests/fixtures/lite/result_parsers.json). - testLiteWalletControllerRefreshPopulatesState drives the full path against the fake. - Surfaced + worked around a real integration issue: parseLiteInfoResponse requires latest_block_height and the gateway aborts the whole refresh on the first command's parse failure (fragile vs partial backend responses; hardening tracked for M2b-3). Verified: ctest green; lite+backend, full-node, lite-no-backend apps + lite_smoke build clean. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -166,11 +166,11 @@ LiteSyncRecoveryDecision evaluateLiteSyncRecovery(const LiteSyncRecoveryInput& i
|
||||
|
||||
LiteSyncService::LiteSyncService(WalletCapabilities capabilities,
|
||||
LiteConnectionSettings connectionSettings,
|
||||
LiteClientBridge bridge,
|
||||
LiteClientBridge* bridge,
|
||||
LiteSyncServiceOptions options)
|
||||
: capabilities_(capabilities),
|
||||
connectionSettings_(std::move(connectionSettings)),
|
||||
bridge_(std::move(bridge)),
|
||||
bridge_(bridge),
|
||||
options_(options)
|
||||
{
|
||||
}
|
||||
@@ -179,7 +179,7 @@ LiteSyncAvailability LiteSyncService::availability() const
|
||||
{
|
||||
if (!isLiteBuild(capabilities_)) return LiteSyncAvailability::UnsupportedBuild;
|
||||
if (!supportsLiteBackend(capabilities_)) return LiteSyncAvailability::BackendUnavailable;
|
||||
if (!bridge_.available()) return LiteSyncAvailability::BridgeUnavailable;
|
||||
if (!bridge_ || !bridge_->available()) return LiteSyncAvailability::BridgeUnavailable;
|
||||
if (!selectLiteServer(connectionSettings_).ok) return LiteSyncAvailability::NoUsableServer;
|
||||
if (!options_.allowSyncStatusBridgeCalls) return LiteSyncAvailability::BridgeCallsDisabled;
|
||||
return LiteSyncAvailability::Ready;
|
||||
@@ -199,7 +199,7 @@ LiteSyncPlan LiteSyncService::planStartSync(const LiteSyncStartRequest& request)
|
||||
return makePlan(
|
||||
LiteSyncOperation::StartSync,
|
||||
request.serverUrl,
|
||||
false,
|
||||
options_.allowSyncStatusBridgeCalls,
|
||||
request.mode,
|
||||
request.forceRescan,
|
||||
request.afterRestore);
|
||||
@@ -229,9 +229,21 @@ LiteSyncStartResult LiteSyncService::startSync(const LiteSyncStartRequest& reque
|
||||
return blockedStartResult(plan, status());
|
||||
}
|
||||
|
||||
return blockedStartResult(
|
||||
plan,
|
||||
makeSyncScaffoldStatus(WalletBackendState::Unavailable, "lite sync start execution is not implemented"));
|
||||
LiteSyncStartResult result;
|
||||
result.plan = plan;
|
||||
result.attempted = true;
|
||||
|
||||
const auto bridgeCall = bridge_->execute(plan.command, plan.args);
|
||||
if (!bridgeCall.ok) {
|
||||
result.status = makeSyncScaffoldStatus(WalletBackendState::Error, "lite sync start bridge call failed");
|
||||
result.error = result.status.message;
|
||||
return result;
|
||||
}
|
||||
|
||||
result.ok = true;
|
||||
result.syncStarted = true;
|
||||
result.status = makeSyncScaffoldStatus(WalletBackendState::Syncing, "lite sync started");
|
||||
return result;
|
||||
}
|
||||
|
||||
LiteSyncStatusResult LiteSyncService::pollSyncStatus(const LiteSyncStatusRequest& request)
|
||||
@@ -245,7 +257,7 @@ LiteSyncStatusResult LiteSyncService::pollSyncStatus(const LiteSyncStatusRequest
|
||||
result.plan = plan;
|
||||
result.attempted = true;
|
||||
|
||||
const auto bridgeCall = bridge_.execute(plan.command, plan.args);
|
||||
const auto bridgeCall = bridge_->execute(plan.command, plan.args);
|
||||
result.bridgeResponseRedacted = bridgeCall.ok || !bridgeCall.error.empty() ? "<redacted>" : "<empty>";
|
||||
if (!bridgeCall.ok) {
|
||||
result.status = makeSyncScaffoldStatus(WalletBackendState::Error, "lite syncstatus bridge call failed");
|
||||
@@ -334,7 +346,7 @@ WalletBackendStatus LiteSyncService::statusFor(LiteSyncAvailability availability
|
||||
case LiteSyncAvailability::BridgeUnavailable:
|
||||
return makeSyncScaffoldStatus(
|
||||
WalletBackendState::Unavailable,
|
||||
detail.empty() ? bridge_.unavailableReason() : detail);
|
||||
detail.empty() ? (bridge_ ? bridge_->unavailableReason() : "lite bridge is unavailable") : detail);
|
||||
case LiteSyncAvailability::BridgeCallsDisabled:
|
||||
return makeSyncScaffoldStatus(
|
||||
WalletBackendState::Unavailable,
|
||||
|
||||
Reference in New Issue
Block a user