Updated on 2026-08-14
This commit is contained in:
parent
043602ebd6
commit
dd362fb32c
21 changed files with 133 additions and 184 deletions
|
|
@ -12,7 +12,6 @@ import com.tangem.blockchainsdk.utils.toBlockchain
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrency
|
||||||
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
import com.tangem.domain.models.wallet.UserWalletId
|
import com.tangem.domain.models.wallet.UserWalletId
|
||||||
import com.tangem.domain.models.yield.supply.YieldSupplyStatus
|
|
||||||
import com.tangem.domain.utils.convertToSdkAmount
|
import com.tangem.domain.utils.convertToSdkAmount
|
||||||
import com.tangem.domain.walletmanager.WalletManagersFacade
|
import com.tangem.domain.walletmanager.WalletManagersFacade
|
||||||
import com.tangem.domain.yield.supply.YieldSupplyTransactionRepository
|
import com.tangem.domain.yield.supply.YieldSupplyTransactionRepository
|
||||||
|
|
@ -52,28 +51,23 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
) ?: error("Calculated yield contract address is null")
|
) ?: error("Calculated yield contract address is null")
|
||||||
|
|
||||||
val yieldTokenStatus = cryptoCurrencyStatus.value.yieldSupplyStatus ?: getYieldTokenStatus(
|
val maxNetworkFee = maxNetworkFee.convertToSdkAmount(cryptoCurrencyStatus)
|
||||||
walletManager = walletManager,
|
|
||||||
cryptoCurrency = cryptoCurrency,
|
|
||||||
)
|
|
||||||
|
|
||||||
return buildEnterTransactions(
|
return buildEnterTransactions(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
existingYieldContractAddress = existingYieldContractAddress,
|
existingYieldContractAddress = existingYieldContractAddress,
|
||||||
calculatedYieldContractAddress = calculatedYieldContractAddress,
|
calculatedYieldContractAddress = calculatedYieldContractAddress,
|
||||||
yieldTokenStatus = yieldTokenStatus,
|
|
||||||
maxNetworkFee = maxNetworkFee,
|
maxNetworkFee = maxNetworkFee,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
override suspend fun createExitTransaction(
|
override suspend fun createExitTransaction(
|
||||||
userWalletId: UserWalletId,
|
userWalletId: UserWalletId,
|
||||||
cryptoCurrency: CryptoCurrency,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
yieldSupplyStatus: YieldSupplyStatus,
|
|
||||||
fee: Fee?,
|
fee: Fee?,
|
||||||
): TransactionData.Uncompiled = withContext(dispatchers.io) {
|
): TransactionData.Uncompiled = withContext(dispatchers.io) {
|
||||||
require(cryptoCurrency is CryptoCurrency.Token)
|
val cryptoCurrency = cryptoCurrencyStatus.currency as CryptoCurrency.Token
|
||||||
|
|
||||||
val walletManager = walletManagersFacade.getOrCreateWalletManager(
|
val walletManager = walletManagersFacade.getOrCreateWalletManager(
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
|
|
@ -90,7 +84,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
callData = callData,
|
callData = callData,
|
||||||
destinationAddress = walletManager.getYieldContract(),
|
destinationAddress = walletManager.getYieldContract(),
|
||||||
yieldSupplyStatus = yieldSupplyStatus,
|
amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
fee = fee,
|
fee = fee,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -98,13 +92,16 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
@Suppress("LongParameterList")
|
@Suppress("LongParameterList")
|
||||||
private fun buildEnterTransactions(
|
private fun buildEnterTransactions(
|
||||||
walletManager: WalletManager,
|
walletManager: WalletManager,
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
existingYieldContractAddress: String?,
|
existingYieldContractAddress: String?,
|
||||||
calculatedYieldContractAddress: String,
|
calculatedYieldContractAddress: String,
|
||||||
yieldTokenStatus: YieldSupplyStatus?,
|
maxNetworkFee: Amount,
|
||||||
maxNetworkFee: BigDecimal,
|
|
||||||
): MutableList<TransactionData.Uncompiled> {
|
): MutableList<TransactionData.Uncompiled> {
|
||||||
val enterTransactions = mutableListOf<TransactionData.Uncompiled>()
|
val enterTransactions = mutableListOf<TransactionData.Uncompiled>()
|
||||||
|
val cryptoCurrency = cryptoCurrencyStatus.currency as CryptoCurrency.Token
|
||||||
|
val yieldSupplyStatus = cryptoCurrencyStatus.value.yieldSupplyStatus
|
||||||
|
|
||||||
|
val amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrencyStatus)
|
||||||
|
|
||||||
when {
|
when {
|
||||||
existingYieldContractAddress == null || existingYieldContractAddress == EthereumUtils.ZERO_ADDRESS -> {
|
existingYieldContractAddress == null || existingYieldContractAddress == EthereumUtils.ZERO_ADDRESS -> {
|
||||||
|
|
@ -112,33 +109,34 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
createDeployTransaction(
|
createDeployTransaction(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
|
amount = amount,
|
||||||
maxNetworkFee = maxNetworkFee,
|
maxNetworkFee = maxNetworkFee,
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
yieldTokenStatus == null -> error("Yield token status is null")
|
yieldSupplyStatus == null -> error("Yield token status is null")
|
||||||
!yieldTokenStatus.isInitialized -> enterTransactions.add(
|
!yieldSupplyStatus.isInitialized -> enterTransactions.add(
|
||||||
createInitTokenTransaction(
|
createInitTokenTransaction(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
yieldSupplyStatus = yieldTokenStatus,
|
|
||||||
yieldContractAddress = calculatedYieldContractAddress,
|
yieldContractAddress = calculatedYieldContractAddress,
|
||||||
|
amount = amount,
|
||||||
maxNetworkFee = maxNetworkFee,
|
maxNetworkFee = maxNetworkFee,
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
!yieldTokenStatus.isActive -> enterTransactions.add(
|
!yieldSupplyStatus.isActive -> enterTransactions.add(
|
||||||
createReactivateTokenTransaction(
|
createReactivateTokenTransaction(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
yieldSupplyStatus = yieldTokenStatus,
|
|
||||||
yieldContractAddress = calculatedYieldContractAddress,
|
yieldContractAddress = calculatedYieldContractAddress,
|
||||||
|
amount = amount,
|
||||||
maxNetworkFee = maxNetworkFee,
|
maxNetworkFee = maxNetworkFee,
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
else -> Unit
|
else -> Unit
|
||||||
}
|
}
|
||||||
|
|
||||||
if (yieldTokenStatus?.isAllowedToSpend != true) {
|
if (yieldSupplyStatus?.isAllowedToSpend != true) {
|
||||||
enterTransactions.add(
|
enterTransactions.add(
|
||||||
createTransaction(
|
createTransaction(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
|
|
@ -148,7 +146,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
amount = null,
|
amount = null,
|
||||||
),
|
),
|
||||||
destinationAddress = cryptoCurrency.contractAddress,
|
destinationAddress = cryptoCurrency.contractAddress,
|
||||||
yieldSupplyStatus = yieldTokenStatus,
|
amount = amount,
|
||||||
fee = null,
|
fee = null,
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
@ -158,7 +156,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
createEnterTransaction(
|
createEnterTransaction(
|
||||||
walletManager = walletManager,
|
walletManager = walletManager,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
yieldSupplyStatus = yieldTokenStatus,
|
amount = amount,
|
||||||
yieldContractAddress = calculatedYieldContractAddress,
|
yieldContractAddress = calculatedYieldContractAddress,
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
@ -178,8 +176,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
derivationPath = cryptoCurrency.network.derivationPath.value,
|
derivationPath = cryptoCurrency.network.derivationPath.value,
|
||||||
) ?: error("Wallet manager not found")
|
) ?: error("Wallet manager not found")
|
||||||
walletManager.calculateYieldContract()
|
walletManager.calculateYieldContract()
|
||||||
}.onFailure(Timber::e)
|
}.onFailure(Timber::e).getOrNull()
|
||||||
.getOrNull()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
override suspend fun getYieldContractAddress(userWalletId: UserWalletId, cryptoCurrency: CryptoCurrency): String? =
|
override suspend fun getYieldContractAddress(userWalletId: UserWalletId, cryptoCurrency: CryptoCurrency): String? =
|
||||||
|
|
@ -192,42 +189,19 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
derivationPath = cryptoCurrency.network.derivationPath.value,
|
derivationPath = cryptoCurrency.network.derivationPath.value,
|
||||||
) ?: error("Wallet manager not found")
|
) ?: error("Wallet manager not found")
|
||||||
walletManager.getYieldContract()
|
walletManager.getYieldContract()
|
||||||
}.onFailure(Timber::e)
|
|
||||||
.getOrNull()
|
|
||||||
}
|
|
||||||
|
|
||||||
private suspend fun getYieldTokenStatus(
|
|
||||||
walletManager: WalletManager,
|
|
||||||
cryptoCurrency: CryptoCurrency,
|
|
||||||
): YieldSupplyStatus? = withContext(dispatchers.io) {
|
|
||||||
require(cryptoCurrency is CryptoCurrency.Token)
|
|
||||||
runCatching {
|
|
||||||
val sdkSupplyStatus = walletManager.getYieldSupplyStatus(cryptoCurrency.contractAddress)
|
|
||||||
val isAllowedToSpend = walletManager.isAllowedToSpend(
|
|
||||||
Token(
|
|
||||||
symbol = cryptoCurrency.symbol,
|
|
||||||
contractAddress = cryptoCurrency.contractAddress,
|
|
||||||
decimals = cryptoCurrency.decimals,
|
|
||||||
),
|
|
||||||
)
|
|
||||||
|
|
||||||
YieldSupplyStatus(
|
|
||||||
isActive = sdkSupplyStatus?.isActive == true,
|
|
||||||
isInitialized = sdkSupplyStatus?.isInitialized == true,
|
|
||||||
isAllowedToSpend = isAllowedToSpend,
|
|
||||||
)
|
|
||||||
}.onFailure(Timber::e).getOrNull()
|
}.onFailure(Timber::e).getOrNull()
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun createDeployTransaction(
|
private fun createDeployTransaction(
|
||||||
walletManager: WalletManager,
|
walletManager: WalletManager,
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrency: CryptoCurrency.Token,
|
||||||
maxNetworkFee: BigDecimal,
|
amount: Amount,
|
||||||
|
maxNetworkFee: Amount,
|
||||||
): TransactionData.Uncompiled {
|
): TransactionData.Uncompiled {
|
||||||
val callData = YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
val callData = YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
||||||
tokenContractAddress = cryptoCurrency.contractAddress,
|
tokenContractAddress = cryptoCurrency.contractAddress,
|
||||||
walletAddress = walletManager.wallet.address,
|
walletAddress = walletManager.wallet.address,
|
||||||
maxNetworkFee = maxNetworkFee.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = maxNetworkFee,
|
||||||
)
|
)
|
||||||
|
|
||||||
val factoryContractAddress = walletManager.getYieldSupplyContractAddresses()?.factoryContractAddress
|
val factoryContractAddress = walletManager.getYieldSupplyContractAddresses()?.factoryContractAddress
|
||||||
|
|
@ -238,7 +212,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
callData = callData,
|
callData = callData,
|
||||||
destinationAddress = factoryContractAddress,
|
destinationAddress = factoryContractAddress,
|
||||||
yieldSupplyStatus = null,
|
amount = amount,
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -247,12 +221,12 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
walletManager: WalletManager,
|
walletManager: WalletManager,
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrency: CryptoCurrency.Token,
|
||||||
yieldContractAddress: String,
|
yieldContractAddress: String,
|
||||||
yieldSupplyStatus: YieldSupplyStatus,
|
amount: Amount,
|
||||||
maxNetworkFee: BigDecimal,
|
maxNetworkFee: Amount,
|
||||||
): TransactionData.Uncompiled {
|
): TransactionData.Uncompiled {
|
||||||
val callData = YieldSupplyContractCallDataProviderFactory.getInitTokenCallData(
|
val callData = YieldSupplyContractCallDataProviderFactory.getInitTokenCallData(
|
||||||
tokenContractAddress = cryptoCurrency.contractAddress,
|
tokenContractAddress = cryptoCurrency.contractAddress,
|
||||||
maxNetworkFee = maxNetworkFee.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = maxNetworkFee,
|
||||||
)
|
)
|
||||||
|
|
||||||
return createTransaction(
|
return createTransaction(
|
||||||
|
|
@ -260,7 +234,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
callData = callData,
|
callData = callData,
|
||||||
destinationAddress = yieldContractAddress,
|
destinationAddress = yieldContractAddress,
|
||||||
yieldSupplyStatus = yieldSupplyStatus,
|
amount = amount,
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -269,12 +243,12 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
walletManager: WalletManager,
|
walletManager: WalletManager,
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrency: CryptoCurrency.Token,
|
||||||
yieldContractAddress: String,
|
yieldContractAddress: String,
|
||||||
yieldSupplyStatus: YieldSupplyStatus,
|
amount: Amount,
|
||||||
maxNetworkFee: BigDecimal,
|
maxNetworkFee: Amount,
|
||||||
): TransactionData.Uncompiled {
|
): TransactionData.Uncompiled {
|
||||||
val callData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
val callData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
||||||
tokenContractAddress = cryptoCurrency.contractAddress,
|
tokenContractAddress = cryptoCurrency.contractAddress,
|
||||||
maxNetworkFee = maxNetworkFee.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = maxNetworkFee,
|
||||||
)
|
)
|
||||||
|
|
||||||
return createTransaction(
|
return createTransaction(
|
||||||
|
|
@ -282,7 +256,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
callData = callData,
|
callData = callData,
|
||||||
destinationAddress = yieldContractAddress,
|
destinationAddress = yieldContractAddress,
|
||||||
yieldSupplyStatus = yieldSupplyStatus,
|
amount = amount,
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -290,7 +264,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
private fun createEnterTransaction(
|
private fun createEnterTransaction(
|
||||||
walletManager: WalletManager,
|
walletManager: WalletManager,
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrency: CryptoCurrency.Token,
|
||||||
yieldSupplyStatus: YieldSupplyStatus?,
|
amount: Amount,
|
||||||
yieldContractAddress: String,
|
yieldContractAddress: String,
|
||||||
): TransactionData.Uncompiled {
|
): TransactionData.Uncompiled {
|
||||||
val callData = YieldSupplyContractCallDataProviderFactory.getEnterCallData(
|
val callData = YieldSupplyContractCallDataProviderFactory.getEnterCallData(
|
||||||
|
|
@ -302,7 +276,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrency = cryptoCurrency,
|
||||||
callData = callData,
|
callData = callData,
|
||||||
destinationAddress = yieldContractAddress,
|
destinationAddress = yieldContractAddress,
|
||||||
yieldSupplyStatus = yieldSupplyStatus,
|
amount = amount,
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -313,7 +287,7 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
cryptoCurrency: CryptoCurrency,
|
cryptoCurrency: CryptoCurrency,
|
||||||
callData: SmartContractCallData,
|
callData: SmartContractCallData,
|
||||||
destinationAddress: String,
|
destinationAddress: String,
|
||||||
yieldSupplyStatus: YieldSupplyStatus?,
|
amount: Amount,
|
||||||
fee: Fee?,
|
fee: Fee?,
|
||||||
): TransactionData.Uncompiled {
|
): TransactionData.Uncompiled {
|
||||||
requireNotNull(cryptoCurrency as? CryptoCurrency.Token)
|
requireNotNull(cryptoCurrency as? CryptoCurrency.Token)
|
||||||
|
|
@ -324,8 +298,6 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
blockchain = blockchain,
|
blockchain = blockchain,
|
||||||
)
|
)
|
||||||
|
|
||||||
val amount = getYieldSupplyAmount(cryptoCurrency, yieldSupplyStatus)
|
|
||||||
|
|
||||||
return if (fee != null) {
|
return if (fee != null) {
|
||||||
walletManager.createTransaction(
|
walletManager.createTransaction(
|
||||||
amount = amount,
|
amount = amount,
|
||||||
|
|
@ -365,19 +337,4 @@ internal class DefaultYieldSupplyTransactionRepository(
|
||||||
else -> error("Data extras not supported for $blockchain")
|
else -> error("Data extras not supported for $blockchain")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun getYieldSupplyAmount(cryptoCurrency: CryptoCurrency.Token, yieldSupplyStatus: YieldSupplyStatus?) =
|
|
||||||
BigDecimal.ZERO.convertToSdkAmount(
|
|
||||||
cryptoCurrency = cryptoCurrency,
|
|
||||||
amountType = AmountType.TokenYieldSupply(
|
|
||||||
token = Token(
|
|
||||||
symbol = cryptoCurrency.symbol,
|
|
||||||
contractAddress = cryptoCurrency.contractAddress,
|
|
||||||
decimals = cryptoCurrency.decimals,
|
|
||||||
),
|
|
||||||
isActive = yieldSupplyStatus?.isActive ?: false,
|
|
||||||
isInitialized = yieldSupplyStatus?.isInitialized ?: false,
|
|
||||||
isAllowedToSpend = yieldSupplyStatus?.isAllowedToSpend ?: false,
|
|
||||||
),
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
@ -88,7 +88,7 @@ class DefaultYieldSupplyTransactionRepositoryTest {
|
||||||
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
||||||
walletAddress = walletManager.wallet.address,
|
walletAddress = walletManager.wallet.address,
|
||||||
tokenContractAddress = mockedContractAddress,
|
tokenContractAddress = mockedContractAddress,
|
||||||
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
val firstTransaction = result.first()
|
val firstTransaction = result.first()
|
||||||
|
|
||||||
|
|
@ -141,7 +141,7 @@ class DefaultYieldSupplyTransactionRepositoryTest {
|
||||||
// Check transaction - init token
|
// Check transaction - init token
|
||||||
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getInitTokenCallData(
|
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getInitTokenCallData(
|
||||||
tokenContractAddress = mockedContractAddress,
|
tokenContractAddress = mockedContractAddress,
|
||||||
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
val firstTransaction = result.first()
|
val firstTransaction = result.first()
|
||||||
|
|
||||||
|
|
@ -194,7 +194,7 @@ class DefaultYieldSupplyTransactionRepositoryTest {
|
||||||
// Check transaction - reactivate token
|
// Check transaction - reactivate token
|
||||||
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
||||||
tokenContractAddress = mockedContractAddress,
|
tokenContractAddress = mockedContractAddress,
|
||||||
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
val firstTransaction = result.first()
|
val firstTransaction = result.first()
|
||||||
|
|
||||||
|
|
@ -247,7 +247,7 @@ class DefaultYieldSupplyTransactionRepositoryTest {
|
||||||
// Check transaction - reactivate token
|
// Check transaction - reactivate token
|
||||||
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
val firstExpectedCallData = YieldSupplyContractCallDataProviderFactory.getReactivateTokenCallData(
|
||||||
tokenContractAddress = mockedContractAddress,
|
tokenContractAddress = mockedContractAddress,
|
||||||
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = BigDecimal.TEN.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
val firstTransaction = result.first()
|
val firstTransaction = result.first()
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,30 +3,37 @@ package com.tangem.domain.utils
|
||||||
import com.tangem.blockchain.common.AmountType
|
import com.tangem.blockchain.common.AmountType
|
||||||
import com.tangem.blockchain.common.Token
|
import com.tangem.blockchain.common.Token
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrency
|
||||||
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
import java.math.BigDecimal
|
import java.math.BigDecimal
|
||||||
import com.tangem.blockchain.common.Amount as SdkAmount
|
import com.tangem.blockchain.common.Amount as SdkAmount
|
||||||
|
|
||||||
/** Converts `BigDecimal` [cryptoCurrency] to [SdkAmount] */
|
/** Converts `BigDecimal` [cryptoCurrencyStatus] to [SdkAmount] */
|
||||||
fun BigDecimal.convertToSdkAmount(
|
fun BigDecimal.convertToSdkAmount(cryptoCurrencyStatus: CryptoCurrencyStatus): SdkAmount {
|
||||||
cryptoCurrency: CryptoCurrency,
|
val cryptoCurrency = cryptoCurrencyStatus.currency
|
||||||
amountType: AmountType = getAmountTypeFromCryptoCurrency(cryptoCurrency),
|
val yieldSupplyStatus = cryptoCurrencyStatus.value.yieldSupplyStatus
|
||||||
): SdkAmount = SdkAmount(
|
return SdkAmount(
|
||||||
currencySymbol = cryptoCurrency.symbol,
|
currencySymbol = cryptoCurrency.symbol,
|
||||||
value = this,
|
value = this,
|
||||||
decimals = cryptoCurrency.decimals,
|
decimals = cryptoCurrency.decimals,
|
||||||
type = amountType,
|
type = when (cryptoCurrency) {
|
||||||
)
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Converts [CryptoCurrency] to [AmountType] based on its type
|
|
||||||
*/
|
|
||||||
private fun getAmountTypeFromCryptoCurrency(cryptoCurrency: CryptoCurrency) = when (cryptoCurrency) {
|
|
||||||
is CryptoCurrency.Coin -> AmountType.Coin
|
is CryptoCurrency.Coin -> AmountType.Coin
|
||||||
is CryptoCurrency.Token -> AmountType.Token(
|
is CryptoCurrency.Token -> {
|
||||||
token = Token(
|
val token = Token(
|
||||||
symbol = cryptoCurrency.symbol,
|
symbol = cryptoCurrency.symbol,
|
||||||
contractAddress = cryptoCurrency.contractAddress,
|
contractAddress = cryptoCurrency.contractAddress,
|
||||||
decimals = cryptoCurrency.decimals,
|
decimals = cryptoCurrency.decimals,
|
||||||
),
|
)
|
||||||
|
if (yieldSupplyStatus == null) {
|
||||||
|
AmountType.Token(token = token)
|
||||||
|
} else {
|
||||||
|
AmountType.TokenYieldSupply(
|
||||||
|
token = token,
|
||||||
|
isActive = yieldSupplyStatus.isActive,
|
||||||
|
isInitialized = yieldSupplyStatus.isInitialized,
|
||||||
|
isAllowedToSpend = yieldSupplyStatus.isAllowedToSpend,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
@ -2,10 +2,10 @@ package com.tangem.domain.transaction.usecase
|
||||||
|
|
||||||
import arrow.core.Either
|
import arrow.core.Either
|
||||||
import com.tangem.blockchain.common.transaction.Fee
|
import com.tangem.blockchain.common.transaction.Fee
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
|
import com.tangem.domain.models.wallet.UserWalletId
|
||||||
import com.tangem.domain.transaction.TransactionRepository
|
import com.tangem.domain.transaction.TransactionRepository
|
||||||
import com.tangem.domain.utils.convertToSdkAmount
|
import com.tangem.domain.utils.convertToSdkAmount
|
||||||
import com.tangem.domain.models.wallet.UserWalletId
|
|
||||||
import java.math.BigDecimal
|
import java.math.BigDecimal
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -17,7 +17,7 @@ class CreateApprovalTransactionUseCase(
|
||||||
|
|
||||||
@Suppress("LongParameterList")
|
@Suppress("LongParameterList")
|
||||||
suspend operator fun invoke(
|
suspend operator fun invoke(
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
userWalletId: UserWalletId,
|
userWalletId: UserWalletId,
|
||||||
amount: BigDecimal?,
|
amount: BigDecimal?,
|
||||||
fee: Fee?,
|
fee: Fee?,
|
||||||
|
|
@ -25,31 +25,31 @@ class CreateApprovalTransactionUseCase(
|
||||||
spenderAddress: String,
|
spenderAddress: String,
|
||||||
) = Either.catch {
|
) = Either.catch {
|
||||||
transactionRepository.createApprovalTransaction(
|
transactionRepository.createApprovalTransaction(
|
||||||
amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrency),
|
amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
approvalAmount = amount?.convertToSdkAmount(cryptoCurrency),
|
approvalAmount = amount?.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
contractAddress = contractAddress,
|
contractAddress = contractAddress,
|
||||||
spenderAddress = spenderAddress,
|
spenderAddress = spenderAddress,
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
network = cryptoCurrency.network,
|
network = cryptoCurrencyStatus.currency.network,
|
||||||
fee = fee,
|
fee = fee,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@Suppress("LongParameterList")
|
@Suppress("LongParameterList")
|
||||||
suspend operator fun invoke(
|
suspend operator fun invoke(
|
||||||
cryptoCurrency: CryptoCurrency.Token,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
userWalletId: UserWalletId,
|
userWalletId: UserWalletId,
|
||||||
amount: BigDecimal?,
|
amount: BigDecimal?,
|
||||||
contractAddress: String,
|
contractAddress: String,
|
||||||
spenderAddress: String,
|
spenderAddress: String,
|
||||||
) = Either.catch {
|
) = Either.catch {
|
||||||
transactionRepository.createApprovalTransaction(
|
transactionRepository.createApprovalTransaction(
|
||||||
amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrency),
|
amount = BigDecimal.ZERO.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
approvalAmount = amount?.convertToSdkAmount(cryptoCurrency),
|
approvalAmount = amount?.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
contractAddress = contractAddress,
|
contractAddress = contractAddress,
|
||||||
spenderAddress = spenderAddress,
|
spenderAddress = spenderAddress,
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
network = cryptoCurrency.network,
|
network = cryptoCurrencyStatus.currency.network,
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -3,18 +3,17 @@ package com.tangem.domain.transaction.usecase
|
||||||
import arrow.core.Either
|
import arrow.core.Either
|
||||||
import arrow.core.left
|
import arrow.core.left
|
||||||
import arrow.core.right
|
import arrow.core.right
|
||||||
import com.tangem.blockchain.common.Amount
|
|
||||||
import com.tangem.blockchain.common.AmountType
|
|
||||||
import com.tangem.blockchain.common.Token
|
|
||||||
import com.tangem.blockchain.common.transaction.TransactionFee
|
import com.tangem.blockchain.common.transaction.TransactionFee
|
||||||
import com.tangem.blockchain.extensions.Result
|
import com.tangem.blockchain.extensions.Result
|
||||||
import com.tangem.domain.demo.models.DemoConfig
|
|
||||||
import com.tangem.domain.demo.DemoTransactionSender
|
import com.tangem.domain.demo.DemoTransactionSender
|
||||||
|
import com.tangem.domain.demo.models.DemoConfig
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrency
|
||||||
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
|
import com.tangem.domain.models.wallet.UserWallet
|
||||||
import com.tangem.domain.transaction.error.GetFeeError
|
import com.tangem.domain.transaction.error.GetFeeError
|
||||||
import com.tangem.domain.transaction.error.mapToFeeError
|
import com.tangem.domain.transaction.error.mapToFeeError
|
||||||
|
import com.tangem.domain.utils.convertToSdkAmount
|
||||||
import com.tangem.domain.walletmanager.WalletManagersFacade
|
import com.tangem.domain.walletmanager.WalletManagersFacade
|
||||||
import com.tangem.domain.models.wallet.UserWallet
|
|
||||||
import java.math.BigDecimal
|
import java.math.BigDecimal
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
@ -27,13 +26,13 @@ class EstimateFeeUseCase(
|
||||||
suspend operator fun invoke(
|
suspend operator fun invoke(
|
||||||
amount: BigDecimal,
|
amount: BigDecimal,
|
||||||
userWallet: UserWallet,
|
userWallet: UserWallet,
|
||||||
cryptoCurrency: CryptoCurrency,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
): Either<GetFeeError, TransactionFee> {
|
): Either<GetFeeError, TransactionFee> {
|
||||||
val amountData = convertCryptoCurrencyToAmount(cryptoCurrency, amount)
|
val amountData = amount.convertToSdkAmount(cryptoCurrencyStatus)
|
||||||
val result = if (userWallet is UserWallet.Cold &&
|
val result = if (userWallet is UserWallet.Cold &&
|
||||||
demoConfig.isDemoCardId(userWallet.scanResponse.card.cardId)
|
demoConfig.isDemoCardId(userWallet.scanResponse.card.cardId)
|
||||||
) {
|
) {
|
||||||
demoTransactionSender(userWallet, cryptoCurrency).estimateFee(
|
demoTransactionSender(userWallet, cryptoCurrencyStatus.currency).estimateFee(
|
||||||
amount = amountData,
|
amount = amountData,
|
||||||
destination = "",
|
destination = "",
|
||||||
)
|
)
|
||||||
|
|
@ -41,7 +40,7 @@ class EstimateFeeUseCase(
|
||||||
walletManagersFacade.estimateFee(
|
walletManagersFacade.estimateFee(
|
||||||
amount = amountData,
|
amount = amountData,
|
||||||
userWalletId = userWallet.walletId,
|
userWalletId = userWallet.walletId,
|
||||||
network = cryptoCurrency.network,
|
network = cryptoCurrencyStatus.currency.network,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -62,20 +61,4 @@ class EstimateFeeUseCase(
|
||||||
?: error("WalletManager is null"),
|
?: error("WalletManager is null"),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun convertCryptoCurrencyToAmount(cryptoCurrency: CryptoCurrency, amount: BigDecimal) = Amount(
|
|
||||||
currencySymbol = cryptoCurrency.symbol,
|
|
||||||
value = amount,
|
|
||||||
decimals = cryptoCurrency.decimals,
|
|
||||||
type = when (cryptoCurrency) {
|
|
||||||
is CryptoCurrency.Coin -> AmountType.Coin
|
|
||||||
is CryptoCurrency.Token -> AmountType.Token(
|
|
||||||
token = Token(
|
|
||||||
symbol = cryptoCurrency.symbol,
|
|
||||||
contractAddress = cryptoCurrency.contractAddress,
|
|
||||||
decimals = cryptoCurrency.decimals,
|
|
||||||
),
|
|
||||||
)
|
|
||||||
},
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
@ -5,7 +5,6 @@ import com.tangem.blockchain.common.transaction.Fee
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrency
|
||||||
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
import com.tangem.domain.models.wallet.UserWalletId
|
import com.tangem.domain.models.wallet.UserWalletId
|
||||||
import com.tangem.domain.models.yield.supply.YieldSupplyStatus
|
|
||||||
import java.math.BigDecimal
|
import java.math.BigDecimal
|
||||||
|
|
||||||
interface YieldSupplyTransactionRepository {
|
interface YieldSupplyTransactionRepository {
|
||||||
|
|
@ -18,8 +17,7 @@ interface YieldSupplyTransactionRepository {
|
||||||
|
|
||||||
suspend fun createExitTransaction(
|
suspend fun createExitTransaction(
|
||||||
userWalletId: UserWalletId,
|
userWalletId: UserWalletId,
|
||||||
cryptoCurrency: CryptoCurrency,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
yieldSupplyStatus: YieldSupplyStatus,
|
|
||||||
fee: Fee?,
|
fee: Fee?,
|
||||||
): TransactionData.Uncompiled
|
): TransactionData.Uncompiled
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -16,13 +16,9 @@ class YieldSupplyStopEarningUseCase(
|
||||||
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
fee: Fee?,
|
fee: Fee?,
|
||||||
): Either<Throwable, TransactionData.Uncompiled> = Either.catch {
|
): Either<Throwable, TransactionData.Uncompiled> = Either.catch {
|
||||||
val yieldTokenStatus = cryptoCurrencyStatus.value.yieldSupplyStatus ?: error("")
|
|
||||||
val cryptoCurrency = cryptoCurrencyStatus.currency
|
|
||||||
|
|
||||||
yieldSupplyTransactionRepository.createExitTransaction(
|
yieldSupplyTransactionRepository.createExitTransaction(
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
yieldSupplyStatus = yieldTokenStatus,
|
|
||||||
fee = null,
|
fee = null,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -11,6 +11,7 @@ import com.tangem.blockchain.common.transaction.Fee
|
||||||
import com.tangem.blockchain.common.transaction.TransactionFee
|
import com.tangem.blockchain.common.transaction.TransactionFee
|
||||||
import com.tangem.blockchain.yieldsupply.YieldSupplyContractCallDataProviderFactory
|
import com.tangem.blockchain.yieldsupply.YieldSupplyContractCallDataProviderFactory
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrency
|
||||||
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
import com.tangem.domain.models.wallet.UserWallet
|
import com.tangem.domain.models.wallet.UserWallet
|
||||||
import com.tangem.domain.transaction.FeeRepository
|
import com.tangem.domain.transaction.FeeRepository
|
||||||
import com.tangem.domain.transaction.error.FeeErrorResolver
|
import com.tangem.domain.transaction.error.FeeErrorResolver
|
||||||
|
|
@ -35,6 +36,10 @@ class YieldSupplyEstimateEnterFeeUseCaseTest {
|
||||||
private val cryptoCurrency: CryptoCurrency = mockk(relaxed = true) {
|
private val cryptoCurrency: CryptoCurrency = mockk(relaxed = true) {
|
||||||
every { decimals } returns 18
|
every { decimals } returns 18
|
||||||
}
|
}
|
||||||
|
private val cryptoCurrencyStatus = mockk<CryptoCurrencyStatus>(relaxed = true) {
|
||||||
|
every { currency } returns cryptoCurrency
|
||||||
|
every { value.yieldSupplyStatus } returns null
|
||||||
|
}
|
||||||
|
|
||||||
private fun ethLegacyFee(
|
private fun ethLegacyFee(
|
||||||
gasPrice: BigInteger = BigInteger.valueOf(100_000_000_000L),
|
gasPrice: BigInteger = BigInteger.valueOf(100_000_000_000L),
|
||||||
|
|
@ -42,7 +47,7 @@ class YieldSupplyEstimateEnterFeeUseCaseTest {
|
||||||
) = Fee.Ethereum.Legacy(
|
) = Fee.Ethereum.Legacy(
|
||||||
gasPrice = gasPrice,
|
gasPrice = gasPrice,
|
||||||
gasLimit = gasLimit,
|
gasLimit = gasLimit,
|
||||||
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrency),
|
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
|
|
||||||
private fun ethEip1559Fee(
|
private fun ethEip1559Fee(
|
||||||
|
|
@ -52,12 +57,12 @@ class YieldSupplyEstimateEnterFeeUseCaseTest {
|
||||||
maxFeePerGas = maxFeePerGas,
|
maxFeePerGas = maxFeePerGas,
|
||||||
priorityFee = BigInteger.ONE,
|
priorityFee = BigInteger.ONE,
|
||||||
gasLimit = gasLimit,
|
gasLimit = gasLimit,
|
||||||
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrency),
|
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
)
|
)
|
||||||
|
|
||||||
private fun uncompiled(fee: Fee, extras: TransactionExtras) = TransactionData.Uncompiled(
|
private fun uncompiled(fee: Fee, extras: TransactionExtras) = TransactionData.Uncompiled(
|
||||||
fee = fee,
|
fee = fee,
|
||||||
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrency),
|
amount = BigDecimal.ONE.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
contractAddress = null,
|
contractAddress = null,
|
||||||
sourceAddress = "0x1234567890123456789012345678901234567890",
|
sourceAddress = "0x1234567890123456789012345678901234567890",
|
||||||
destinationAddress = "0x1234567890123456789012345678901234567890",
|
destinationAddress = "0x1234567890123456789012345678901234567890",
|
||||||
|
|
@ -214,7 +219,7 @@ class YieldSupplyEstimateEnterFeeUseCaseTest {
|
||||||
YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
YieldSupplyContractCallDataProviderFactory.getDeployCallData(
|
||||||
walletAddress = "0x1234567890123456789012345678901234567890",
|
walletAddress = "0x1234567890123456789012345678901234567890",
|
||||||
tokenContractAddress = "0x1234567890123456789012345678901234567890",
|
tokenContractAddress = "0x1234567890123456789012345678901234567890",
|
||||||
maxNetworkFee = BigDecimal.ONE.convertToSdkAmount(cryptoCurrency),
|
maxNetworkFee = BigDecimal.ONE.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -317,7 +317,7 @@ internal class SendConfirmModel @Inject constructor(
|
||||||
null
|
null
|
||||||
}
|
}
|
||||||
|
|
||||||
val amount = receivingAmount?.convertToSdkAmount(cryptoCurrency)
|
val amount = receivingAmount?.convertToSdkAmount(cryptoCurrencyStatus)
|
||||||
|
|
||||||
saveBlockchainErrorUseCase(
|
saveBlockchainErrorUseCase(
|
||||||
error = BlockchainErrorInfo(
|
error = BlockchainErrorInfo(
|
||||||
|
|
@ -331,7 +331,7 @@ internal class SendConfirmModel @Inject constructor(
|
||||||
""
|
""
|
||||||
},
|
},
|
||||||
amount = amount?.value?.stripZeroPlainString() ?: "unknown",
|
amount = amount?.value?.stripZeroPlainString() ?: "unknown",
|
||||||
fee = feeValue?.convertToSdkAmount(cryptoCurrency)
|
fee = feeValue?.convertToSdkAmount(cryptoCurrencyStatus)
|
||||||
?.value?.stripZeroPlainString() ?: "unknown",
|
?.value?.stripZeroPlainString() ?: "unknown",
|
||||||
),
|
),
|
||||||
)
|
)
|
||||||
|
|
@ -424,7 +424,7 @@ internal class SendConfirmModel @Inject constructor(
|
||||||
|
|
||||||
modelScope.launch {
|
modelScope.launch {
|
||||||
createTransferTransactionUseCase(
|
createTransferTransactionUseCase(
|
||||||
amount = receivingAmount.convertToSdkAmount(cryptoCurrency),
|
amount = receivingAmount.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
fee = fee,
|
fee = fee,
|
||||||
memo = memo,
|
memo = memo,
|
||||||
nonce = nonce,
|
nonce = nonce,
|
||||||
|
|
|
||||||
|
|
@ -260,10 +260,11 @@ internal class SendModel @Inject constructor(
|
||||||
|
|
||||||
suspend fun loadFee(): Either<GetFeeError, TransactionFee> {
|
suspend fun loadFee(): Either<GetFeeError, TransactionFee> {
|
||||||
val predefinedValues = predefinedValues
|
val predefinedValues = predefinedValues
|
||||||
|
val cryptoCurrencyStatus = cryptoCurrencyStatusFlow.value
|
||||||
val transferTransaction = if (predefinedValues is PredefinedValues.Content.Deeplink) {
|
val transferTransaction = if (predefinedValues is PredefinedValues.Content.Deeplink) {
|
||||||
val predefinedAmount = predefinedValues.amount.parseBigDecimalOrNull()?.convertToSdkAmount(cryptoCurrency)
|
val predefinedAmount = predefinedValues.amount.parseBigDecimalOrNull()
|
||||||
createTransferTransactionUseCase(
|
createTransferTransactionUseCase(
|
||||||
amount = predefinedAmount ?: error("Invalid amount"),
|
amount = predefinedAmount?.convertToSdkAmount(cryptoCurrencyStatus) ?: error("Invalid amount"),
|
||||||
memo = predefinedValues.memo,
|
memo = predefinedValues.memo,
|
||||||
destination = predefinedValues.address,
|
destination = predefinedValues.address,
|
||||||
userWalletId = userWallet.walletId,
|
userWalletId = userWallet.walletId,
|
||||||
|
|
@ -277,7 +278,7 @@ internal class SendModel @Inject constructor(
|
||||||
val enteredAmount = amountUM.amountTextField.cryptoAmount.value ?: error("Invalid amount")
|
val enteredAmount = amountUM.amountTextField.cryptoAmount.value ?: error("Invalid amount")
|
||||||
|
|
||||||
createTransferTransactionUseCase(
|
createTransferTransactionUseCase(
|
||||||
amount = enteredAmount.convertToSdkAmount(cryptoCurrency),
|
amount = enteredAmount.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
memo = enteredMemo,
|
memo = enteredMemo,
|
||||||
destination = enteredDestinationAddress,
|
destination = enteredDestinationAddress,
|
||||||
userWalletId = userWallet.walletId,
|
userWalletId = userWallet.walletId,
|
||||||
|
|
|
||||||
|
|
@ -287,7 +287,7 @@ internal class NotificationsModel @Inject constructor(
|
||||||
) {
|
) {
|
||||||
val validationError = validateTransactionUseCase(
|
val validationError = validateTransactionUseCase(
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
amount = enteredAmount.convertToSdkAmount(currency),
|
amount = enteredAmount.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
fee = fee,
|
fee = fee,
|
||||||
memo = memo,
|
memo = memo,
|
||||||
destination = destinationAddress,
|
destination = destinationAddress,
|
||||||
|
|
|
||||||
|
|
@ -651,7 +651,7 @@ internal class StakingModel @Inject constructor(
|
||||||
contractAddress = tokenCryptoCurrency.contractAddress,
|
contractAddress = tokenCryptoCurrency.contractAddress,
|
||||||
spenderAddress = approval.spenderAddress,
|
spenderAddress = approval.spenderAddress,
|
||||||
fee = fee,
|
fee = fee,
|
||||||
cryptoCurrency = tokenCryptoCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
).fold(
|
).fold(
|
||||||
ifLeft = { error ->
|
ifLeft = { error ->
|
||||||
|
|
|
||||||
|
|
@ -189,7 +189,7 @@ internal class StakingFeeTransactionLoader @AssistedInject constructor(
|
||||||
val tokenCurrency = cryptoCurrencyStatus.currency as? CryptoCurrency.Token
|
val tokenCurrency = cryptoCurrencyStatus.currency as? CryptoCurrency.Token
|
||||||
?: return onApprovalFeeError(GetFeeError.UnknownError)
|
?: return onApprovalFeeError(GetFeeError.UnknownError)
|
||||||
val approvalTransactionData = createApprovalTransactionUseCase(
|
val approvalTransactionData = createApprovalTransactionUseCase(
|
||||||
cryptoCurrency = tokenCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
userWalletId = userWallet.walletId,
|
userWalletId = userWallet.walletId,
|
||||||
amount = amount,
|
amount = amount,
|
||||||
contractAddress = tokenCurrency.contractAddress,
|
contractAddress = tokenCurrency.contractAddress,
|
||||||
|
|
|
||||||
|
|
@ -158,7 +158,7 @@ internal class StakingTransactionSender @AssistedInject constructor(
|
||||||
getConstructedStakingTransactionUseCase(
|
getConstructedStakingTransactionUseCase(
|
||||||
networkId = cryptoCurrencyStatus.currency.network.rawId,
|
networkId = cryptoCurrencyStatus.currency.network.rawId,
|
||||||
fee = fee,
|
fee = fee,
|
||||||
amount = amount.convertToSdkAmount(cryptoCurrencyStatus.currency),
|
amount = amount.convertToSdkAmount(cryptoCurrencyStatus),
|
||||||
transactionId = transaction.id,
|
transactionId = transaction.id,
|
||||||
).fold(
|
).fold(
|
||||||
ifRight = { (constructedTransaction, transactionData) ->
|
ifRight = { (constructedTransaction, transactionData) ->
|
||||||
|
|
|
||||||
|
|
@ -227,7 +227,7 @@ internal class SendWithSwapConfirmModel @Inject constructor(
|
||||||
estimateFeeUseCase(
|
estimateFeeUseCase(
|
||||||
amount = amountValue,
|
amount = amountValue,
|
||||||
userWallet = params.userWallet,
|
userWallet = params.userWallet,
|
||||||
cryptoCurrency = primaryCurrencyStatus.currency,
|
cryptoCurrencyStatus = primaryCurrencyStatus,
|
||||||
).map {
|
).map {
|
||||||
it.patchTransactionFeeForSwap(INCREASE_GAS_LIMIT_FOR_CEX)
|
it.patchTransactionFeeForSwap(INCREASE_GAS_LIMIT_FOR_CEX)
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -131,7 +131,7 @@ internal class SwapTransactionSender @AssistedInject constructor(
|
||||||
}
|
}
|
||||||
|
|
||||||
val txData = createTransferTransactionUseCase(
|
val txData = createTransferTransactionUseCase(
|
||||||
amount = fromAmount.convertToSdkAmount(fromStatus.currency),
|
amount = fromAmount.convertToSdkAmount(fromStatus),
|
||||||
fee = fee,
|
fee = fee,
|
||||||
memo = swapTransaction.txExtraId,
|
memo = swapTransaction.txExtraId,
|
||||||
destination = swapTransaction.txTo,
|
destination = swapTransaction.txTo,
|
||||||
|
|
|
||||||
|
|
@ -307,7 +307,7 @@ private fun SendWithSwapSuccessContent_Preview() {
|
||||||
fees = TransactionFee.Single(
|
fees = TransactionFee.Single(
|
||||||
normal = Fee.Common(
|
normal = Fee.Common(
|
||||||
BigDecimal.ONE.convertToSdkAmount(
|
BigDecimal.ONE.convertToSdkAmount(
|
||||||
SwapAmountContentPreview.cryptoCurrencyStatus.currency,
|
SwapAmountContentPreview.cryptoCurrencyStatus,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
@ -315,7 +315,7 @@ private fun SendWithSwapSuccessContent_Preview() {
|
||||||
selectedFeeItem = FeeItem.Market(
|
selectedFeeItem = FeeItem.Market(
|
||||||
Fee.Common(
|
Fee.Common(
|
||||||
BigDecimal.ONE.convertToSdkAmount(
|
BigDecimal.ONE.convertToSdkAmount(
|
||||||
SwapAmountContentPreview.cryptoCurrencyStatus.currency,
|
SwapAmountContentPreview.cryptoCurrencyStatus,
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
),
|
),
|
||||||
|
|
|
||||||
|
|
@ -1,6 +1,6 @@
|
||||||
package com.tangem.feature.swap.domain.models.domain
|
package com.tangem.feature.swap.domain.models.domain
|
||||||
|
|
||||||
import com.tangem.domain.models.currency.CryptoCurrency
|
import com.tangem.domain.models.currency.CryptoCurrencyStatus
|
||||||
import com.tangem.feature.swap.domain.models.ui.RequestApproveStateData
|
import com.tangem.feature.swap.domain.models.ui.RequestApproveStateData
|
||||||
import com.tangem.feature.swap.domain.models.ui.TxFee
|
import com.tangem.feature.swap.domain.models.ui.TxFee
|
||||||
|
|
||||||
|
|
@ -9,14 +9,14 @@ import com.tangem.feature.swap.domain.models.ui.TxFee
|
||||||
*
|
*
|
||||||
* @param approveData tx data to give approve, it loaded from 1inch in findBestQuote if needed
|
* @param approveData tx data to give approve, it loaded from 1inch in findBestQuote if needed
|
||||||
* @param forTokenContractAddress token contract address for which needs permission
|
* @param forTokenContractAddress token contract address for which needs permission
|
||||||
* @param fromToken which token will be swapping
|
* @param fromTokenStatus which token will be swapping
|
||||||
* @param approveType unlimited or tx amount approve
|
* @param approveType unlimited or tx amount approve
|
||||||
* @param txFee fee for tx
|
* @param txFee fee for tx
|
||||||
*/
|
*/
|
||||||
data class PermissionOptions(
|
data class PermissionOptions(
|
||||||
val approveData: RequestApproveStateData,
|
val approveData: RequestApproveStateData,
|
||||||
val forTokenContractAddress: String,
|
val forTokenContractAddress: String,
|
||||||
val fromToken: CryptoCurrency,
|
val fromTokenStatus: CryptoCurrencyStatus,
|
||||||
val spenderAddress: String,
|
val spenderAddress: String,
|
||||||
val approveType: SwapApproveType,
|
val approveType: SwapApproveType,
|
||||||
val txFee: TxFee,
|
val txFee: TxFee,
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
package com.tangem.feature.swap.domain
|
package com.tangem.feature.swap.domain
|
||||||
|
|
||||||
|
import android.util.Base64
|
||||||
import arrow.core.Either
|
import arrow.core.Either
|
||||||
import arrow.core.getOrElse
|
import arrow.core.getOrElse
|
||||||
import com.tangem.blockchain.common.Amount
|
import com.tangem.blockchain.common.Amount
|
||||||
|
|
@ -11,6 +12,7 @@ import com.tangem.blockchain.common.transaction.Fee
|
||||||
import com.tangem.blockchain.common.transaction.TransactionFee
|
import com.tangem.blockchain.common.transaction.TransactionFee
|
||||||
import com.tangem.blockchainsdk.utils.fromNetworkId
|
import com.tangem.blockchainsdk.utils.fromNetworkId
|
||||||
import com.tangem.blockchainsdk.utils.toBlockchain
|
import com.tangem.blockchainsdk.utils.toBlockchain
|
||||||
|
import com.tangem.blockchainsdk.utils.toNetworkId
|
||||||
import com.tangem.core.ui.format.bigdecimal.fiat
|
import com.tangem.core.ui.format.bigdecimal.fiat
|
||||||
import com.tangem.core.ui.format.bigdecimal.format
|
import com.tangem.core.ui.format.bigdecimal.format
|
||||||
import com.tangem.domain.appcurrency.GetSelectedAppCurrencyUseCase
|
import com.tangem.domain.appcurrency.GetSelectedAppCurrencyUseCase
|
||||||
|
|
@ -52,8 +54,6 @@ import timber.log.Timber
|
||||||
import java.math.BigDecimal
|
import java.math.BigDecimal
|
||||||
import java.math.BigInteger
|
import java.math.BigInteger
|
||||||
import java.math.RoundingMode
|
import java.math.RoundingMode
|
||||||
import android.util.Base64
|
|
||||||
import com.tangem.blockchainsdk.utils.toNetworkId
|
|
||||||
|
|
||||||
@Suppress("LargeClass", "LongParameterList")
|
@Suppress("LargeClass", "LongParameterList")
|
||||||
internal class SwapInteractorImpl @AssistedInject constructor(
|
internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
|
|
@ -227,7 +227,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
val approveTransaction = createApprovalTransactionUseCase(
|
val approveTransaction = createApprovalTransactionUseCase(
|
||||||
fee = permissionOptions.txFee.fee,
|
fee = permissionOptions.txFee.fee,
|
||||||
userWalletId = userWalletId,
|
userWalletId = userWalletId,
|
||||||
cryptoCurrency = permissionOptions.fromToken as CryptoCurrency.Token,
|
cryptoCurrencyStatus = permissionOptions.fromTokenStatus,
|
||||||
amount = amount?.value,
|
amount = amount?.value,
|
||||||
contractAddress = permissionOptions.forTokenContractAddress,
|
contractAddress = permissionOptions.forTokenContractAddress,
|
||||||
spenderAddress = permissionOptions.spenderAddress,
|
spenderAddress = permissionOptions.spenderAddress,
|
||||||
|
|
@ -239,7 +239,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
val result = sendTransactionUseCase(
|
val result = sendTransactionUseCase(
|
||||||
txData = approveTransaction,
|
txData = approveTransaction,
|
||||||
userWallet = userWallet,
|
userWallet = userWallet,
|
||||||
network = permissionOptions.fromToken.network,
|
network = permissionOptions.fromTokenStatus.currency.network,
|
||||||
)
|
)
|
||||||
return result.fold(
|
return result.fold(
|
||||||
ifRight = { hash ->
|
ifRight = { hash ->
|
||||||
|
|
@ -546,7 +546,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
)
|
)
|
||||||
|
|
||||||
val result = validateTransactionUseCase(
|
val result = validateTransactionUseCase(
|
||||||
amount = amount.value.convertToSdkAmount(currency),
|
amount = amount.value.convertToSdkAmount(fromToken),
|
||||||
fee = fee,
|
fee = fee,
|
||||||
memo = null,
|
memo = null,
|
||||||
destination = getTokenAddress(fromToken.currency),
|
destination = getTokenAddress(fromToken.currency),
|
||||||
|
|
@ -842,7 +842,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
}
|
}
|
||||||
|
|
||||||
val txData = createTransferTransactionUseCase(
|
val txData = createTransferTransactionUseCase(
|
||||||
amount = amount.value.convertToSdkAmount(currencyToSend.currency),
|
amount = amount.value.convertToSdkAmount(currencyToSend),
|
||||||
fee = txFee.fee,
|
fee = txFee.fee,
|
||||||
memo = exchangeDataCex.txExtraId,
|
memo = exchangeDataCex.txExtraId,
|
||||||
destination = exchangeDataCex.txTo,
|
destination = exchangeDataCex.txTo,
|
||||||
|
|
@ -1022,7 +1022,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
val txFeeResult = getUnhandledFee(
|
val txFeeResult = getUnhandledFee(
|
||||||
amount = amount.value,
|
amount = amount.value,
|
||||||
userWallet = userWallet,
|
userWallet = userWallet,
|
||||||
cryptoCurrency = fromToken,
|
cryptoCurrencyStatus = fromTokenStatus,
|
||||||
)
|
)
|
||||||
|
|
||||||
val txFee = if (provider.type == ExchangeProviderType.CEX) {
|
val txFee = if (provider.type == ExchangeProviderType.CEX) {
|
||||||
|
|
@ -1520,12 +1520,12 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
private suspend fun getUnhandledFee(
|
private suspend fun getUnhandledFee(
|
||||||
amount: BigDecimal,
|
amount: BigDecimal,
|
||||||
userWallet: UserWallet,
|
userWallet: UserWallet,
|
||||||
cryptoCurrency: CryptoCurrency,
|
cryptoCurrencyStatus: CryptoCurrencyStatus,
|
||||||
): Either<GetFeeError, TransactionFee> {
|
): Either<GetFeeError, TransactionFee> {
|
||||||
return estimateFeeUseCase(
|
return estimateFeeUseCase(
|
||||||
amount = amount,
|
amount = amount,
|
||||||
userWallet = userWallet,
|
userWallet = userWallet,
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1560,7 +1560,7 @@ internal class SwapInteractorImpl @AssistedInject constructor(
|
||||||
// setting up amount for approve with given amount for swap [SwapApproveType.Limited]
|
// setting up amount for approve with given amount for swap [SwapApproveType.Limited]
|
||||||
val callData = SmartContractCallDataProviderFactory.getApprovalCallData(
|
val callData = SmartContractCallDataProviderFactory.getApprovalCallData(
|
||||||
spenderAddress = requireNotNull(spenderAddress) { "Spender address is null" },
|
spenderAddress = requireNotNull(spenderAddress) { "Spender address is null" },
|
||||||
amount = swapAmount.value.convertToSdkAmount(fromToken),
|
amount = swapAmount.value.convertToSdkAmount(fromTokenStatus),
|
||||||
blockchain = fromToken.network.toBlockchain(),
|
blockchain = fromToken.network.toBlockchain(),
|
||||||
)
|
)
|
||||||
val feeData = try {
|
val feeData = try {
|
||||||
|
|
|
||||||
|
|
@ -700,9 +700,11 @@ internal class SwapModel @Inject constructor(
|
||||||
private fun givePermissionsToSwap() {
|
private fun givePermissionsToSwap() {
|
||||||
modelScope.launch(dispatchers.main) {
|
modelScope.launch(dispatchers.main) {
|
||||||
runCatching {
|
runCatching {
|
||||||
val fromToken = requireNotNull(dataState.fromCryptoCurrency?.currency) {
|
val fromCryptoCurrency = requireNotNull(dataState.fromCryptoCurrency) {
|
||||||
"dataState.fromCurrency might not be null"
|
"dataState.fromCryptoCurrency might not be null"
|
||||||
}
|
}
|
||||||
|
val fromToken = fromCryptoCurrency.currency
|
||||||
|
|
||||||
val approveDataModel = requireNotNull(dataState.approveDataModel) {
|
val approveDataModel = requireNotNull(dataState.approveDataModel) {
|
||||||
"dataState.approveDataModel.spenderAddress shouldn't be null"
|
"dataState.approveDataModel.spenderAddress shouldn't be null"
|
||||||
}
|
}
|
||||||
|
|
@ -725,7 +727,7 @@ internal class SwapModel @Inject constructor(
|
||||||
permissionOptions = PermissionOptions(
|
permissionOptions = PermissionOptions(
|
||||||
approveData = approveDataModel,
|
approveData = approveDataModel,
|
||||||
forTokenContractAddress = (fromToken as? CryptoCurrency.Token)?.contractAddress.orEmpty(),
|
forTokenContractAddress = (fromToken as? CryptoCurrency.Token)?.contractAddress.orEmpty(),
|
||||||
fromToken = fromToken,
|
fromTokenStatus = fromCryptoCurrency,
|
||||||
approveType = approveType,
|
approveType = approveType,
|
||||||
txFee = feeForPermission,
|
txFee = feeForPermission,
|
||||||
spenderAddress = approveDataModel.spenderAddress,
|
spenderAddress = approveDataModel.spenderAddress,
|
||||||
|
|
|
||||||
|
|
@ -144,7 +144,7 @@ internal class YieldSupplyApproveModel @Inject constructor(
|
||||||
).getOrNull() ?: return
|
).getOrNull() ?: return
|
||||||
|
|
||||||
val approvalTransitionData = createApprovalTransactionUseCase(
|
val approvalTransitionData = createApprovalTransactionUseCase(
|
||||||
cryptoCurrency = cryptoCurrency,
|
cryptoCurrencyStatus = cryptoCurrencyStatus,
|
||||||
userWalletId = userWallet.walletId,
|
userWalletId = userWallet.walletId,
|
||||||
contractAddress = cryptoCurrency.contractAddress,
|
contractAddress = cryptoCurrency.contractAddress,
|
||||||
spenderAddress = contractAddress,
|
spenderAddress = contractAddress,
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue