fix: prevent staking dashboard hang when exposure flag not cached

isPagedExposuresUsed() called storageCache.getEntry() which suspends
forever if the entry doesn't exist. The flag is only written by
ValidatorExposureUpdater (staking detail flow), so the dashboard
would hang indefinitely waiting for it.

Check cache first with isFullKeyInCache() and default to paged
exposures when the flag is absent. Also remove debug log statements.
This commit is contained in:
2026-02-27 13:41:26 +03:00
parent 2d0d46688e
commit 894e5dac22
5 changed files with 10 additions and 21 deletions
@@ -130,7 +130,6 @@ class RealStakingDashboardUpdateSystem(
val stats = runCatching {
stakingStatsDataSource.fetchStakingStats(stakingAccounts, stakingChains)
}.getOrElse {
Log.d("StakingDashboardUpdateSystem", "Failed to fetch staking stats after retries", it)
emptyMap()
}
@@ -405,6 +405,16 @@ class StakingRepositoryImpl(
}
private suspend fun isPagedExposuresUsed(chainId: ChainId): Boolean {
// Check if the flag is already in cache before calling getEntry, which suspends
// forever if the entry doesn't exist. The flag is written by ValidatorExposureUpdater
// which only runs in the staking detail flow, not the dashboard.
val isCached = storageCache.isFullKeyInCache(ValidatorExposureUpdater.STORAGE_KEY_PAGED_EXPOSURES, chainId)
if (!isCached) {
// Default to paged exposures (modern chains). If paged returns empty,
// getElectedValidatorsExposure will return an empty map gracefully.
return true
}
val isPagedExposuresValue = storageCache.getEntry(ValidatorExposureUpdater.STORAGE_KEY_PAGED_EXPOSURES, chainId)
return ValidatorExposureUpdater.decodeIsPagedExposuresValue(isPagedExposuresValue.content)
@@ -225,14 +225,6 @@ class RealStakingDashboardInteractor(
noPriceStakingDashboard: NoPriceStakingDashboard,
assets: Map<FullChainAssetId, Asset>,
): ExtendedLoadingState<StakingDashboard> {
Log.d(
"StakingDashboard",
"addPricesToDashboard: hasStake=${noPriceStakingDashboard.hasStake.size}, " +
"noStake=${noPriceStakingDashboard.noStake.size}, " +
"notYetResolved=${noPriceStakingDashboard.notYetResolved.size}, " +
"assets=${assets.size}"
)
val hasStakeOptions = noPriceStakingDashboard.hasStake.mapNotNull { addPriceToHasStakeItem(it, assets) }
val noStakeOptions = noPriceStakingDashboard.noStake.mapNotNull { addAssetInfoToNoStakeItem(it, assets) }
val notYetResolvedOptions = noPriceStakingDashboard.notYetResolved.mapNotNull { addAssetInfoToNotYetResolvedItem(it, assets) }