Updated on 2026-08-14

This commit is contained in:
Tangem 2024-09-02 13:21:06 +03:00
parent 47e284436a
commit a7fbf9b3ee
11 changed files with 60 additions and 29 deletions

View file

@ -2,7 +2,6 @@ package com.tangem.data.staking
import android.util.Base64
import arrow.core.raise.catch
import com.squareup.moshi.JsonAdapter
import com.squareup.moshi.Moshi
import com.tangem.blockchain.common.Blockchain
import com.tangem.blockchain.common.TransactionData
@ -108,8 +107,7 @@ internal class DefaultStakingRepository(
value = emptyMap<UserWalletId, Boolean>(),
)
private val tronStakeKitTransactionAdapter: JsonAdapter<TronStakeKitTransaction> =
moshi.adapter(TronStakeKitTransaction::class.java)
private val tronStakeKitTransactionAdapter by lazy { moshi.adapter(TronStakeKitTransaction::class.java) }
override fun getIntegrationKey(cryptoCurrencyId: CryptoCurrency.ID): String = with(cryptoCurrencyId) {
rawNetworkId.plus(rawCurrencyId)
@ -537,6 +535,7 @@ internal class DefaultStakingRepository(
args = ActionRequestBodyArgs(
amount = params.amount.toPlainString(),
validatorAddress = params.validatorAddress,
validatorAddresses = listOf(params.validatorAddress),
),
)
}

View file

@ -25,7 +25,8 @@ internal class YieldBalanceConverter : Converter<YieldBalanceConverter.Data, Yie
pricePerShare = item.pricePerShare,
rawCurrencyId = item.tokenDTO.coinGeckoId,
rawNetworkId = item.tokenDTO.network.name,
validatorAddress = item.validatorAddress,
// tron-specific. operates validatorAddresses instead of validatorAddress
validatorAddress = item.validatorAddress ?: item.validatorAddresses?.get(0),
date = item.date?.toDateTime(),
pendingActions = pendingActionConverter.convertList(item.pendingActions),
)

View file

@ -55,12 +55,12 @@ data class Yield(
val address: String,
val status: String,
val name: String,
val image: String?,
val website: String?,
val apr: SerializedBigDecimal?,
val commission: Double?,
val stakedBalance: String?,
val votingPower: Double?,
val image: String? = null,
val website: String? = null,
val apr: SerializedBigDecimal? = null,
val commission: Double? = null,
val stakedBalance: String? = null,
val votingPower: Double? = null,
val preferred: Boolean,
)

View file

