diff --git a/app/src/main/java/com/tangem/tap/di/domain/TokensDomainModule.kt b/app/src/main/java/com/tangem/tap/di/domain/TokensDomainModule.kt index 7528f0f18b..7e1c0e98de 100644 --- a/app/src/main/java/com/tangem/tap/di/domain/TokensDomainModule.kt +++ b/app/src/main/java/com/tangem/tap/di/domain/TokensDomainModule.kt @@ -294,9 +294,8 @@ internal object TokensDomainModule { @Singleton fun provideIsAmountSubtractAvailableUseCase( currenciesRepository: CurrenciesRepository, - dispatchers: CoroutineDispatcherProvider, ): IsAmountSubtractAvailableUseCase { - return IsAmountSubtractAvailableUseCase(currenciesRepository, dispatchers) + return IsAmountSubtractAvailableUseCase(currenciesRepository) } @Provides diff --git a/domain/tokens/src/main/kotlin/com/tangem/domain/tokens/IsAmountSubtractAvailableUseCase.kt b/domain/tokens/src/main/kotlin/com/tangem/domain/tokens/IsAmountSubtractAvailableUseCase.kt index 2338f7f243..bdbc0507df 100644 --- a/domain/tokens/src/main/kotlin/com/tangem/domain/tokens/IsAmountSubtractAvailableUseCase.kt +++ b/domain/tokens/src/main/kotlin/com/tangem/domain/tokens/IsAmountSubtractAvailableUseCase.kt @@ -2,11 +2,9 @@ package com.tangem.domain.tokens import arrow.core.Either import com.tangem.domain.models.currency.CryptoCurrency +import com.tangem.domain.models.wallet.UserWalletId import com.tangem.domain.tokens.model.FeePaidCurrency import com.tangem.domain.tokens.repository.CurrenciesRepository -import com.tangem.domain.models.wallet.UserWalletId -import com.tangem.utils.coroutines.CoroutineDispatcherProvider -import kotlinx.coroutines.withContext /** * Use case for checking if currency amount can be subtracted. @@ -14,17 +12,18 @@ import kotlinx.coroutines.withContext */ class IsAmountSubtractAvailableUseCase( private val currenciesRepository: CurrenciesRepository, - private val dispatchers: CoroutineDispatcherProvider, ) { - suspend operator fun invoke(userWalletId: UserWalletId, currency: CryptoCurrency): Either = - Either.catch { - withContext(dispatchers.io) { - when (val feeCurrency = currenciesRepository.getFeePaidCurrency(userWalletId, currency.network)) { - is FeePaidCurrency.Coin -> currency is CryptoCurrency.Coin - is FeePaidCurrency.SameCurrency -> true - is FeePaidCurrency.Token -> currency.id == feeCurrency.tokenId - is FeePaidCurrency.FeeResource -> false - } - } + suspend operator fun invoke( + userWalletId: UserWalletId, + currency: CryptoCurrency, + isGaslessEthTx: Boolean = false, + ): Either = Either.catch { + if (isGaslessEthTx) return@catch true + when (val feeCurrency = currenciesRepository.getFeePaidCurrency(userWalletId, currency.network)) { + is FeePaidCurrency.Coin -> currency is CryptoCurrency.Coin + is FeePaidCurrency.SameCurrency -> true + is FeePaidCurrency.Token -> currency.id == feeCurrency.tokenId + is FeePaidCurrency.FeeResource -> false } + } } \ No newline at end of file diff --git a/features/send-v2/api/src/main/java/com/tangem/features/send/v2/api/SendNotificationsComponent.kt b/features/send-v2/api/src/main/java/com/tangem/features/send/v2/api/SendNotificationsComponent.kt index 90823b9c00..5ec0bf75e3 100644 --- a/features/send-v2/api/src/main/java/com/tangem/features/send/v2/api/SendNotificationsComponent.kt +++ b/features/send-v2/api/src/main/java/com/tangem/features/send/v2/api/SendNotificationsComponent.kt @@ -28,7 +28,6 @@ interface SendNotificationsComponent { val analyticsCategoryName: String, val userWalletId: UserWalletId, val cryptoCurrencyStatus: CryptoCurrencyStatus, - val feeCryptoCurrencyStatus: CryptoCurrencyStatus, val appCurrency: AppCurrency, val notificationData: NotificationData, val callback: ModelCallback, @@ -41,6 +40,7 @@ interface SendNotificationsComponent { val isIgnoreReduce: Boolean, val fee: Fee?, val feeError: GetFeeError?, + val feeCryptoCurrencyStatus: CryptoCurrencyStatus, ) } diff --git a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/SendConfirmComponent.kt b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/SendConfirmComponent.kt index afab0e41d7..423fc07b00 100644 --- a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/SendConfirmComponent.kt +++ b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/SendConfirmComponent.kt @@ -105,7 +105,6 @@ internal class SendConfirmComponent( analyticsCategoryName = params.analyticsCategoryName, userWalletId = params.userWallet.walletId, cryptoCurrencyStatus = params.cryptoCurrencyStatus, - feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus, appCurrency = params.appCurrency, callback = model, notificationData = NotificationData( @@ -116,6 +115,7 @@ internal class SendConfirmComponent( isIgnoreReduce = model.confirmData.isIgnoreReduce, fee = model.confirmData.fee, feeError = model.confirmData.feeError, + feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus, ), ), ) diff --git a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/model/SendConfirmModel.kt b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/model/SendConfirmModel.kt index 15e6d54b17..f99abc7f71 100644 --- a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/model/SendConfirmModel.kt +++ b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/send/confirm/model/SendConfirmModel.kt @@ -5,6 +5,7 @@ import androidx.compose.runtime.Stable import arrow.core.getOrElse import com.tangem.blockchain.common.AmountType import com.tangem.blockchain.common.TransactionData +import com.tangem.blockchain.common.transaction.Fee import com.tangem.common.routing.AppRouter import com.tangem.common.ui.amountScreen.converters.AmountReduceByTransformer import com.tangem.common.ui.amountScreen.models.AmountState @@ -29,6 +30,7 @@ import com.tangem.domain.feedback.SendFeedbackEmailUseCase import com.tangem.domain.feedback.models.BlockchainErrorInfo import com.tangem.domain.feedback.models.FeedbackEmailType import com.tangem.domain.models.currency.CryptoCurrency +import com.tangem.domain.models.currency.CryptoCurrencyStatus import com.tangem.domain.settings.IsSendTapHelpEnabledUseCase import com.tangem.domain.settings.NeverShowTapHelpUseCase import com.tangem.domain.tokens.AddCryptoCurrenciesUseCase @@ -155,10 +157,7 @@ internal class SendConfirmModel @Inject constructor( internal var feeStateConfiguration: FeeStateConfiguration = FeeStateConfiguration.None init { - modelScope.launch { - isAmountSubtractAvailable = - isAmountSubtractAvailableUseCase(userWallet.walletId, cryptoCurrency).getOrElse { false } - } + updateAmountSubtractAvailability() configConfirmNavigation() subscribeOnNotificationsUpdateTrigger() subscribeOnCheckFeeResultUpdates() @@ -357,7 +356,7 @@ internal class SendConfirmModel @Inject constructor( val receivingAmount = checkAndCalculateSubtractedAmount( isAmountSubtractAvailable = isAmountSubtractAvailable, - cryptoCurrencyStatus = cryptoCurrencyStatus, + cryptoCurrencyStatus = getCurrencyStatusForFeePayment(), amountValue = amountValue, feeValue = feeValue, reduceAmountBy = confirmData.reduceAmountBy.orZero(), @@ -392,7 +391,9 @@ internal class SendConfirmModel @Inject constructor( private suspend fun sendTransaction(txData: TransactionData.Uncompiled) { val feeExtended = feeUMV2?.feeExtraInfo?.transactionFeeExtended - val result = if (feeExtended != null) { + val isFeeInTokenCurrency = feeExtended?.transactionFee?.normal is Fee.Ethereum.TokenCurrency + + val result = if (isFeeInTokenCurrency) { createAndSendGaslessTransactionUseCase( userWallet = userWallet, transactionData = txData, @@ -439,6 +440,16 @@ internal class SendConfirmModel @Inject constructor( ) } + private fun getCurrencyStatusForFeePayment(): CryptoCurrencyStatus { + val feeExtended = feeUMV2?.feeExtraInfo?.transactionFeeExtended + val isFeeInTokenCurrency = feeExtended?.transactionFee?.normal is Fee.Ethereum.TokenCurrency + return if (isFeeInTokenCurrency) { + feeUMV2?.feeExtraInfo?.feeCryptoCurrencyStatus ?: cryptoCurrencyStatus + } else { + params.feeCryptoCurrencyStatus + } + } + private fun addTokenToWalletIfNeeded() { if (cryptoCurrency !is CryptoCurrency.Token) return val wallets = destinationUM?.wallets ?: return @@ -509,6 +520,7 @@ internal class SendConfirmModel @Inject constructor( isIgnoreReduce = confirmData.isIgnoreReduce, fee = confirmData.fee, feeError = confirmData.feeError, + feeCryptoCurrencyStatus = getCurrencyStatusForFeePayment(), ), ) _uiState.update { state -> @@ -610,9 +622,23 @@ internal class SendConfirmModel @Inject constructor( override fun onFeeResult(feeSelectorUM: FeeSelectorUMRedesigned) { sendIdleTimer = SystemClock.elapsedRealtime() _uiState.update { it.copy(feeSelectorUM = feeSelectorUM) } + updateAmountSubtractAvailability() updateConfirmNotifications() } + private fun updateAmountSubtractAvailability() { + modelScope.launch { + val isGaslessEthTx = + feeUMV2?.feeExtraInfo?.transactionFeeExtended?.transactionFee?.normal is Fee.Ethereum.TokenCurrency + isAmountSubtractAvailable = + isAmountSubtractAvailableUseCase( + userWalletId = userWallet.walletId, + currency = cryptoCurrency, + isGaslessEthTx = isGaslessEthTx, + ).getOrElse { false } + } + } + private companion object { const val CHECK_FEE_UPDATE_DELAY = 10_000L } diff --git a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/NFTSendConfirmComponent.kt b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/NFTSendConfirmComponent.kt index fec1c74cb7..98e150c9bb 100644 --- a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/NFTSendConfirmComponent.kt +++ b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/NFTSendConfirmComponent.kt @@ -102,7 +102,6 @@ internal class NFTSendConfirmComponent @AssistedInject constructor( analyticsCategoryName = params.analyticsCategoryName, userWalletId = params.userWallet.walletId, cryptoCurrencyStatus = params.cryptoCurrencyStatus, - feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus, appCurrency = params.appCurrency, callback = model, notificationData = SendNotificationsComponent.Params.NotificationData( @@ -113,6 +112,7 @@ internal class NFTSendConfirmComponent @AssistedInject constructor( isIgnoreReduce = false, fee = model.confirmData.fee, feeError = model.confirmData.feeError, + feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus, ), ), ) diff --git a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/model/NFTSendConfirmModel.kt b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/model/NFTSendConfirmModel.kt index 8bab99a2a4..1b926b4ea2 100644 --- a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/model/NFTSendConfirmModel.kt +++ b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/sendnft/confirm/model/NFTSendConfirmModel.kt @@ -350,6 +350,7 @@ internal class NFTSendConfirmModel @Inject constructor( isIgnoreReduce = false, fee = confirmData.fee, feeError = confirmData.feeError, + feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus, // TODO change when gasless implement ), ) } diff --git a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/subcomponents/notifications/model/NotificationsModel.kt b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/subcomponents/notifications/model/NotificationsModel.kt index 7efbe2186d..eb07ae00ec 100644 --- a/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/subcomponents/notifications/model/NotificationsModel.kt +++ b/features/send-v2/impl/src/main/java/com/tangem/features/send/v2/subcomponents/notifications/model/NotificationsModel.kt @@ -79,7 +79,7 @@ internal class NotificationsModel @Inject constructor( private val analyticsCategoryName = params.analyticsCategoryName private val userWalletId = params.userWalletId private val cryptoCurrencyStatus = params.cryptoCurrencyStatus - private val feeCryptoCurrencyStatus = params.feeCryptoCurrencyStatus + private val feeCryptoCurrencyStatus = params.notificationData.feeCryptoCurrencyStatus private val currency = cryptoCurrencyStatus.currency private val appCurrency = params.appCurrency @@ -92,7 +92,10 @@ internal class NotificationsModel @Inject constructor( init { subscribeToNotificationUpdateTrigger() - checkIfSubtractAvailable() + modelScope.launch { + checkIfSubtractAvailable() + buildNotifications() + } incrementNotificationsShowCount() } @@ -102,11 +105,12 @@ internal class NotificationsModel @Inject constructor( .launchIn(modelScope) } - private fun checkIfSubtractAvailable() { - modelScope.launch { - isAmountSubtractAvailable = isAmountSubtractAvailableUseCase(userWalletId, currency).getOrElse { false } - buildNotifications() - } + private suspend fun checkIfSubtractAvailable() { + isAmountSubtractAvailable = isAmountSubtractAvailableUseCase( + userWalletId = userWalletId, + currency = currency, + isGaslessEthTx = notificationData.fee is Fee.Ethereum.TokenCurrency, + ).getOrElse { false } } private fun incrementNotificationsShowCount() { @@ -115,16 +119,19 @@ internal class NotificationsModel @Inject constructor( } } - private suspend fun updateState(data: NotificationData) { + private fun updateState(data: NotificationData) { notificationData = data - buildNotifications() + modelScope.launch { + checkIfSubtractAvailable() + buildNotifications() + } } private suspend fun buildNotifications() = with(notificationData) { val feeValue = fee?.amount?.value val sendingAmount = checkAndCalculateSubtractedAmount( isAmountSubtractAvailable = isAmountSubtractAvailable, - cryptoCurrencyStatus = cryptoCurrencyStatus, + cryptoCurrencyStatus = getCurrencyStatusForFeePayment(), amountValue = amountValue, feeValue = feeValue, reduceAmountBy = reduceAmountBy, @@ -369,6 +376,15 @@ internal class NotificationsModel @Inject constructor( } } + private fun getCurrencyStatusForFeePayment(): CryptoCurrencyStatus { + val isFeeInTokenCurrency = notificationData.fee is Fee.Ethereum.TokenCurrency + return if (isFeeInTokenCurrency) { + notificationData.feeCryptoCurrencyStatus + } else { + cryptoCurrencyStatus + } + } + companion object { const val TRON_FEE_NOTIFICATION_MAX_SHOW_COUNT = 3 } diff --git a/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/SendWithSwapConfirmComponent.kt b/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/SendWithSwapConfirmComponent.kt index dc79a0ee29..a81a280eda 100644 --- a/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/SendWithSwapConfirmComponent.kt +++ b/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/SendWithSwapConfirmComponent.kt @@ -107,7 +107,6 @@ internal class SendWithSwapConfirmComponent @AssistedInject constructor( analyticsCategoryName = params.analyticsCategoryName, userWalletId = params.userWallet.walletId, cryptoCurrencyStatus = model.primaryCurrencyStatus, - feeCryptoCurrencyStatus = model.primaryFeePaidCurrencyStatus, appCurrency = params.appCurrency, callback = model, notificationData = SendNotificationsComponent.Params.NotificationData( @@ -121,6 +120,7 @@ internal class SendWithSwapConfirmComponent @AssistedInject constructor( isIgnoreReduce = model.confirmData.isIgnoreReduce, fee = model.confirmData.fee, feeError = model.confirmData.feeError, + feeCryptoCurrencyStatus = model.primaryFeePaidCurrencyStatus, ), ), ) diff --git a/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/model/SendWithSwapConfirmModel.kt b/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/model/SendWithSwapConfirmModel.kt index 3fcd6d870c..ead2a200fb 100644 --- a/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/model/SendWithSwapConfirmModel.kt +++ b/features/swap-v2/impl/src/main/java/com/tangem/features/swap/v2/impl/sendviaswap/confirm/model/SendWithSwapConfirmModel.kt @@ -357,6 +357,7 @@ internal class SendWithSwapConfirmModel @Inject constructor( isIgnoreReduce = confirmData.isIgnoreReduce, fee = confirmData.fee, feeError = confirmData.feeError, + feeCryptoCurrencyStatus = params.primaryFeePaidCurrencyStatusFlow.value, ), ) swapNotificationsUpdateTrigger.triggerUpdate(