Updated on 2026-08-14

This commit is contained in:
Tangem 2023-10-26 15:59:36 +08:00
parent 4ee802212b
commit d2e036e574
12 changed files with 133 additions and 58 deletions

View file

@ -92,6 +92,7 @@ internal class WalletStateFactory(
private val loadingTransactionsStateConverter by lazy {
WalletLoadingTxHistoryConverter(
currentStateProvider = currentStateProvider,
currentCardTypeResolverProvider = currentCardTypeResolverProvider,
clickIntents = clickIntents,
)
}
@ -225,9 +226,15 @@ internal class WalletStateFactory(
)
}
fun getLoadingTxHistoryState(itemsCountEither: Either<TxHistoryStateError, Int>): WalletState {
fun getLoadingTxHistoryState(
itemsCountEither: Either<TxHistoryStateError, Int>,
pendingTransactions: Set<TxHistoryItem>,
): WalletState {
return loadingTransactionsStateConverter.convert(
WalletLoadingTxHistoryConverter.WalletLoadingTxHistoryModel(historyLoadingState = itemsCountEither),
WalletLoadingTxHistoryConverter.WalletLoadingTxHistoryModel(
historyLoadingState = itemsCountEither,
pendingTransactions = pendingTransactions,
),
)
}

View file

@ -6,10 +6,13 @@ import com.tangem.common.Converter
import com.tangem.common.Provider
import com.tangem.core.ui.components.transactions.state.TransactionState
import com.tangem.core.ui.components.transactions.state.TxHistoryState.*
import com.tangem.domain.common.CardTypesResolver
import com.tangem.domain.txhistory.models.TxHistoryItem
import com.tangem.domain.txhistory.models.TxHistoryStateError
import com.tangem.feature.wallet.presentation.wallet.state.WalletSingleCurrencyState
import com.tangem.feature.wallet.presentation.wallet.state.WalletState
import com.tangem.feature.wallet.presentation.wallet.viewmodels.WalletClickIntents
import kotlinx.collections.immutable.toImmutableList
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.update
@ -23,17 +26,27 @@ import kotlinx.coroutines.flow.update
*/
internal class WalletLoadingTxHistoryConverter(
private val currentStateProvider: Provider<WalletState>,
private val currentCardTypeResolverProvider: Provider<CardTypesResolver>,
private val clickIntents: WalletClickIntents,
) : Converter<WalletLoadingTxHistoryConverter.WalletLoadingTxHistoryModel, WalletState> {
private val txHistoryItemConverter by lazy {
val blockchain = currentCardTypeResolverProvider().getBlockchain()
WalletTxHistoryTransactionStateConverter(
symbol = blockchain.currency,
decimals = blockchain.decimals(),
clickIntents = clickIntents,
)
}
override fun convert(value: WalletLoadingTxHistoryModel): WalletState {
return value.historyLoadingState.fold(
ifLeft = ::convertError,
ifLeft = { convertError(it, value.pendingTransactions) },
ifRight = ::convertRight,
)
}
private fun convertError(error: TxHistoryStateError): WalletState {
private fun convertError(error: TxHistoryStateError, pendingTransactions: Set<TxHistoryItem>): WalletState {
val state = currentStateProvider()
return if (state is WalletSingleCurrencyState.Content) {
@ -42,7 +55,11 @@ internal class WalletLoadingTxHistoryConverter(
is TxHistoryStateError.EmptyTxHistories -> Empty
is TxHistoryStateError.DataError -> Error(onReloadClick = clickIntents::onReloadClick)
is TxHistoryStateError.TxHistoryNotImplemented -> {
NotSupported(onExploreClick = clickIntents::onExploreClick)
NotSupported(
pendingTransactions = txHistoryItemConverter.convertList(pendingTransactions)
.toImmutableList(),
onExploreClick = clickIntents::onExploreClick,
)
}
},
)
@ -78,5 +95,8 @@ internal class WalletLoadingTxHistoryConverter(
}
}
data class WalletLoadingTxHistoryModel(val historyLoadingState: Either<TxHistoryStateError, Int>)
data class WalletLoadingTxHistoryModel(
val historyLoadingState: Either<TxHistoryStateError, Int>,
val pendingTransactions: Set<TxHistoryItem>,
)
}

View file

@ -768,6 +768,8 @@ internal class WalletViewModel @Inject constructor(
refreshSingleCurrencyContent(selectedWalletIndex)
}
// FIXME: refreshSingleCurrencyContent mustn't update the TxHistory and Buttons. It only must fetch primary
// currency. Now it not works because GetPrimaryCurrency's subscriber uses .distinctUntilChanged()
private fun refreshSingleCurrencyContent(walletIndex: Int) {
uiState = stateFactory.getRefreshingState()
val wallet = getWallet(walletIndex)
@ -785,9 +787,12 @@ internal class WalletViewModel @Inject constructor(
val singleCurrencyState = uiState as WalletSingleCurrencyState
if (singleCurrencyState.txHistoryState !is TxHistoryState.Content) {
// show loading indicator while refreshing in non content state
uiState = stateFactory.getLoadingTxHistoryState(1.right())
uiState = stateFactory.getLoadingTxHistoryState(
itemsCountEither = 1.right(),
pendingTransactions = it.value.pendingTransactions,
)
}
updateTxHistory(wallet.walletId, it.currency, refresh = true)
updateTxHistory(userWalletId = wallet.walletId, currencyStatus = it, refresh = true)
}
}.saveIn(refreshContentJobHolder)
}
@ -1218,7 +1223,7 @@ internal class WalletViewModel @Inject constructor(
updateNotifications(index)
updateButtons(userWallet = wallet, currencyStatus = status)
updateTxHistory(wallet.walletId, status.currency, refresh = false)
updateTxHistory(userWalletId = wallet.walletId, currencyStatus = status, refresh = false)
}
}
.flowOn(dispatchers.io)
@ -1274,22 +1279,23 @@ internal class WalletViewModel @Inject constructor(
}
}
private fun updateTxHistory(userWalletId: UserWalletId, currency: CryptoCurrency, refresh: Boolean) {
private fun updateTxHistory(userWalletId: UserWalletId, currencyStatus: CryptoCurrencyStatus, refresh: Boolean) {
viewModelScope.launch(dispatchers.io) {
val txHistoryItemsCountEither = txHistoryItemsCountUseCase(
userWalletId = userWalletId,
network = currency.network,
network = currencyStatus.currency.network,
)
uiState = stateFactory.getLoadingTxHistoryState(
itemsCountEither = txHistoryItemsCountEither,
pendingTransactions = currencyStatus.value.pendingTransactions,
)
txHistoryItemsCountEither.onRight {
uiState = stateFactory.getLoadedTxHistoryState(
txHistoryEither = txHistoryItemsUseCase(
userWalletId = userWalletId,
currency = currency,
currency = currencyStatus.currency,
refresh = refresh,
).map {
it.cachedIn(viewModelScope)