Updated on 2026-08-14
This commit is contained in:
commit
1146554992
1461 changed files with 62266 additions and 17096 deletions
|
|
@ -36,8 +36,6 @@ dependencies {
|
|||
api(projects.domain.visa)
|
||||
// endregion
|
||||
|
||||
implementation(projects.features.tangempay.details.api) // Remove after TANGEM_PAY_ACCOUNTS_REFACTOR_ENABLED
|
||||
|
||||
// region Project - Data
|
||||
implementation(projects.data.common)
|
||||
// endregion
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package com.tangem.data.account.converter
|
||||
|
||||
import arrow.core.getOrElse
|
||||
import arrow.core.right
|
||||
import com.tangem.datasource.api.tangemTech.models.account.WalletAccountDTO
|
||||
import com.tangem.domain.models.account.AccountId
|
||||
import com.tangem.domain.models.account.CryptoPortfolioIcon
|
||||
|
|
@ -8,7 +9,10 @@ import com.tangem.domain.models.account.DerivationIndex
|
|||
import com.tangem.domain.models.wallet.UserWalletId
|
||||
|
||||
internal fun String.toAccountId(userWalletId: UserWalletId): AccountId {
|
||||
return AccountId.forCryptoPortfolio(value = this, userWalletId = userWalletId).getOrElse {
|
||||
return when {
|
||||
startsWith(AccountId.PaymentAccountIdPrefix) -> AccountId.forPaymentAccount(userWalletId).right()
|
||||
else -> AccountId.forCryptoPortfolio(value = this, userWalletId = userWalletId)
|
||||
}.getOrElse {
|
||||
error("Unable to create AccountId from value: $this. Cause: $it")
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,14 +1,9 @@
|
|||
package com.tangem.data.account.di
|
||||
|
||||
import android.content.Context
|
||||
import androidx.datastore.core.DataStoreFactory
|
||||
import androidx.datastore.dataStoreFile
|
||||
import com.squareup.moshi.Moshi
|
||||
import com.tangem.data.account.converter.AccountConverterFactoryContainer
|
||||
import com.tangem.data.account.fetcher.DefaultWalletAccountsFetcher
|
||||
import com.tangem.data.account.repository.AccountsExpandedDTO
|
||||
import com.tangem.data.account.repository.DefaultAccountsCRUDRepository
|
||||
import com.tangem.data.account.repository.DefaultAccountsExpandedRepository
|
||||
import com.tangem.data.account.store.AccountsResponseStoreFactory
|
||||
import com.tangem.data.account.store.ArchivedAccountsStoreFactory
|
||||
import com.tangem.data.account.tokens.DefaultMainAccountTokensMigration
|
||||
|
|
@ -17,14 +12,9 @@ import com.tangem.data.common.account.WalletAccountsSaver
|
|||
import com.tangem.data.common.cache.etag.ETagsStore
|
||||
import com.tangem.data.common.currency.UserTokensSaver
|
||||
import com.tangem.datasource.api.tangemTech.TangemTechApi
|
||||
import com.tangem.datasource.di.NetworkMoshi
|
||||
import com.tangem.datasource.local.accounts.AccountTokenMigrationStore
|
||||
import com.tangem.datasource.local.datastore.RuntimeStateStore
|
||||
import com.tangem.datasource.utils.MoshiDataStoreSerializer
|
||||
import com.tangem.datasource.utils.mapWithStringKeyTypes
|
||||
import com.tangem.datasource.utils.setTypes
|
||||
import com.tangem.domain.account.repository.AccountsCRUDRepository
|
||||
import com.tangem.domain.account.repository.AccountsExpandedRepository
|
||||
import com.tangem.domain.account.tokens.MainAccountTokensMigration
|
||||
import com.tangem.utils.coroutines.AppCoroutineScope
|
||||
import com.tangem.utils.coroutines.CoroutineDispatcherProvider
|
||||
|
|
@ -63,28 +53,6 @@ internal object AccountDataModule {
|
|||
)
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
fun provideAccountsExpandedRepository(
|
||||
@NetworkMoshi moshi: Moshi,
|
||||
@ApplicationContext context: Context,
|
||||
appScope: AppCoroutineScope,
|
||||
): AccountsExpandedRepository {
|
||||
val store = DataStoreFactory.create<Map<String, Set<AccountsExpandedDTO>>>(
|
||||
serializer = MoshiDataStoreSerializer(
|
||||
moshi = moshi,
|
||||
types = mapWithStringKeyTypes(valueTypes = setTypes<AccountsExpandedDTO>()),
|
||||
defaultValue = emptyMap(),
|
||||
),
|
||||
produceFile = { context.dataStoreFile(fileName = "account_expanded_store") },
|
||||
scope = appScope,
|
||||
)
|
||||
|
||||
return DefaultAccountsExpandedRepository(
|
||||
store = store,
|
||||
)
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
fun provideWalletAccountsFetcher(impl: DefaultWalletAccountsFetcher): WalletAccountsFetcher = impl
|
||||
|
|
|
|||
|
|
@ -0,0 +1,18 @@
|
|||
package com.tangem.data.account.di
|
||||
|
||||
import com.tangem.data.account.repository.DefaultAccountsExpandedRepository
|
||||
import com.tangem.domain.account.repository.AccountsExpandedRepository
|
||||
import dagger.Binds
|
||||
import dagger.Module
|
||||
import dagger.hilt.InstallIn
|
||||
import dagger.hilt.components.SingletonComponent
|
||||
|
||||
@Module
|
||||
@InstallIn(SingletonComponent::class)
|
||||
internal interface AccountUtilsModule {
|
||||
|
||||
@Binds
|
||||
fun provideAccountsExpandedRepositoryFactory(
|
||||
factory: DefaultAccountsExpandedRepository.Factory,
|
||||
): AccountsExpandedRepository.Factory
|
||||
}
|
||||
|
|
@ -11,8 +11,6 @@ import com.tangem.domain.common.wallets.getSyncStrict
|
|||
import com.tangem.domain.core.flow.FlowProducerTools
|
||||
import com.tangem.domain.models.account.Account
|
||||
import com.tangem.domain.models.wallet.UserWallet
|
||||
import com.tangem.domain.models.wallet.UserWalletId
|
||||
import com.tangem.features.tangempay.TangemPayFeatureToggles
|
||||
import com.tangem.hot.sdk.model.HotWalletId
|
||||
import com.tangem.utils.coroutines.CoroutineDispatcherProvider
|
||||
import com.tangem.utils.logging.TangemLogger
|
||||
|
|
@ -23,7 +21,6 @@ import kotlinx.coroutines.ExperimentalCoroutinesApi
|
|||
import kotlinx.coroutines.flow.Flow
|
||||
import kotlinx.coroutines.flow.flowOn
|
||||
import kotlinx.coroutines.flow.map
|
||||
import kotlinx.coroutines.flow.onEach
|
||||
|
||||
/**
|
||||
* Default implementation of [SingleAccountListProducer].
|
||||
|
|
@ -39,7 +36,6 @@ internal class DefaultSingleAccountListProducer @AssistedInject constructor(
|
|||
@Assisted val params: SingleAccountListProducer.Params,
|
||||
override val flowProducerTools: FlowProducerTools,
|
||||
private val walletAccountListFlowFactory: WalletAccountListFlowFactory,
|
||||
private val tangemPayFeatureToggles: TangemPayFeatureToggles,
|
||||
private val userWalletsListRepository: UserWalletsListRepository,
|
||||
private val dispatchers: CoroutineDispatcherProvider,
|
||||
) : SingleAccountListProducer {
|
||||
|
|
@ -52,30 +48,7 @@ internal class DefaultSingleAccountListProducer @AssistedInject constructor(
|
|||
override fun produce(): Flow<AccountList> {
|
||||
val walletId = params.userWalletId
|
||||
logger.i("produce() called for $walletId")
|
||||
val accountListFlow: Flow<AccountList> = if (tangemPayFeatureToggles.isTangemPayAccountsRefactorEnabled) {
|
||||
combineWithPaymentAccount(walletId)
|
||||
} else {
|
||||
walletAccountListFlowFactory.create(userWalletId = walletId)
|
||||
}
|
||||
|
||||
return accountListFlow
|
||||
.onEach { accountList ->
|
||||
logger.i(
|
||||
"produce()[$walletId] emit: accounts=${accountList.accounts.size}, " +
|
||||
"currencies=${accountList.flattenMapCurrencies().size}",
|
||||
)
|
||||
}
|
||||
.flowOn(dispatchers.default)
|
||||
}
|
||||
|
||||
private fun combineWithPaymentAccount(walletId: UserWalletId): Flow<AccountList> {
|
||||
return walletAccountListFlowFactory.create(walletId)
|
||||
.onEach { accountList ->
|
||||
logger.i(
|
||||
"produce()[$walletId]: accountList received accounts=${accountList.accounts.size}, " +
|
||||
"currencies=${accountList.flattenMapCurrencies().size}",
|
||||
)
|
||||
}
|
||||
.map { accountList ->
|
||||
val userWallet = userWalletsListRepository.getSyncStrict(id = walletId)
|
||||
val isPaymentSupported = userWallet.isPaymentAccountSupported()
|
||||
|
|
@ -91,6 +64,7 @@ internal class DefaultSingleAccountListProducer @AssistedInject constructor(
|
|||
accountList
|
||||
}
|
||||
}
|
||||
.flowOn(dispatchers.default)
|
||||
}
|
||||
|
||||
private fun UserWallet.isPaymentAccountSupported(): Boolean = when (this) {
|
||||
|
|
|
|||
|
|
@ -1,17 +1,28 @@
|
|||
package com.tangem.data.account.repository
|
||||
|
||||
import android.content.Context
|
||||
import androidx.datastore.core.DataStore
|
||||
import androidx.datastore.core.DataStoreFactory
|
||||
import androidx.datastore.dataStoreFile
|
||||
import com.squareup.moshi.Json
|
||||
import com.squareup.moshi.JsonClass
|
||||
import com.squareup.moshi.Moshi
|
||||
import com.tangem.data.account.converter.toAccountId
|
||||
import com.tangem.datasource.di.NetworkMoshi
|
||||
import com.tangem.datasource.utils.MoshiDataStoreSerializer
|
||||
import com.tangem.datasource.utils.mapWithStringKeyTypes
|
||||
import com.tangem.datasource.utils.setTypes
|
||||
import com.tangem.domain.account.models.AccountExpandedState
|
||||
import com.tangem.domain.account.repository.AccountsExpandedRepository
|
||||
import com.tangem.domain.models.account.AccountId
|
||||
import com.tangem.domain.models.wallet.UserWalletId
|
||||
import com.tangem.utils.coroutines.AppCoroutineScope
|
||||
import dagger.hilt.android.qualifiers.ApplicationContext
|
||||
import kotlinx.coroutines.flow.Flow
|
||||
import kotlinx.coroutines.flow.map
|
||||
import javax.inject.Inject
|
||||
|
||||
internal class DefaultAccountsExpandedRepository(
|
||||
internal class DefaultAccountsExpandedRepository constructor(
|
||||
private val store: DataStore<Map<String, Set<AccountsExpandedDTO>>>,
|
||||
) : AccountsExpandedRepository {
|
||||
|
||||
|
|
@ -41,7 +52,7 @@ internal class DefaultAccountsExpandedRepository(
|
|||
}
|
||||
|
||||
override suspend fun clearStore() {
|
||||
store.updateData { emptyMap() }
|
||||
store.updateData { map -> map.mapValues { emptySet() } }
|
||||
}
|
||||
|
||||
override suspend fun update(accountState: AccountExpandedState) {
|
||||
|
|
@ -59,6 +70,28 @@ internal class DefaultAccountsExpandedRepository(
|
|||
map.plus(walletId.stringValue to updatedSet)
|
||||
}
|
||||
}
|
||||
|
||||
internal class Factory @Inject constructor(
|
||||
@NetworkMoshi private val moshi: Moshi,
|
||||
@ApplicationContext private val context: Context,
|
||||
private val appScope: AppCoroutineScope,
|
||||
) : AccountsExpandedRepository.Factory {
|
||||
override fun create(storeFileName: String): DefaultAccountsExpandedRepository {
|
||||
val store = DataStoreFactory.create<Map<String, Set<AccountsExpandedDTO>>>(
|
||||
serializer = MoshiDataStoreSerializer(
|
||||
moshi = moshi,
|
||||
types = mapWithStringKeyTypes(valueTypes = setTypes<AccountsExpandedDTO>()),
|
||||
defaultValue = emptyMap(),
|
||||
),
|
||||
produceFile = { context.dataStoreFile(fileName = storeFileName) },
|
||||
scope = appScope,
|
||||
)
|
||||
|
||||
return DefaultAccountsExpandedRepository(
|
||||
store = store,
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@JsonClass(generateAdapter = true)
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ import com.tangem.domain.core.flow.FlowProducerTools
|
|||
import com.tangem.domain.models.TokensSortType
|
||||
import com.tangem.domain.models.wallet.UserWallet
|
||||
import com.tangem.domain.models.wallet.UserWalletId
|
||||
import com.tangem.features.tangempay.TangemPayFeatureToggles
|
||||
import com.tangem.hot.sdk.model.HotWalletId
|
||||
import com.tangem.test.core.getEmittedValues
|
||||
import com.tangem.utils.coroutines.TestingCoroutineDispatcherProvider
|
||||
import io.mockk.*
|
||||
|
|
@ -31,21 +31,22 @@ class DefaultSingleAccountListProducerTest {
|
|||
|
||||
private val userWalletId = UserWalletId("011")
|
||||
private val flowProducerTools: FlowProducerTools = mockk()
|
||||
private val tangemPayFeatureToggles = mockk<TangemPayFeatureToggles> {
|
||||
every { this@mockk.isTangemPayAccountsRefactorEnabled } returns false
|
||||
private val userWallet = mockk<UserWallet.Hot> {
|
||||
every { walletId } returns userWalletId
|
||||
every { hotWalletId } returns mockk {
|
||||
every { authType } returns HotWalletId.AuthType.NoPassword
|
||||
}
|
||||
}
|
||||
private val userWalletsListRepository = mockk<UserWalletsListRepository>()
|
||||
private val userWallet = mockk<UserWallet> {
|
||||
every { this@mockk.walletId } returns userWalletId
|
||||
private val userWalletsListRepository = mockk<UserWalletsListRepository> {
|
||||
every { userWallets } returns MutableStateFlow<List<UserWallet>?>(value = listOf(userWallet))
|
||||
}
|
||||
|
||||
private val producer = DefaultSingleAccountListProducer(
|
||||
params = SingleAccountListProducer.Params(userWalletId = userWalletId),
|
||||
walletAccountListFlowFactory = walletAccountListFlowFactory,
|
||||
dispatchers = TestingCoroutineDispatcherProvider(),
|
||||
flowProducerTools = flowProducerTools,
|
||||
tangemPayFeatureToggles = tangemPayFeatureToggles,
|
||||
userWalletsListRepository = userWalletsListRepository,
|
||||
dispatchers = TestingCoroutineDispatcherProvider(),
|
||||
)
|
||||
|
||||
@AfterEach
|
||||
|
|
@ -56,8 +57,6 @@ class DefaultSingleAccountListProducerTest {
|
|||
@Test
|
||||
fun produce() = runTest {
|
||||
// Arrange
|
||||
MutableStateFlow(listOf(userWallet))
|
||||
|
||||
val accountList = AccountList.empty(userWalletId)
|
||||
every { walletAccountListFlowFactory.create(userWalletId) } returns flowOf(accountList)
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue