From bd7218fa794ae4952ad2d956ea507abe3066cd6e Mon Sep 17 00:00:00 2001 From: Tangem Date: Wed, 23 Mar 2022 21:27:16 +0300 Subject: [PATCH] Updated on 2026-08-14 --- .../com/tangem/tap/domain/TapWalletManager.kt | 60 ++++++++++++++++--- .../tap/features/wallet/redux/WalletState.kt | 7 --- .../redux/middlewares/WalletMiddleware.kt | 34 +++-------- .../wallet/redux/reducers/WalletReducer.kt | 24 -------- 4 files changed, 62 insertions(+), 63 deletions(-) diff --git a/app/src/main/java/com/tangem/tap/domain/TapWalletManager.kt b/app/src/main/java/com/tangem/tap/domain/TapWalletManager.kt index 55fc7f2154..5af87ae3a8 100644 --- a/app/src/main/java/com/tangem/tap/domain/TapWalletManager.kt +++ b/app/src/main/java/com/tangem/tap/domain/TapWalletManager.kt @@ -27,22 +27,42 @@ import com.tangem.tap.network.coinmarketcap.CoinMarketCapService import com.tangem.tap.scope import com.tangem.tap.store import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.delay import kotlinx.coroutines.launch import kotlinx.coroutines.withContext import java.math.BigDecimal class TapWalletManager { - private val coinMarketCapService = CoinMarketCapService() - - private val blockchainSdkConfig by lazy { - store.state.globalState.configManager?.config?.blockchainSdkConfig ?: BlockchainSdkConfig() - } val walletManagerFactory: WalletManagerFactory by lazy { WalletManagerFactory(blockchainSdkConfig) } + private val coinMarketCapService = CoinMarketCapService() + private val blockchainSdkConfig by lazy { + store.state.globalState.configManager?.config?.blockchainSdkConfig ?: BlockchainSdkConfig() + } + + private val throttlingDuration = 10000 + private val throttlingWalletManagers: MutableMap = mutableMapOf() + + private val throttlingFiatRateDuration = 60000 + private val throttlingFiatRate: MutableMap = mutableMapOf() + suspend fun loadWalletData(walletManager: WalletManager) { - handleUpdateWalletResult(walletManager.safeUpdate(), walletManager) + val result = if (managerIsStillThrottled(walletManager)) { + delay(200) + Result.Success(walletManager.wallet) + } else { + val blockchain = walletManager.wallet.blockchain + val now = System.currentTimeMillis() + val throttledUpTo = throttlingWalletManagers[blockchain] ?: 0L + if (throttledUpTo == 0L || throttledUpTo < now) { + val newTime = now + throttlingDuration + throttlingWalletManagers[blockchain] = newTime + } + walletManager.safeUpdate() + } + handleUpdateWalletResult(result, walletManager) } suspend fun updateWallet(walletManager: WalletManager) { @@ -72,7 +92,21 @@ class TapWalletManager { suspend fun loadFiatRate(fiatCurrency: FiatCurrencyName, currencies: List) { val results = mutableListOf?>>() - currencies.forEach { + val toUpdate = currencies.mapNotNull { + if (fiatRateIsStillThrottled(it)) { + null + } else { + val now = System.currentTimeMillis() + val throttledUpTo = throttlingFiatRate[it] ?: 0L + if (throttledUpTo == 0L || throttledUpTo < now) { + val newTime = now + throttlingFiatRateDuration + throttlingFiatRate[it] = newTime + } + it + } + } + + toUpdate.forEach { results.add(it to coinMarketCapService.getRate(it.currencySymbol, fiatCurrency)) } handleFiatRatesResult(results) @@ -301,6 +335,18 @@ class TapWalletManager { } } } + + private fun managerIsStillThrottled(walletManager: WalletManager): Boolean { + val inThrottlingUpTo = throttlingWalletManagers[walletManager.wallet.blockchain] ?: return false + val diff = System.currentTimeMillis() - inThrottlingUpTo + return diff < 0 + } + + private fun fiatRateIsStillThrottled(currency: Currency): Boolean { + val inThrottlingUpTo = throttlingFiatRate[currency] ?: return false + val diff = System.currentTimeMillis() - inThrottlingUpTo + return diff < 0 + } } fun Wallet.getFirstToken(): Token? { diff --git a/app/src/main/java/com/tangem/tap/features/wallet/redux/WalletState.kt b/app/src/main/java/com/tangem/tap/features/wallet/redux/WalletState.kt index e8521c17d9..58dfedb6ce 100644 --- a/app/src/main/java/com/tangem/tap/features/wallet/redux/WalletState.kt +++ b/app/src/main/java/com/tangem/tap/features/wallet/redux/WalletState.kt @@ -34,7 +34,6 @@ data class WalletState( val mainWarningsList: List = mutableListOf(), val wallets: List = emptyList(), val walletManagers: List = emptyList(), - val walletManagersThrottling: MutableMap = mutableMapOf(), val isMultiwalletAllowed: Boolean = false, val cardCurrency: CryptoCurrencyName? = null, val selectedWallet: Currency? = null, @@ -182,12 +181,6 @@ data class WalletState( newWalletManagers.filterNot { this.blockchains.contains(it.wallet.blockchain) } return copy(walletManagers = updatedWalletManagers) } - - fun isThrottling(walletManager: WalletManager): Boolean { - val inThrottlingUpTo = walletManagersThrottling[walletManager.wallet.blockchain] ?: return false - val diff = System.currentTimeMillis() - inThrottlingUpTo - return diff < 0 - } } sealed class WalletDialog : StateDialog { diff --git a/app/src/main/java/com/tangem/tap/features/wallet/redux/middlewares/WalletMiddleware.kt b/app/src/main/java/com/tangem/tap/features/wallet/redux/middlewares/WalletMiddleware.kt index 28abc867e9..e48b76c1a6 100644 --- a/app/src/main/java/com/tangem/tap/features/wallet/redux/middlewares/WalletMiddleware.kt +++ b/app/src/main/java/com/tangem/tap/features/wallet/redux/middlewares/WalletMiddleware.kt @@ -29,7 +29,9 @@ import com.tangem.tap.network.NetworkStateChanged import com.tangem.tap.scope import com.tangem.tap.store import com.tangem.tap.tangemSdkManager -import kotlinx.coroutines.* +import kotlinx.coroutines.async +import kotlinx.coroutines.awaitAll +import kotlinx.coroutines.launch import org.rekotlin.Action import org.rekotlin.DispatchFunction import org.rekotlin.Middleware @@ -59,32 +61,14 @@ class WalletMiddleware { is WalletAction.Warnings -> warningsMiddleware.handle(action, globalState) is WalletAction.MultiWallet -> multiWalletMiddleware.handle(action, walletState, globalState) is WalletAction.LoadWallet -> { - if (action.blockchain == null) { - val throttledWalletManagers = walletState.walletManagers.filter { walletState.isThrottling(it) } - val freeWalletManagers = walletState.walletManagers.filter { !walletState.isThrottling(it) } - scope.launch { - freeWalletManagers.map { walletManager -> + scope.launch { + if (action.blockchain == null) { + walletState.walletManagers.map { walletManager -> async { globalState.tapWalletManager.loadWalletData(walletManager) } }.awaitAll() - - delay(500) - launch(Dispatchers.Main) { - throttledWalletManagers.forEach { store.dispatch(WalletAction.LoadWallet.Success(it.wallet)) } - } - } - - } else { - val walletManager = walletState.getWalletManager(action.blockchain) ?: return - - scope.launch { - if (walletState.isThrottling(walletManager)) { - delay(500) - launch(Dispatchers.Main) { - store.dispatch(WalletAction.LoadWallet.Success(walletManager.wallet)) - } - } else { - globalState.tapWalletManager.loadWalletData(walletManager) - } + } else { + val walletManager = walletState.getWalletManager(action.blockchain) + walletManager?.let { globalState.tapWalletManager.loadWalletData(it) } } } } diff --git a/app/src/main/java/com/tangem/tap/features/wallet/redux/reducers/WalletReducer.kt b/app/src/main/java/com/tangem/tap/features/wallet/redux/reducers/WalletReducer.kt index 4077d877ee..960a4e76b7 100644 --- a/app/src/main/java/com/tangem/tap/features/wallet/redux/reducers/WalletReducer.kt +++ b/app/src/main/java/com/tangem/tap/features/wallet/redux/reducers/WalletReducer.kt @@ -94,19 +94,6 @@ private fun internalReduce(action: Action, state: AppState): WalletState { } is WalletAction.LoadWallet -> { if (action.blockchain == null) { - // update throttling - val updatedThrottling = newState.walletManagersThrottling - newState.walletManagers.forEach { - val now = System.currentTimeMillis() - val currentThrottling = newState.walletManagersThrottling[it.wallet.blockchain] ?: 0L - if (currentThrottling == 0L || currentThrottling < now) { - val newThrottlingUpTo = now + newState.throttlingDuration - updatedThrottling[it.wallet.blockchain] = newThrottlingUpTo - } - - } - newState = newState.copy(walletManagersThrottling = updatedThrottling) - val wallets = newState.wallets.map { wallet -> wallet.copy( currencyData = wallet.currencyData.copy( @@ -125,17 +112,6 @@ private fun internalReduce(action: Action, state: AppState): WalletState { } else { val walletManager = newState.getWalletManager(action.blockchain) ?: return newState val blockchain = walletManager.wallet.blockchain - - // update throttling - val now = System.currentTimeMillis() - val currentThrottling = newState.walletManagersThrottling[blockchain] ?: 0L - if (currentThrottling == 0L || currentThrottling < now) { - val newThrottlingUpTo = now + newState.throttlingDuration - val newMap = newState.walletManagersThrottling.toMutableMap() - newMap[blockchain] = newThrottlingUpTo - newState = newState.copy(walletManagersThrottling = newMap) - } - val currencies = listOf(Currency.Blockchain(blockchain)) + walletManager.cardTokens.map { Currency.Token(it) } val newWallets = newState.wallets.filter { currencies.contains(it.currency) }