@ -91,12 +91,12 @@ enum class BalanceType {
fun BalanceType.isClickable() = when (this) {
STAKED,
UNSTAKED,
LOCKED,
-> true
AVAILABLE,
UNSTAKING,
PREPARING,
REWARDS,
LOCKED,
UNLOCKING,
UNKNOWN,
-> false

View file

@ -85,7 +85,7 @@ internal class YieldBalancesConverter(
.mapNotNull { balance ->
val validator = yield.validators.firstOrNull {
balance.validatorAddress?.contains(it.address, ignoreCase = true) == true
}
} ?: mockedValidator
val cryptoAmount = balance.amount
val fiatAmount = cryptoCurrencyStatus.value.fiatRate?.times(cryptoAmount)
val unbonding = getUnbondingDate(balance.date)
@ -130,10 +130,10 @@ internal class YieldBalancesConverter(
BalanceType.UNSTAKED -> resourceReference(R.string.staking_unstaked) to
resourceReference(R.string.staking_unstaked_footer)
BalanceType.UNSTAKING -> resourceReference(R.string.staking_unstaking) to null
BalanceType.LOCKED -> resourceReference(R.string.staking_locked) to null
BalanceType.AVAILABLE -> null to null
BalanceType.PREPARING -> resourceReference(R.string.staking_preparing) to null
BalanceType.REWARDS -> null to null
BalanceType.LOCKED -> null to null
BalanceType.UNLOCKING -> null to null
BalanceType.UNKNOWN -> null to null
}
@ -164,5 +164,12 @@ internal class YieldBalancesConverter(
private companion object {
const val DAY_IN_MILLIS = 24 * 60 * 60 * 1000
private val mockedValidator = Yield.Validator(
address = "",
status = "",
name = "Mocked validator",
preferred = true,
)
}
}

View file

@ -15,7 +15,7 @@ internal object StakingClickIntentsStub : StakingClickIntents {
override fun onBackClick() {}
override fun onNextClick(actionType: StakingActionCommonType?, pendingAction: PendingAction?) {}
override fun onNextClick(actionTypeToOverwrite: StakingActionCommonType?, pendingAction: PendingAction?) {}
override fun onActionClick() {}

View file

@ -0,0 +1,24 @@
package com.tangem.features.staking.impl.presentation.state.transformers
import com.tangem.domain.staking.model.stakekit.action.StakingActionCommonType
import com.tangem.domain.tokens.model.CryptoCurrencyStatus
import com.tangem.features.staking.impl.presentation.state.*
import com.tangem.lib.crypto.BlockchainUtils.isTron
import com.tangem.utils.transformer.Transformer
internal class ActionTypeActiveStakeTransformer(
private val cryptoCurrencyStatus: CryptoCurrencyStatus,
private val activeStake: BalanceState,
) : Transformer<StakingUiState> {
override fun transform(prevState: StakingUiState): StakingUiState {
val isTron = isTron(cryptoCurrencyStatus.currency.network.id.value)
val actionType = if (activeStake.pendingActions.isEmpty() || isTron) {
StakingActionCommonType.EXIT
} else {
StakingActionCommonType.PENDING_OTHER
}
return prevState.copy(actionType = actionType)
}
}

View file

@ -137,9 +137,8 @@ internal class SetButtonsStateTransformer : Transformer<StakingUiState> {
private fun StakingUiState.onPrimaryClick() {
when (currentStep) {
StakingStep.InitialInfo -> {
val actionType = StakingActionCommonType.ENTER
clickIntents.onAmountValueChange("") // reset amount state
clickIntents.onNextClick(actionType)
clickIntents.onNextClick(StakingActionCommonType.ENTER)
}
StakingStep.Validators,
StakingStep.Amount,

View file

@ -15,7 +15,7 @@ internal interface StakingClickIntents : AmountScreenClickIntents {
fun onBackClick()
fun onNextClick(actionType: StakingActionCommonType? = null, pendingAction: PendingAction? = null)
fun onNextClick(actionTypeToOverwrite: StakingActionCommonType? = null, pendingAction: PendingAction? = null)
fun onActionClick()
@ -27,7 +27,7 @@ internal interface StakingClickIntents : AmountScreenClickIntents {
fun getFee(pendingAction: PendingAction?)
override fun onAmountNext() = onNextClick(actionType = null)
override fun onAmountNext() = onNextClick(actionTypeToOverwrite = null)
fun openValidators()

View file

@ -159,9 +159,9 @@ internal class StakingViewModel @Inject constructor(
stakingStateRouter.onBackClick()
}
override fun onNextClick(actionType: StakingActionCommonType?, pendingAction: PendingAction?) {
if (actionType != null) {
stateController.update { it.copy(actionType = actionType) }
override fun onNextClick(actionTypeToOverwrite: StakingActionCommonType?, pendingAction: PendingAction?) {
if (actionTypeToOverwrite != null) {
stateController.update { it.copy(actionType = actionTypeToOverwrite) }
}
stakingStateRouter.onNextClick()
when {
@ -395,7 +395,7 @@ internal class StakingViewModel @Inject constructor(
if (rewards != null && rewards.isSingleItem()) {
onActiveStake(rewards.first())
} else {
onNextClick(actionType = StakingActionCommonType.PENDING_REWARDS)
onNextClick(actionTypeToOverwrite = StakingActionCommonType.PENDING_REWARDS)
}
}
@ -405,7 +405,7 @@ internal class StakingViewModel @Inject constructor(
ShowActionSelectorBottomSheetTransformer(
pendingActions = activeStake.pendingActions,
onActionSelect = {
onNextClick(actionType = StakingActionCommonType.PENDING_OTHER, pendingAction = it)
onNextClick(actionTypeToOverwrite = StakingActionCommonType.PENDING_OTHER, pendingAction = it)
stateController.update(DismissBottomSheetStateTransformer())
},
onDismiss = {
@ -414,14 +414,10 @@ internal class StakingViewModel @Inject constructor(
),
)
} else {
val actionType = if (activeStake.pendingActions.isEmpty()) {
StakingActionCommonType.EXIT
} else {
StakingActionCommonType.PENDING_OTHER
}
stateController.update(ActionTypeActiveStakeTransformer(cryptoCurrencyStatus, activeStake))
stateController.update(ValidatorSelectChangeTransformer(activeStake.validator))
stateController.update(AmountChangeStateTransformer(cryptoCurrencyStatus, activeStake.cryptoValue, yield))
onNextClick(actionType, activeStake.pendingActions.firstOrNull())
onNextClick(null, activeStake.pendingActions.firstOrNull())
}
}

View file

@ -52,6 +52,11 @@ object BlockchainUtils {
return blockchain == Blockchain.Binance || blockchain == Blockchain.BinanceTestnet
}
fun isTron(networkId: String): Boolean {
val blockchain = Blockchain.fromId(networkId)
return blockchain == Blockchain.Tron || blockchain == Blockchain.TronTestnet
}
fun isSupportedNetworkId(networkId: String): Boolean {
return Blockchain.fromNetworkId(networkId)?.isSupportedInApp() ?: false
}