Updated on 2026-08-14
This commit is contained in:
parent
e98780ff93
commit
479d142807
283 changed files with 2338 additions and 2730 deletions
|
|
@ -12,7 +12,7 @@ object DomainLayer {
|
|||
|
||||
var onInitComplete: ((DomainModuleError?) -> Unit)? = null
|
||||
|
||||
fun init(data: Map<String, Any?>? = null) {
|
||||
fun init() {
|
||||
initActionStateLogger()
|
||||
|
||||
onInitComplete?.invoke(null)
|
||||
|
|
|
|||
|
|
@ -48,6 +48,7 @@ data class CardDTO(
|
|||
backupStatus = BackupStatus.fromSdkStatus(card.backupStatus),
|
||||
)
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
override fun equals(other: Any?): Boolean {
|
||||
if (this === other) return true
|
||||
if (other !is CardDTO) return false
|
||||
|
|
@ -120,13 +121,6 @@ data class CardDTO(
|
|||
val patch: Int,
|
||||
val type: SdkFirmwareVersion.FirmwareType,
|
||||
) : Comparable<SdkFirmwareVersion> {
|
||||
constructor(firmwareVersion: SdkFirmwareVersion) : this(
|
||||
major = firmwareVersion.major,
|
||||
minor = firmwareVersion.minor,
|
||||
patch = firmwareVersion.patch,
|
||||
type = firmwareVersion.type,
|
||||
)
|
||||
|
||||
val stringValue: String
|
||||
get() = StringBuilder()
|
||||
.append("$major.$minor")
|
||||
|
|
@ -134,6 +128,13 @@ data class CardDTO(
|
|||
.append(type.rawValue ?: "")
|
||||
.toString()
|
||||
|
||||
constructor(firmwareVersion: SdkFirmwareVersion) : this(
|
||||
major = firmwareVersion.major,
|
||||
minor = firmwareVersion.minor,
|
||||
patch = firmwareVersion.patch,
|
||||
type = firmwareVersion.type,
|
||||
)
|
||||
|
||||
override fun compareTo(other: SdkFirmwareVersion): Int = when {
|
||||
major != other.major -> major.compareTo(other.major)
|
||||
minor != other.minor -> minor.compareTo(other.minor)
|
||||
|
|
|
|||
|
|
@ -3,22 +3,21 @@ package com.tangem.domain.common
|
|||
import com.tangem.domain.features.BuildConfig
|
||||
|
||||
object LogConfig {
|
||||
val imageLoader: Boolean = false
|
||||
const val imageLoader: Boolean = false
|
||||
val storeAction: Boolean = BuildConfig.DEBUG
|
||||
val zendesk: Boolean = false
|
||||
const val zendesk: Boolean = false
|
||||
val network: NetworkLogConfig = NetworkLogConfig
|
||||
val analyticsHandlers: AnalyticsHandlersLogConfig = AnalyticsHandlersLogConfig
|
||||
}
|
||||
|
||||
object NetworkLogConfig {
|
||||
val mercuryoService: Boolean = false
|
||||
val moonPayService: Boolean = false
|
||||
val paymentologyApiService: Boolean = BuildConfig.DEBUG
|
||||
const val mercuryoService: Boolean = false
|
||||
const val moonPayService: Boolean = false
|
||||
val blockchainSdkNetwork: Boolean = BuildConfig.DEBUG
|
||||
}
|
||||
|
||||
object AnalyticsHandlersLogConfig {
|
||||
val firebase: Boolean = false
|
||||
val appsFlyer: Boolean = false
|
||||
val amplitude: Boolean = false
|
||||
const val firebase: Boolean = false
|
||||
const val appsFlyer: Boolean = false
|
||||
const val amplitude: Boolean = false
|
||||
}
|
||||
|
|
@ -6,35 +6,8 @@ import com.tangem.common.CardIdRange
|
|||
import com.tangem.common.contains
|
||||
|
||||
object SaltPayWorkaround {
|
||||
fun tokenFrom(blockchain: Blockchain): Token {
|
||||
return when (blockchain) {
|
||||
Blockchain.SaltPay -> Token(
|
||||
name = "WXDAI",
|
||||
symbol = "wxDAI",
|
||||
contractAddress = "0x4200000000000000000000000000000000000006",
|
||||
decimals = 18,
|
||||
id = "wrapped-xdai",
|
||||
)
|
||||
else -> throw IllegalArgumentException()
|
||||
}
|
||||
}
|
||||
|
||||
fun isVisaBatchId(batchId: String): Boolean = visaBatches.contains(batchId)
|
||||
|
||||
fun isWalletCardId(cardId: String): Boolean {
|
||||
return if (walletCardIds.contains(cardId)) true else walletCardIdRanges.contains(cardId)
|
||||
}
|
||||
|
||||
val visaBatches = listOf(
|
||||
"AE02",
|
||||
"AE03",
|
||||
) + attachTestVisaBatches()
|
||||
|
||||
private fun attachTestVisaBatches(): List<String> {
|
||||
return listOf(
|
||||
"FF03",
|
||||
)
|
||||
}
|
||||
@Suppress("MagicNumber")
|
||||
val visaBatches = listOf("AE02", "AE03") + attachTestVisaBatches()
|
||||
|
||||
val walletCardIds = listOf(
|
||||
"AC01000000033503",
|
||||
|
|
@ -67,19 +40,38 @@ object SaltPayWorkaround {
|
|||
"AC03000000076229",
|
||||
) + attachTestWalletCardIds()
|
||||
|
||||
private fun attachTestWalletCardIds(): List<String> {
|
||||
return listOf(
|
||||
"FF04000000000232",
|
||||
)
|
||||
}
|
||||
|
||||
val walletCardIdRanges = listOf(
|
||||
CardIdRange("AC05000000000003", "AC05000000023997")!!,
|
||||
) + attachTestWalletCardIdRanges()
|
||||
|
||||
fun tokenFrom(blockchain: Blockchain): Token {
|
||||
return when (blockchain) {
|
||||
Blockchain.SaltPay -> Token(
|
||||
name = "WXDAI",
|
||||
symbol = "wxDAI",
|
||||
contractAddress = "0x4200000000000000000000000000000000000006",
|
||||
decimals = 18,
|
||||
id = "wrapped-xdai",
|
||||
)
|
||||
else -> error("It is not SaltPay")
|
||||
}
|
||||
}
|
||||
|
||||
fun isVisaBatchId(batchId: String): Boolean = visaBatches.contains(batchId)
|
||||
|
||||
fun isWalletCardId(cardId: String): Boolean {
|
||||
return if (walletCardIds.contains(cardId)) true else walletCardIdRanges.contains(cardId)
|
||||
}
|
||||
|
||||
private fun attachTestVisaBatches(): List<String> {
|
||||
return listOf("FF03")
|
||||
}
|
||||
|
||||
private fun attachTestWalletCardIds(): List<String> {
|
||||
return listOf("FF04000000000232")
|
||||
}
|
||||
|
||||
private fun attachTestWalletCardIdRanges(): List<CardIdRange> {
|
||||
return listOf(
|
||||
CardIdRange("FF04000000000000", "FF04999999999999")!!,
|
||||
)
|
||||
return listOf(CardIdRange("FF04000000000000", "FF04999999999999")!!)
|
||||
}
|
||||
}
|
||||
|
|
@ -13,10 +13,6 @@ object TapWorkarounds {
|
|||
private const val TEST_CARD_BATCH = "99FF"
|
||||
private const val TEST_CARD_ID_STARTS_WITH = "FF99"
|
||||
|
||||
fun isStart2CoinIssuer(cardIssuer: String?): Boolean {
|
||||
return cardIssuer?.lowercase(Locale.US) == START_2_COIN_ISSUER
|
||||
}
|
||||
|
||||
val CardDTO.isTangemTwins: Boolean
|
||||
get() = TwinsHelper.getTwinCardNumber(cardId) != null
|
||||
|
||||
|
|
@ -41,6 +37,7 @@ object TapWorkarounds {
|
|||
|
||||
val CardDTO.useOldStyleDerivation: Boolean
|
||||
get() = batchId == "AC01" || batchId == "AC02" || batchId == "CB95"
|
||||
|
||||
val CardDTO.derivationStyle: DerivationStyle?
|
||||
get() = if (!settings.isHDWalletAllowed) {
|
||||
null
|
||||
|
|
@ -49,7 +46,6 @@ object TapWorkarounds {
|
|||
} else {
|
||||
DerivationStyle.NEW
|
||||
}
|
||||
|
||||
val CardDTO.isExcluded: Boolean
|
||||
get() {
|
||||
val excludedBatch = excludedBatches.contains(batchId)
|
||||
|
|
@ -60,9 +56,6 @@ object TapWorkarounds {
|
|||
val CardDTO.isNotSupportedInThatRelease: Boolean
|
||||
get() = false
|
||||
|
||||
fun CardDTO.getTangemNoteBlockchain(): Blockchain? =
|
||||
tangemNoteBatches[batchId] ?: if (isSaltPay) Blockchain.Gnosis else null
|
||||
|
||||
private val tangemNoteBatches = mapOf(
|
||||
"AB01" to Blockchain.Bitcoin,
|
||||
"AB02" to Blockchain.Ethereum,
|
||||
|
|
@ -78,16 +71,16 @@ object TapWorkarounds {
|
|||
"AB12" to Blockchain.Ethereum,
|
||||
)
|
||||
|
||||
private val excludedBatches = listOf("0027", "0030", "0031", "0035")
|
||||
|
||||
private val excludedIssuers = listOf("TTM BANK")
|
||||
|
||||
fun CardDTO.getTangemNoteBlockchain(): Blockchain? =
|
||||
tangemNoteBatches[batchId] ?: if (isSaltPay) Blockchain.Gnosis else null
|
||||
|
||||
fun isStart2CoinIssuer(cardIssuer: String?): Boolean {
|
||||
return cardIssuer?.lowercase(Locale.US) == START_2_COIN_ISSUER
|
||||
}
|
||||
|
||||
fun Card.getTangemNoteBlockchain(): Blockchain? = tangemNoteBatches[batchId] ?: null
|
||||
|
||||
private val excludedBatches = listOf(
|
||||
"0027",
|
||||
"0030",
|
||||
"0031",
|
||||
"0035",
|
||||
)
|
||||
|
||||
private val excludedIssuers = listOf(
|
||||
"TTM BANK",
|
||||
)
|
||||
}
|
||||
|
|
@ -2,47 +2,32 @@ package com.tangem.domain.common
|
|||
|
||||
import com.tangem.crypto.CryptoUtils
|
||||
|
||||
class TwinsHelper {
|
||||
companion object {
|
||||
const val TWIN_FILE_NAME = "TwinPublicKey"
|
||||
object TwinsHelper {
|
||||
private val firstCardSeries = listOf("CB61", "CB64")
|
||||
private val secondCardSeries = listOf("CB62", "CB65")
|
||||
|
||||
fun verifyTwinPublicKey(issuerData: ByteArray, cardWalletPublicKey: ByteArray?): Boolean {
|
||||
if (issuerData.size < 65 || cardWalletPublicKey == null) return false
|
||||
@Suppress("MagicNumber")
|
||||
fun verifyTwinPublicKey(issuerData: ByteArray, cardWalletPublicKey: ByteArray?): Boolean {
|
||||
if (issuerData.size < 65 || cardWalletPublicKey == null) return false
|
||||
|
||||
val publicKey = issuerData.sliceArray(0 until 65)
|
||||
val signedKey = issuerData.sliceArray(65 until issuerData.size)
|
||||
return CryptoUtils.verify(cardWalletPublicKey, publicKey, signedKey)
|
||||
}
|
||||
val publicKey = issuerData.sliceArray(0 until 65)
|
||||
val signedKey = issuerData.sliceArray(65 until issuerData.size)
|
||||
return CryptoUtils.verify(cardWalletPublicKey, publicKey, signedKey)
|
||||
}
|
||||
|
||||
fun getTwinCardNumber(cardId: String): TwinCardNumber? = when {
|
||||
firstCardSeries.any(cardId::startsWith) -> TwinCardNumber.First
|
||||
secondCardSeries.any(cardId::startsWith) -> TwinCardNumber.Second
|
||||
else -> null
|
||||
}
|
||||
fun getTwinCardNumber(cardId: String): TwinCardNumber? = when {
|
||||
firstCardSeries.any(cardId::startsWith) -> TwinCardNumber.First
|
||||
secondCardSeries.any(cardId::startsWith) -> TwinCardNumber.Second
|
||||
else -> null
|
||||
}
|
||||
|
||||
fun getPairCardSeries(cardId: String): String? {
|
||||
return when (getTwinCardNumber(cardId) ?: return null) {
|
||||
TwinCardNumber.First -> {
|
||||
val index = firstCardSeries.indexOf(cardId.take(4))
|
||||
secondCardSeries[index]
|
||||
}
|
||||
TwinCardNumber.Second -> {
|
||||
val index = secondCardSeries.indexOf(cardId.take(4))
|
||||
firstCardSeries[index]
|
||||
}
|
||||
}
|
||||
}
|
||||
@Suppress("MagicNumber")
|
||||
fun getTwinCardIdForUser(cardId: String): String {
|
||||
if (cardId.length < 16) return cardId
|
||||
|
||||
fun getTwinCardIdForUser(cardId: String): String {
|
||||
if (cardId.length < 16) return cardId
|
||||
|
||||
val twinCardId = cardId.substring(11..14)
|
||||
val twinCardNumber = getTwinCardNumber(cardId)?.number ?: 1
|
||||
return "$twinCardId #$twinCardNumber"
|
||||
}
|
||||
|
||||
private val firstCardSeries = listOf("CB61", "CB64")
|
||||
private val secondCardSeries = listOf("CB62", "CB65")
|
||||
val twinCardId = cardId.substring(11..14)
|
||||
val twinCardNumber = getTwinCardNumber(cardId)?.number ?: 1
|
||||
return "$twinCardId #$twinCardNumber"
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ package com.tangem.domain.common.extensions
|
|||
|
||||
import com.tangem.blockchain.common.Blockchain
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
fun Blockchain.Companion.fromNetworkId(networkId: String): Blockchain? {
|
||||
return when (networkId) {
|
||||
"arbitrum-one" -> Blockchain.Arbitrum
|
||||
|
|
@ -52,6 +53,7 @@ fun Blockchain.Companion.fromNetworkId(networkId: String): Blockchain? {
|
|||
}
|
||||
}
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
fun Blockchain.toNetworkId(): String {
|
||||
return when (this) {
|
||||
Blockchain.Unknown -> "unknown"
|
||||
|
|
@ -103,6 +105,7 @@ fun Blockchain.toNetworkId(): String {
|
|||
}
|
||||
}
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
fun Blockchain.toCoinId(): String {
|
||||
return when (this) {
|
||||
Blockchain.Binance, Blockchain.BinanceTestnet, Blockchain.BSC, Blockchain.BSCTestnet -> "binancecoin"
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ interface DataConverterVisitor<Data, Result> {
|
|||
|
||||
interface FieldDataConverter<Result> : DataConverterVisitor<FieldData, Result>
|
||||
|
||||
abstract class BaseFieldDataConverter<Result>() : FieldDataConverter<Result> {
|
||||
abstract class BaseFieldDataConverter<Result> : FieldDataConverter<Result> {
|
||||
protected val collectIds: List<FieldId>
|
||||
get() = getIdToCollect()
|
||||
|
||||
|
|
@ -31,7 +31,7 @@ abstract class BaseFieldDataConverter<Result>() : FieldDataConverter<Result> {
|
|||
|
||||
class FieldToJsonConverter(
|
||||
private val fieldsToConvert: List<FieldId> = listOf(),
|
||||
protected val jsonConverter: MoshiJsonConverter
|
||||
protected val jsonConverter: MoshiJsonConverter,
|
||||
) : BaseFieldDataConverter<String>() {
|
||||
|
||||
override fun getConvertedData(): String = jsonConverter.toJson(collectedData, " ")
|
||||
|
|
|
|||
|
|
@ -13,26 +13,34 @@ import timber.log.Timber
|
|||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
abstract class CustomTokenValidator<T> : Validator<T, AddCustomTokenError>
|
||||
interface CustomTokenValidator<T> : Validator<T, AddCustomTokenError>
|
||||
|
||||
class StringIsEmptyValidator : CustomTokenValidator<String>() {
|
||||
class StringIsEmptyValidator : CustomTokenValidator<String> {
|
||||
override fun validate(data: String?): AddCustomTokenError? = when {
|
||||
data == null || data.isEmpty() -> null
|
||||
else -> AddCustomTokenError.FieldIsNotEmpty
|
||||
}
|
||||
}
|
||||
|
||||
class StringIsNotEmptyValidator : CustomTokenValidator<String>() {
|
||||
class StringIsNotEmptyValidator : CustomTokenValidator<String> {
|
||||
override fun validate(data: String?): AddCustomTokenError? = when {
|
||||
data == null || data.isEmpty() -> AddCustomTokenError.FieldIsEmpty
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
|
||||
class TokenContractAddressValidator : CustomTokenValidator<String>() {
|
||||
class TokenContractAddressValidator : CustomTokenValidator<String> {
|
||||
|
||||
private var blockchain: Blockchain = Blockchain.Unknown
|
||||
|
||||
private val successAddressValidator = object : AddressService() {
|
||||
override fun makeAddress(walletPublicKey: ByteArray, curve: EllipticCurve?): String {
|
||||
throw UnsupportedOperationException()
|
||||
}
|
||||
|
||||
override fun validate(address: String): Boolean = true
|
||||
}
|
||||
|
||||
fun nextValidationFor(blockchain: Blockchain) {
|
||||
this.blockchain = blockchain
|
||||
}
|
||||
|
|
@ -63,32 +71,25 @@ class TokenContractAddressValidator : CustomTokenValidator<String>() {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
private val successAddressValidator = object : AddressService() {
|
||||
override fun makeAddress(walletPublicKey: ByteArray, curve: EllipticCurve?): String {
|
||||
throw UnsupportedOperationException()
|
||||
}
|
||||
|
||||
override fun validate(address: String): Boolean = true
|
||||
}
|
||||
}
|
||||
|
||||
class TokenNetworkValidator : CustomTokenValidator<Blockchain>() {
|
||||
class TokenNetworkValidator : CustomTokenValidator<Blockchain> {
|
||||
override fun validate(data: Blockchain?): AddCustomTokenError? = when (data) {
|
||||
null, Blockchain.Unknown -> AddCustomTokenError.NetworkIsNotSelected
|
||||
else -> null
|
||||
}
|
||||
}
|
||||
|
||||
class TokenNameValidator : CustomTokenValidator<String>() {
|
||||
class TokenNameValidator : CustomTokenValidator<String> {
|
||||
override fun validate(data: String?): AddCustomTokenError? = StringIsNotEmptyValidator().validate(data)
|
||||
}
|
||||
|
||||
class TokenSymbolValidator : CustomTokenValidator<String>() {
|
||||
class TokenSymbolValidator : CustomTokenValidator<String> {
|
||||
override fun validate(data: String?): AddCustomTokenError? = StringIsNotEmptyValidator().validate(data)
|
||||
}
|
||||
|
||||
class TokenDecimalsValidator : CustomTokenValidator<String>() {
|
||||
@Suppress("MagicNumber")
|
||||
class TokenDecimalsValidator : CustomTokenValidator<String> {
|
||||
override fun validate(data: String?): AddCustomTokenError? {
|
||||
val decimal = data?.toIntOrNull() ?: return AddCustomTokenError.FieldIsEmpty
|
||||
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@ class UserWalletId(
|
|||
return stringValue.hashCode()
|
||||
}
|
||||
|
||||
@Suppress("MagicNumber")
|
||||
override fun toString(): String {
|
||||
return with(stringValue) {
|
||||
"UserWalletId(${take(3)}...${takeLast(3)})"
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@ import kotlinx.coroutines.flow.onEach
|
|||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
@Suppress("MagicNumber")
|
||||
class ValueDebouncer<T>(
|
||||
private val initialValue: T,
|
||||
private val debounceDuration: Long = 400,
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ class AddCustomTokenService(
|
|||
return@withContext emptyList()
|
||||
}
|
||||
|
||||
throw IllegalStateException("Unreachable code because runCatching must return result")
|
||||
error("Unreachable code because runCatching must return result")
|
||||
}
|
||||
|
||||
private fun selectNetworksForSearch(networkId: String?): String {
|
||||
|
|
|
|||
|
|
@ -18,11 +18,11 @@ sealed class CustomCurrency(
|
|||
|
||||
class CustomBlockchain(
|
||||
network: Blockchain,
|
||||
derivationPath: DerivationPath?
|
||||
derivationPath: DerivationPath?,
|
||||
) : CustomCurrency(network, derivationPath) {
|
||||
|
||||
class Converter(
|
||||
private val derivationStyle: DerivationStyle?
|
||||
private val derivationStyle: DerivationStyle?,
|
||||
) : BaseFieldDataConverter<CustomBlockchain>() {
|
||||
override fun getConvertedData(): CustomBlockchain {
|
||||
val mainNetwork = collectedData[CustomTokenFieldId.Network] as Blockchain
|
||||
|
|
@ -30,24 +30,25 @@ sealed class CustomCurrency(
|
|||
val derivationPath = AddCustomTokenState.getDerivationPath(
|
||||
mainNetwork,
|
||||
derivationPathNetwork,
|
||||
derivationStyle
|
||||
derivationStyle,
|
||||
)
|
||||
return CustomBlockchain(mainNetwork, derivationPath)
|
||||
}
|
||||
|
||||
override fun getIdToCollect(): List<FieldId> = listOf(CustomTokenFieldId.Network, CustomTokenFieldId.DerivationPath)
|
||||
override fun getIdToCollect(): List<FieldId> =
|
||||
listOf(CustomTokenFieldId.Network, CustomTokenFieldId.DerivationPath)
|
||||
}
|
||||
}
|
||||
|
||||
class CustomToken(
|
||||
val token: Token,
|
||||
network: Blockchain,
|
||||
derivationPath: DerivationPath?
|
||||
derivationPath: DerivationPath?,
|
||||
) : CustomCurrency(network, derivationPath) {
|
||||
|
||||
class Converter(
|
||||
private val tokenId: String?,
|
||||
private val derivationStyle: DerivationStyle?
|
||||
private val derivationStyle: DerivationStyle?,
|
||||
) : BaseFieldDataConverter<CustomToken>() {
|
||||
|
||||
override fun getConvertedData(): CustomToken {
|
||||
|
|
@ -56,7 +57,7 @@ sealed class CustomCurrency(
|
|||
val derivationPath = AddCustomTokenState.getDerivationPath(
|
||||
mainNetwork,
|
||||
derivationPathNetwork,
|
||||
derivationStyle
|
||||
derivationStyle,
|
||||
)
|
||||
|
||||
val token = Token(
|
||||
|
|
|
|||
|
|
@ -31,7 +31,10 @@ sealed class AddCustomTokenAction : Action {
|
|||
data class OnTokenNetworkChanged(val blockchainNetwork: Field.Data<Blockchain>) : AddCustomTokenAction()
|
||||
data class OnTokenNameChanged(val tokenName: Field.Data<String>) : AddCustomTokenAction()
|
||||
data class OnTokenSymbolChanged(val tokenSymbol: Field.Data<String>) : AddCustomTokenAction()
|
||||
data class OnTokenDerivationPathChanged(val blockchainDerivationPath: Field.Data<Blockchain>) : AddCustomTokenAction()
|
||||
data class OnTokenDerivationPathChanged(
|
||||
val blockchainDerivationPath: Field.Data<Blockchain>,
|
||||
) : AddCustomTokenAction()
|
||||
|
||||
data class OnTokenDecimalsChanged(val tokenDecimals: Field.Data<String>) : AddCustomTokenAction()
|
||||
object OnAddCustomTokenClicked : AddCustomTokenAction()
|
||||
|
||||
|
|
@ -51,7 +54,7 @@ sealed class AddCustomTokenAction : Action {
|
|||
data class Remove(val warnings: Set<AddCustomTokenError.Warning>) : Warning()
|
||||
data class Replace(
|
||||
val remove: Set<AddCustomTokenError.Warning>,
|
||||
val add: Set<AddCustomTokenError.Warning>
|
||||
val add: Set<AddCustomTokenError.Warning>,
|
||||
) : Warning()
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -66,6 +66,7 @@ import timber.log.Timber
|
|||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
@Suppress("LargeClass")
|
||||
internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomTokenHub") {
|
||||
|
||||
private val hubState: AddCustomTokenState
|
||||
|
|
@ -79,10 +80,11 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
return storeState.copy(addCustomTokensState = newHubState)
|
||||
}
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
override suspend fun handleAction(
|
||||
action: Action,
|
||||
storeState: DomainState,
|
||||
cancel: ValueCallback<Action>
|
||||
cancel: ValueCallback<Action>,
|
||||
) {
|
||||
if (action !is AddCustomTokenAction) return
|
||||
|
||||
|
|
@ -225,7 +227,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
val derivationField = DerivationPath.getField<TokenDerivationPathField>()
|
||||
derivationField.data = derivationField.data.copy(
|
||||
value = Blockchain.Unknown,
|
||||
isUserInput = false
|
||||
isUserInput = false,
|
||||
)
|
||||
state.setField(derivationField)
|
||||
dispatchOnMain(UpdateForm(hubState))
|
||||
|
|
@ -344,6 +346,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
}
|
||||
}
|
||||
|
||||
@Suppress("MagicNumber")
|
||||
private suspend fun requestInfoAboutToken(contractAddress: String): List<CoinsResponse.Coin> {
|
||||
val tangemTechServiceManager = requireNotNull(hubState.tangemTechServiceManager)
|
||||
dispatchOnMain(Screen.UpdateTokenFields(listOf(ContractAddress to ViewStates.TokenField(isLoading = true))))
|
||||
|
|
@ -375,7 +378,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
tokenId: String? = hubState.foundToken?.id,
|
||||
tokenContractAddress: String = ContractAddress.getFieldValue(),
|
||||
tokenNetworkId: String = Network.getFieldValue<Blockchain>().toNetworkId(),
|
||||
selectedDerivation: Blockchain = DerivationPath.getFieldValue()
|
||||
selectedDerivation: Blockchain = DerivationPath.getFieldValue(),
|
||||
): Boolean {
|
||||
val savedCurrencies = hubState.appSavedCurrencies ?: return false
|
||||
|
||||
|
|
@ -388,6 +391,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
val sameAddress = tokenContractAddress == wrappedCurrency.token.contractAddress
|
||||
val sameBlockchain = Blockchain.fromNetworkId(tokenNetworkId) == wrappedCurrency.blockchain
|
||||
val sameDerivationPath = derivationPath?.rawPath == wrappedCurrency.derivationPath
|
||||
@Suppress("ComplexCondition")
|
||||
if (sameId && sameAddress && sameBlockchain && sameDerivationPath) {
|
||||
return true
|
||||
}
|
||||
|
|
@ -399,7 +403,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
|
||||
private fun isBlockchainPersistIntoAppSavedTokensList(
|
||||
selectedNetwork: Blockchain = Network.getFieldValue(),
|
||||
selectedDerivation: Blockchain = DerivationPath.getFieldValue()
|
||||
selectedDerivation: Blockchain = DerivationPath.getFieldValue(),
|
||||
): Boolean {
|
||||
val state = hubState
|
||||
val savedCurrencies = state.appSavedCurrencies ?: return false
|
||||
|
|
@ -419,11 +423,11 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
}
|
||||
|
||||
private fun getDerivationPathFromSelectedBlockchain(
|
||||
selectedDerivationBlockchain: Blockchain
|
||||
selectedDerivationBlockchain: Blockchain,
|
||||
): com.tangem.common.hdWallet.DerivationPath? = AddCustomTokenState.getDerivationPath(
|
||||
mainNetwork = Network.getFieldValue(),
|
||||
derivationNetwork = selectedDerivationBlockchain,
|
||||
derivationStyle = hubState.cardDerivationStyle
|
||||
derivationStyle = hubState.cardDerivationStyle,
|
||||
)
|
||||
|
||||
private suspend fun fillTokenFields(token: CoinsResponse.Coin, coinNetwork: CoinsResponse.Coin.Network) {
|
||||
|
|
@ -482,7 +486,7 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
@Throws
|
||||
private fun throwUnAppropriateInitialization(objName: String) {
|
||||
throw AddCustomTokenError.UnAppropriateInitialization(
|
||||
"AddCustomTokenHub", "$objName must be not NULL"
|
||||
"AddCustomTokenHub", "$objName must be not NULL",
|
||||
)
|
||||
}
|
||||
|
||||
|
|
@ -567,16 +571,14 @@ internal class AddCustomTokenHub : BaseStoreHub<AddCustomTokenState>("AddCustomT
|
|||
private suspend fun AddCustomTokenError.Warning.remove() {
|
||||
dispatchOnMain(Warning.Remove(setOf(this)))
|
||||
}
|
||||
|
||||
private suspend fun AddCustomTokenError.Warning.replaceBy(to: AddCustomTokenError.Warning) {
|
||||
dispatchOnMain(Warning.Replace(setOf(this), setOf(to)))
|
||||
}
|
||||
}
|
||||
|
||||
@Suppress("ComplexMethod")
|
||||
private class AddCustomTokenReducer(
|
||||
private val globalState: DomainGlobalState,
|
||||
) : ReStoreReducer<AddCustomTokenState> {
|
||||
|
||||
@Suppress("LongMethod")
|
||||
override fun reduceAction(action: Action, state: AddCustomTokenState): AddCustomTokenState {
|
||||
return when (action) {
|
||||
is Init.SetAddedCurrencies -> {
|
||||
|
|
|
|||
|
|
@ -265,7 +265,7 @@ data class AddCustomTokenState(
|
|||
private var builder: StringBuilder = StringBuilder()
|
||||
|
||||
override fun convert(action: Action, stateHolder: DomainState): String? {
|
||||
val action = (action as? AddCustomTokenAction) ?: return null
|
||||
val action = action as? AddCustomTokenAction ?: return null
|
||||
|
||||
val state = stateHolder.addCustomTokensState
|
||||
val fieldConverter =
|
||||
|
|
|
|||
|
|
@ -9,8 +9,6 @@ import org.rekotlin.Store
|
|||
/**
|
||||
[REDACTED_AUTHOR]
|
||||
*/
|
||||
private class DomainStore // for simple search
|
||||
|
||||
private val RE_STORE_HUBS: List<ReStoreHub<DomainState, *>> = listOf(
|
||||
DomainGlobalHub(),
|
||||
AddCustomTokenHub(),
|
||||
|
|
@ -19,7 +17,7 @@ private val RE_STORE_HUBS: List<ReStoreHub<DomainState, *>> = listOf(
|
|||
val domainStore = Store(
|
||||
state = DomainState(),
|
||||
middleware = RE_STORE_HUBS.map { it.getMiddleware() },
|
||||
reducer = { action, state -> reduce(action, state) }
|
||||
reducer = { action, state -> reduce(action, state) },
|
||||
)
|
||||
|
||||
private fun reduce(action: Action, domainState: DomainState?): DomainState {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue