Updated on 2026-08-14
This commit is contained in:
parent
47e284436a
commit
0387fb8a4f
10 changed files with 33 additions and 57 deletions
|
|
@ -2,12 +2,15 @@ package com.tangem.datasource.api.stakekit.models.response.model
|
|||
|
||||
import com.squareup.moshi.Json
|
||||
import com.squareup.moshi.JsonClass
|
||||
import com.tangem.datasource.api.stakekit.models.request.Address
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.action.StakingActionTypeDTO
|
||||
import org.joda.time.DateTime
|
||||
import java.math.BigDecimal
|
||||
|
||||
@JsonClass(generateAdapter = true)
|
||||
data class YieldBalanceWrapperDTO(
|
||||
@Json(name = "addresses")
|
||||
val addresses: Address,
|
||||
@Json(name = "balances")
|
||||
val balances: List<BalanceDTO>,
|
||||
@Json(name = "integrationId")
|
||||
|
|
|
|||
|
|
@ -1,12 +1,11 @@
|
|||
package com.tangem.datasource.local.token
|
||||
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.BalanceDTO
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.YieldBalanceWrapperDTO
|
||||
import com.tangem.datasource.local.datastore.core.StringKeyDataStore
|
||||
import com.tangem.domain.wallets.models.UserWalletId
|
||||
import com.tangem.utils.extensions.addOrReplace
|
||||
import kotlinx.coroutines.flow.Flow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import kotlinx.coroutines.flow.mapNotNull
|
||||
import kotlinx.coroutines.sync.Mutex
|
||||
import kotlinx.coroutines.sync.withLock
|
||||
|
||||
|
|
@ -30,17 +29,16 @@ internal class DefaultStakingBalanceStore(
|
|||
}
|
||||
}
|
||||
|
||||
override fun get(userWalletId: UserWalletId, integrationId: String): Flow<List<BalanceDTO>> {
|
||||
override fun get(userWalletId: UserWalletId, integrationId: String): Flow<YieldBalanceWrapperDTO> {
|
||||
return dataStore.get(userWalletId.stringValue)
|
||||
.map { balances ->
|
||||
balances.filter { it.integrationId == integrationId }
|
||||
.flatMap { it.balances }
|
||||
.mapNotNull { balances ->
|
||||
balances.firstOrNull { it.integrationId == integrationId }
|
||||
}
|
||||
}
|
||||
|
||||
override suspend fun getSyncOrNull(userWalletId: UserWalletId, integrationId: String): List<BalanceDTO>? {
|
||||
override suspend fun getSyncOrNull(userWalletId: UserWalletId, integrationId: String): YieldBalanceWrapperDTO? {
|
||||
return dataStore.getSyncOrNull(userWalletId.stringValue)
|
||||
?.firstOrNull { it.integrationId == integrationId }?.balances
|
||||
?.firstOrNull { it.integrationId == integrationId }
|
||||
}
|
||||
|
||||
override suspend fun store(userWalletId: UserWalletId, integrationId: String, item: YieldBalanceWrapperDTO) {
|
||||
|
|
|
|||
|
|
@ -1,6 +1,5 @@
|
|||
package com.tangem.datasource.local.token
|
||||
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.BalanceDTO
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.YieldBalanceWrapperDTO
|
||||
import com.tangem.domain.wallets.models.UserWalletId
|
||||
import kotlinx.coroutines.flow.Flow
|
||||
|
|
@ -13,9 +12,9 @@ interface StakingBalanceStore {
|
|||
|
||||
suspend fun store(userWalletId: UserWalletId, items: Set<YieldBalanceWrapperDTO>)
|
||||
|
||||
fun get(userWalletId: UserWalletId, integrationId: String): Flow<List<BalanceDTO>>
|
||||
fun get(userWalletId: UserWalletId, integrationId: String): Flow<YieldBalanceWrapperDTO>
|
||||
|
||||
suspend fun getSyncOrNull(userWalletId: UserWalletId, integrationId: String): List<BalanceDTO>?
|
||||
suspend fun getSyncOrNull(userWalletId: UserWalletId, integrationId: String): YieldBalanceWrapperDTO?
|
||||
|
||||
suspend fun store(userWalletId: UserWalletId, integrationId: String, item: YieldBalanceWrapperDTO)
|
||||
}
|
||||
|
|
@ -299,6 +299,7 @@ internal class DefaultStakingRepository(
|
|||
YieldBalanceWrapperDTO(
|
||||
balances = result,
|
||||
integrationId = requestBody.integrationId,
|
||||
addresses = requestBody.addresses,
|
||||
),
|
||||
)
|
||||
},
|
||||
|
|
@ -317,14 +318,7 @@ internal class DefaultStakingRepository(
|
|||
?: error("Could not get integrationId")
|
||||
stakingBalanceStore.get(userWalletId, integrationId)
|
||||
.collectLatest {
|
||||
send(
|
||||
yieldBalanceConverter.convert(
|
||||
YieldBalanceConverter.Data(
|
||||
balance = it,
|
||||
integrationId = integrationId,
|
||||
),
|
||||
),
|
||||
)
|
||||
send(yieldBalanceConverter.convert(it))
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -351,12 +345,7 @@ internal class DefaultStakingRepository(
|
|||
val result = stakingBalanceStore.getSyncOrNull(userWalletId, integrationId)
|
||||
?: return@withContext YieldBalance.Error
|
||||
|
||||
yieldBalanceConverter.convert(
|
||||
YieldBalanceConverter.Data(
|
||||
balance = result,
|
||||
integrationId = integrationId,
|
||||
),
|
||||
)
|
||||
yieldBalanceConverter.convert(result)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -385,7 +374,7 @@ internal class DefaultStakingRepository(
|
|||
null
|
||||
}
|
||||
}
|
||||
.distinct()
|
||||
.distinctBy { it.second }
|
||||
.map { getBalanceRequestData(it.first, it.second) }
|
||||
.ifEmpty { return@invokeOnExpire }
|
||||
val result = stakeKitApi.getMultipleYieldBalances(availableCurrencies).getOrThrow()
|
||||
|
|
|
|||
|
|
@ -1,24 +1,22 @@
|
|||
package com.tangem.data.staking.converters
|
||||
|
||||
import com.tangem.data.staking.converters.action.PendingActionConverter
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.BalanceDTO
|
||||
import com.tangem.domain.staking.model.stakekit.BalanceItem
|
||||
import com.tangem.domain.staking.model.stakekit.BalanceType
|
||||
import com.tangem.domain.staking.model.stakekit.YieldBalance
|
||||
import com.tangem.domain.staking.model.stakekit.YieldBalanceItem
|
||||
import com.tangem.datasource.api.stakekit.models.response.model.YieldBalanceWrapperDTO
|
||||
import com.tangem.domain.staking.model.stakekit.*
|
||||
import com.tangem.utils.converter.Converter
|
||||
|
||||
internal class YieldBalanceConverter : Converter<YieldBalanceConverter.Data, YieldBalance> {
|
||||
internal class YieldBalanceConverter : Converter<YieldBalanceWrapperDTO, YieldBalance> {
|
||||
|
||||
private val pendingActionConverter by lazy(LazyThreadSafetyMode.NONE) { PendingActionConverter() }
|
||||
|
||||
override fun convert(value: Data): YieldBalance {
|
||||
return if (value.balance.isEmpty()) {
|
||||
override fun convert(value: YieldBalanceWrapperDTO): YieldBalance {
|
||||
return if (value.balances.isEmpty()) {
|
||||
YieldBalance.Empty
|
||||
} else {
|
||||
YieldBalance.Data(
|
||||
address = value.addresses.address,
|
||||
balance = YieldBalanceItem(
|
||||
items = value.balance.map { item ->
|
||||
items = value.balances.map { item ->
|
||||
BalanceItem(
|
||||
type = BalanceType.valueOf(item.type.name),
|
||||
amount = item.amount,
|
||||
|
|
@ -35,9 +33,4 @@ internal class YieldBalanceConverter : Converter<YieldBalanceConverter.Data, Yie
|
|||
)
|
||||
}
|
||||
}
|
||||
|
||||
data class Data(
|
||||
val balance: List<BalanceDTO>,
|
||||
val integrationId: String?,
|
||||
)
|
||||
}
|
||||
|
|
@ -15,14 +15,7 @@ internal class YieldBalanceListConverter : Converter<Set<YieldBalanceWrapperDTO>
|
|||
YieldBalanceList.Empty
|
||||
} else {
|
||||
YieldBalanceList.Data(
|
||||
balances = value.map {
|
||||
converter.convert(
|
||||
YieldBalanceConverter.Data(
|
||||
balance = it.balances,
|
||||
integrationId = it.integrationId,
|
||||
),
|
||||
)
|
||||
},
|
||||
balances = value.map(converter::convert),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@ sealed class YieldBalance {
|
|||
|
||||
data class Data(
|
||||
val balance: YieldBalanceItem,
|
||||
val address: String,
|
||||
) : YieldBalance() {
|
||||
fun getTotalStakingBalance(): BigDecimal {
|
||||
return balance.items
|
||||
|
|
|
|||
|
|
@ -57,14 +57,16 @@ internal class CurrencyStatusOperations(
|
|||
|
||||
val hasCurrentNetworkTransactions = status.pendingTransactions.isNotEmpty()
|
||||
val currentTransactions = status.pendingTransactions.getOrElse(currency.id, ::emptySet)
|
||||
|
||||
val isCurrentAddressStaking =
|
||||
(yieldBalance as? YieldBalance.Data)?.address == status.address.defaultAddress.value
|
||||
val currentYieldBalance = yieldBalance.takeIf { isCurrentAddressStaking }
|
||||
return when {
|
||||
ignoreQuote -> CryptoCurrencyStatus.NoQuote(
|
||||
amount = amount,
|
||||
hasCurrentNetworkTransactions = hasCurrentNetworkTransactions,
|
||||
pendingTransactions = currentTransactions,
|
||||
networkAddress = status.address,
|
||||
yieldBalance = yieldBalance,
|
||||
yieldBalance = currentYieldBalance,
|
||||
)
|
||||
currency is CryptoCurrency.Token && currency.isCustom -> CryptoCurrencyStatus.Custom(
|
||||
amount = amount,
|
||||
|
|
@ -74,7 +76,7 @@ internal class CurrencyStatusOperations(
|
|||
hasCurrentNetworkTransactions = hasCurrentNetworkTransactions,
|
||||
pendingTransactions = currentTransactions,
|
||||
networkAddress = status.address,
|
||||
yieldBalance = yieldBalance,
|
||||
yieldBalance = currentYieldBalance,
|
||||
)
|
||||
quote == null -> CryptoCurrencyStatus.Loading
|
||||
else -> CryptoCurrencyStatus.Loaded(
|
||||
|
|
@ -85,7 +87,7 @@ internal class CurrencyStatusOperations(
|
|||
hasCurrentNetworkTransactions = hasCurrentNetworkTransactions,
|
||||
pendingTransactions = currentTransactions,
|
||||
networkAddress = status.address,
|
||||
yieldBalance = yieldBalance,
|
||||
yieldBalance = currentYieldBalance,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ import arrow.core.Either
|
|||
import arrow.core.left
|
||||
import arrow.core.right
|
||||
import com.tangem.domain.core.error.DataError
|
||||
import com.tangem.domain.staking.model.stakekit.YieldBalance
|
||||
import com.tangem.domain.tokens.error.CurrencyStatusError
|
||||
import com.tangem.domain.tokens.mock.MockNetworks
|
||||
import com.tangem.domain.tokens.mock.MockQuotes
|
||||
|
|
@ -123,7 +122,7 @@ internal class GetPrimaryCurrencyStatusUpdatesUseCaseTest {
|
|||
networkAddress = NetworkAddress.Single(
|
||||
defaultAddress = NetworkAddress.Address(value = "mock", NetworkAddress.Address.Type.Primary),
|
||||
),
|
||||
yieldBalance = YieldBalance.Error,
|
||||
yieldBalance = null,
|
||||
),
|
||||
)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
package com.tangem.domain.tokens.mock
|
||||
|
||||
import arrow.core.nonEmptyListOf
|
||||
import com.tangem.domain.staking.model.stakekit.YieldBalance
|
||||
import com.tangem.domain.tokens.model.CryptoCurrencyAmountStatus
|
||||
import com.tangem.domain.tokens.model.CryptoCurrencyStatus
|
||||
import com.tangem.domain.tokens.model.NetworkAddress
|
||||
|
|
@ -152,7 +151,7 @@ internal object MockTokensStates {
|
|||
pendingTransactions = emptySet(),
|
||||
hasCurrentNetworkTransactions = false,
|
||||
networkAddress = requireNotNull(networkStatus.value as? NetworkStatus.Verified).address,
|
||||
yieldBalance = YieldBalance.Error,
|
||||
yieldBalance = null,
|
||||
),
|
||||
)
|
||||
}
|
||||
|
|
@ -168,7 +167,7 @@ internal object MockTokensStates {
|
|||
.first { it.network == status.currency.network }
|
||||
.value as? NetworkStatus.Verified,
|
||||
).address,
|
||||
yieldBalance = YieldBalance.Error,
|
||||
yieldBalance = null,
|
||||
),
|
||||
)
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue