From b352bb62354457e6cf17d3e6aa68530342078877 Mon Sep 17 00:00:00 2001 From: Tangem Date: Mon, 9 Jun 2025 12:42:30 +0300 Subject: [PATCH] Updated on 2026-08-14 --- app/build.gradle.kts | 3 + .../com/tangem/tap/routing/ProxyAppRouter.kt | 2 +- .../tangem/tap/routing/utils/ChildFactory.kt | 9 ++ common/routing/build.gradle.kts | 1 + .../com/tangem/common/routing/AppRoute.kt | 6 ++ .../configs/feature_toggles_config.json | 2 +- data/feedback/build.gradle.kts | 1 + .../feedback/DefaultFeedbackFeatureToggles.kt | 2 +- domain/feedback/build.gradle.kts | 1 + domain/feedback/models/.gitignore | 1 + domain/feedback/models/build.gradle.kts | 14 +++ .../domain/feedback/models/AppLogModel.kt | 0 .../feedback/models/BlockchainErrorInfo.kt | 0 .../domain/feedback/models/BlockchainInfo.kt | 0 .../tangem/domain/feedback/models/CardInfo.kt | 3 + .../domain/feedback/models/FeedbackEmail.kt | 0 .../feedback/models/FeedbackEmailType.kt | 0 .../domain/feedback/models/PhoneInfo.kt | 0 .../domain/feedback/models/UserWalletsInfo.kt | 0 .../utils/EmailMessageBodyResolver.kt | 6 +- features/details/impl/build.gradle.kts | 2 + features/markets/impl/build.gradle.kts | 1 + features/onboarding-v2/impl/build.gradle.kts | 1 + features/send-v2/impl/build.gradle.kts | 1 + features/send/impl/build.gradle.kts | 95 +++++++++++++++++++ features/staking/impl/build.gradle.kts | 1 + features/swap/impl/build.gradle.kts | 1 + features/usedesk/api/.gitignore | 1 + features/usedesk/api/build.gradle.kts | 17 ++++ .../feature/usedesk/api/UsedeskComponent.kt | 13 +++ features/usedesk/impl/.gitignore | 1 + features/usedesk/impl/build.gradle.kts | 36 +++++++ .../usedesk/DefaultUsedeskComponent.kt | 60 ++++++++++++ .../usedesk/di/UsedeskFeatureModule.kt | 25 +++++ .../feature/usedesk/model/UsedeskModel.kt | 35 +++++++ .../feature/usedesk/model/UsedeskState.kt | 9 ++ features/wallet/impl/build.gradle.kts | 1 + gradle/dependencies.toml | 3 + settings.gradle.kts | 4 + 39 files changed, 353 insertions(+), 5 deletions(-) create mode 100644 domain/feedback/models/.gitignore create mode 100644 domain/feedback/models/build.gradle.kts rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/AppLogModel.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/BlockchainErrorInfo.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/BlockchainInfo.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/CardInfo.kt (86%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/FeedbackEmail.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/FeedbackEmailType.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/PhoneInfo.kt (100%) rename domain/feedback/{src/main/java => models/src/main/kotlin}/com/tangem/domain/feedback/models/UserWalletsInfo.kt (100%) create mode 100644 features/send/impl/build.gradle.kts create mode 100644 features/usedesk/api/.gitignore create mode 100644 features/usedesk/api/build.gradle.kts create mode 100644 features/usedesk/api/src/main/java/com/tangem/feature/usedesk/api/UsedeskComponent.kt create mode 100644 features/usedesk/impl/.gitignore create mode 100644 features/usedesk/impl/build.gradle.kts create mode 100644 features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/DefaultUsedeskComponent.kt create mode 100644 features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/di/UsedeskFeatureModule.kt create mode 100644 features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskModel.kt create mode 100644 features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskState.kt diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 383bdf1b24..d8d88a7037 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -96,6 +96,7 @@ dependencies { implementation(projects.domain.visa) implementation(projects.domain.onboarding) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.qrScanning) implementation(projects.domain.qrScanning.models) implementation(projects.domain.staking) @@ -207,6 +208,8 @@ dependencies { implementation(projects.features.nft.impl) implementation(projects.features.walletconnect.api) implementation(projects.features.walletconnect.impl) + implementation(projects.features.usedesk.api) + implementation(projects.features.usedesk.impl) implementation(projects.features.feeSelector.api) implementation(projects.features.feeSelector.impl) diff --git a/app/src/main/java/com/tangem/tap/routing/ProxyAppRouter.kt b/app/src/main/java/com/tangem/tap/routing/ProxyAppRouter.kt index 19f2b9b8a7..5007213b9b 100644 --- a/app/src/main/java/com/tangem/tap/routing/ProxyAppRouter.kt +++ b/app/src/main/java/com/tangem/tap/routing/ProxyAppRouter.kt @@ -45,7 +45,7 @@ internal class ProxyAppRouter( runCatching { innerRouter.replaceAll(*routes, onComplete = onComplete) }.getOrElse { - Timber.tag("ASDASD").e(it) + Timber.e(it) } } } diff --git a/app/src/main/java/com/tangem/tap/routing/utils/ChildFactory.kt b/app/src/main/java/com/tangem/tap/routing/utils/ChildFactory.kt index 1c3e20f554..0657cb5dab 100644 --- a/app/src/main/java/com/tangem/tap/routing/utils/ChildFactory.kt +++ b/app/src/main/java/com/tangem/tap/routing/utils/ChildFactory.kt @@ -3,6 +3,7 @@ package com.tangem.tap.routing.utils import com.tangem.common.routing.AppRoute import com.tangem.core.decompose.context.AppComponentContext import com.tangem.domain.qrscanning.models.SourceType +import com.tangem.feature.usedesk.api.UsedeskComponent import com.tangem.feature.qrscanning.QrScanningComponent import com.tangem.feature.referral.api.ReferralComponent import com.tangem.feature.stories.api.StoriesComponent @@ -76,6 +77,7 @@ internal class ChildFactory @Inject constructor( private val redesignedWalletConnectComponentFactory: WalletConnectEntryComponent.Factory, private val nftComponentFactory: NFTComponent.Factory, private val nftSendComponentFactory: NFTSendComponent.Factory, + private val usedeskComponentFactory: UsedeskComponent.Factory, private val testerRouter: TesterRouter, private val walletConnectFeatureToggles: WalletConnectFeatureToggles, ) { @@ -398,6 +400,13 @@ internal class ChildFactory @Inject constructor( componentFactory = marketsTokenListComponentFactory, ) } + is AppRoute.Usedesk -> { // TODO [REDACTED_TASK_KEY] pass params + createComponentChild( + context = context, + params = UsedeskComponent.Params(), + componentFactory = usedeskComponentFactory, + ) + } } } } \ No newline at end of file diff --git a/common/routing/build.gradle.kts b/common/routing/build.gradle.kts index 75ff433c7e..7a2f8e3e73 100644 --- a/common/routing/build.gradle.kts +++ b/common/routing/build.gradle.kts @@ -24,6 +24,7 @@ dependencies { implementation(projects.domain.onramp.models) implementation(projects.domain.appCurrency.models) implementation(projects.domain.nft.models) + implementation(projects.domain.feedback.models) /* Libs - Other */ api(deps.kotlin.serialization) diff --git a/common/routing/src/main/kotlin/com/tangem/common/routing/AppRoute.kt b/common/routing/src/main/kotlin/com/tangem/common/routing/AppRoute.kt index b9629af57a..4b7523311c 100644 --- a/common/routing/src/main/kotlin/com/tangem/common/routing/AppRoute.kt +++ b/common/routing/src/main/kotlin/com/tangem/common/routing/AppRoute.kt @@ -6,6 +6,7 @@ import com.tangem.common.routing.bundle.bundle import com.tangem.common.routing.entity.SerializableIntent import com.tangem.core.decompose.navigation.Route import com.tangem.domain.appcurrency.model.AppCurrency +import com.tangem.domain.feedback.models.CardInfo import com.tangem.domain.markets.TokenMarketParams import com.tangem.domain.models.currency.CryptoCurrency import com.tangem.domain.models.scan.ScanResponse @@ -75,6 +76,11 @@ sealed class AppRoute(val path: String) : Route { val userWalletId: UserWalletId, ) : AppRoute(path = "/details/security") + @Serializable + data class Usedesk( + val cardInfo: CardInfo, + ) : AppRoute(path = "/usedesk/${cardInfo.cardId}") + @Serializable data class CardSettings( val userWalletId: UserWalletId, diff --git a/core/config-toggles/src/main/assets/configs/feature_toggles_config.json b/core/config-toggles/src/main/assets/configs/feature_toggles_config.json index 931748ec09..c952e46d1d 100644 --- a/core/config-toggles/src/main/assets/configs/feature_toggles_config.json +++ b/core/config-toggles/src/main/assets/configs/feature_toggles_config.json @@ -60,7 +60,7 @@ "version": "undefined" }, { - "name": "USEDESK_FEEDBACK_ENABLED", + "name": "USEDESK_ENABLED", "version": "undefined" } ] diff --git a/data/feedback/build.gradle.kts b/data/feedback/build.gradle.kts index 98e7e62d4a..96623a4d50 100644 --- a/data/feedback/build.gradle.kts +++ b/data/feedback/build.gradle.kts @@ -39,6 +39,7 @@ dependencies { implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.legacy) implementation(projects.domain.models) implementation(projects.domain.wallets) diff --git a/data/feedback/src/main/java/com/tangem/data/feedback/DefaultFeedbackFeatureToggles.kt b/data/feedback/src/main/java/com/tangem/data/feedback/DefaultFeedbackFeatureToggles.kt index 00c72a285f..77af42d09c 100644 --- a/data/feedback/src/main/java/com/tangem/data/feedback/DefaultFeedbackFeatureToggles.kt +++ b/data/feedback/src/main/java/com/tangem/data/feedback/DefaultFeedbackFeatureToggles.kt @@ -8,5 +8,5 @@ internal class DefaultFeedbackFeatureToggles( ) : FeedbackFeatureToggles { override val isUsedeskEnabled: Boolean - get() = featureTogglesManager.isFeatureEnabled(name = "USEDESK_FEEDBACK_ENABLED") + get() = featureTogglesManager.isFeatureEnabled(name = "USEDESK_ENABLED") } \ No newline at end of file diff --git a/domain/feedback/build.gradle.kts b/domain/feedback/build.gradle.kts index 213c40c655..3f4978f5a9 100644 --- a/domain/feedback/build.gradle.kts +++ b/domain/feedback/build.gradle.kts @@ -16,4 +16,5 @@ dependencies { implementation(projects.domain.models) implementation(projects.domain.wallets.models) implementation(projects.domain.visa.models) + implementation(projects.domain.feedback.models) } \ No newline at end of file diff --git a/domain/feedback/models/.gitignore b/domain/feedback/models/.gitignore new file mode 100644 index 0000000000..42afabfd2a --- /dev/null +++ b/domain/feedback/models/.gitignore @@ -0,0 +1 @@ +/build \ No newline at end of file diff --git a/domain/feedback/models/build.gradle.kts b/domain/feedback/models/build.gradle.kts new file mode 100644 index 0000000000..09652f0b44 --- /dev/null +++ b/domain/feedback/models/build.gradle.kts @@ -0,0 +1,14 @@ +plugins { + alias(deps.plugins.kotlin.jvm) + alias(deps.plugins.ksp) + alias(deps.plugins.kotlin.serialization) + id("configuration") +} +dependencies { + /* Other */ + implementation(deps.moshi) + ksp(deps.moshi.kotlin.codegen) + implementation(deps.kotlin.serialization) + implementation(projects.domain.wallets.models) + implementation(projects.domain.visa.models) +} \ No newline at end of file diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/AppLogModel.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/AppLogModel.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/AppLogModel.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/AppLogModel.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/BlockchainErrorInfo.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/BlockchainErrorInfo.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/BlockchainErrorInfo.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/BlockchainErrorInfo.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/BlockchainInfo.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/BlockchainInfo.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/BlockchainInfo.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/BlockchainInfo.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/CardInfo.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/CardInfo.kt similarity index 86% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/CardInfo.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/CardInfo.kt index d6d83ea329..7893d3a685 100644 --- a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/CardInfo.kt +++ b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/CardInfo.kt @@ -1,7 +1,9 @@ package com.tangem.domain.feedback.models import com.tangem.domain.wallets.models.UserWalletId +import kotlinx.serialization.Serializable +@Serializable data class CardInfo( val userWalletId: UserWalletId?, val cardId: String, @@ -14,5 +16,6 @@ data class CardInfo( val isVisa: Boolean, ) { + @Serializable data class SignedHashes(val curve: String, val total: String?) } \ No newline at end of file diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/FeedbackEmail.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/FeedbackEmail.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/FeedbackEmail.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/FeedbackEmail.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/FeedbackEmailType.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/FeedbackEmailType.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/FeedbackEmailType.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/FeedbackEmailType.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/PhoneInfo.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/PhoneInfo.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/PhoneInfo.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/PhoneInfo.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/models/UserWalletsInfo.kt b/domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/UserWalletsInfo.kt similarity index 100% rename from domain/feedback/src/main/java/com/tangem/domain/feedback/models/UserWalletsInfo.kt rename to domain/feedback/models/src/main/kotlin/com/tangem/domain/feedback/models/UserWalletsInfo.kt diff --git a/domain/feedback/src/main/java/com/tangem/domain/feedback/utils/EmailMessageBodyResolver.kt b/domain/feedback/src/main/java/com/tangem/domain/feedback/utils/EmailMessageBodyResolver.kt index 7711abe1d1..b976293f59 100644 --- a/domain/feedback/src/main/java/com/tangem/domain/feedback/utils/EmailMessageBodyResolver.kt +++ b/domain/feedback/src/main/java/com/tangem/domain/feedback/utils/EmailMessageBodyResolver.kt @@ -50,8 +50,10 @@ internal class EmailMessageBodyResolver( addCardInfo(cardInfo) addDelimiter() - if (cardInfo.userWalletId != null) { - val blockchainInfoList = feedbackRepository.getBlockchainInfoList(cardInfo.userWalletId) + val userWalletId = cardInfo.userWalletId + + if (userWalletId != null) { + val blockchainInfoList = feedbackRepository.getBlockchainInfoList(userWalletId) if (blockchainInfoList.isNotEmpty()) { addBlockchainInfoList(blockchainInfoList = blockchainInfoList) diff --git a/features/details/impl/build.gradle.kts b/features/details/impl/build.gradle.kts index 6522c52450..e44ec003ea 100644 --- a/features/details/impl/build.gradle.kts +++ b/features/details/impl/build.gradle.kts @@ -32,6 +32,7 @@ dependencies { /* Project - Domain */ implementation(projects.domain.models) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.wallets) implementation(projects.domain.wallets.models) implementation(projects.domain.card) @@ -52,6 +53,7 @@ dependencies { /* AndroidX */ implementation(deps.androidx.activity.compose) + implementation(deps.androidx.appCompat) implementation(deps.lifecycle.compose) /* Compose */ diff --git a/features/markets/impl/build.gradle.kts b/features/markets/impl/build.gradle.kts index b614e87a77..499ba281a4 100644 --- a/features/markets/impl/build.gradle.kts +++ b/features/markets/impl/build.gradle.kts @@ -28,6 +28,7 @@ dependencies { implementation(projects.domain.card) implementation(projects.domain.demo) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.manageTokens) implementation(projects.domain.markets) implementation(projects.domain.onramp.models) diff --git a/features/onboarding-v2/impl/build.gradle.kts b/features/onboarding-v2/impl/build.gradle.kts index c557f4a7a8..bc3dc77d8d 100644 --- a/features/onboarding-v2/impl/build.gradle.kts +++ b/features/onboarding-v2/impl/build.gradle.kts @@ -36,6 +36,7 @@ dependencies { /** Domain */ implementation(projects.domain.models) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.core) implementation(projects.domain.card) implementation(projects.domain.wallets) diff --git a/features/send-v2/impl/build.gradle.kts b/features/send-v2/impl/build.gradle.kts index 15d1d01b0b..f3961499eb 100644 --- a/features/send-v2/impl/build.gradle.kts +++ b/features/send-v2/impl/build.gradle.kts @@ -54,6 +54,7 @@ dependencies { implementation(projects.domain.qrScanning) implementation(projects.domain.settings) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.txhistory) implementation(projects.domain.balanceHiding.models) implementation(projects.domain.balanceHiding) diff --git a/features/send/impl/build.gradle.kts b/features/send/impl/build.gradle.kts new file mode 100644 index 0000000000..f104eedf8b --- /dev/null +++ b/features/send/impl/build.gradle.kts @@ -0,0 +1,95 @@ +plugins { + alias(deps.plugins.android.library) + alias(deps.plugins.kotlin.android) + alias(deps.plugins.kotlin.kapt) + alias(deps.plugins.hilt.android) + id("configuration") +} + +android { + namespace = "com.tangem.features.send.impl" +} + +dependencies { + /** AndroidX */ + implementation(deps.androidx.fragment.ktx) + implementation(deps.androidx.appCompat) + implementation(deps.androidx.paging.runtime) + + /** Other dependencies */ + implementation(deps.kotlin.immutable.collections) + implementation(deps.material) + implementation(deps.arrow.core) + implementation(deps.lifecycle.compose) + implementation(deps.jodatime) + implementation(deps.timber) + implementation(deps.reKotlin) + implementation(deps.kotlin.serialization) + + /** Compose */ + implementation(deps.compose.accompanist.systemUiController) + implementation(deps.compose.material3) + implementation(deps.compose.material) + implementation(deps.compose.foundation) + implementation(deps.compose.ui) + implementation(deps.compose.ui.tooling) + implementation(deps.compose.navigation) + implementation(deps.compose.navigation.hilt) + implementation(deps.compose.paging) + implementation(deps.compose.constraintLayout) + + /** Tangem SDKs */ + implementation(tangemDeps.card.core) + implementation(tangemDeps.blockchain) + + /** Core modules */ + implementation(projects.core.configToggles) + implementation(projects.core.ui) + implementation(projects.core.utils) + implementation(projects.core.navigation) + implementation(projects.core.analytics) + implementation(projects.core.analytics.models) + implementation(projects.core.datasource) + implementation(projects.core.decompose) + + /** Common */ + implementation(projects.common.ui) + implementation(projects.common.routing) + + /** Libs */ + implementation(projects.libs.crypto) + + /** Domain modules */ + implementation(projects.domain.models) + implementation(projects.domain.legacy) + implementation(projects.libs.blockchainSdk) + implementation(projects.domain.tokens) + implementation(projects.domain.tokens.models) + implementation(projects.domain.wallets) + implementation(projects.domain.wallets.models) + implementation(projects.domain.appCurrency) + implementation(projects.domain.appCurrency.models) + implementation(projects.domain.txhistory) + implementation(projects.domain.txhistory.models) + implementation(projects.domain.transaction) + implementation(projects.domain.transaction.models) + implementation(projects.domain.card) + implementation(projects.domain.balanceHiding) + implementation(projects.domain.balanceHiding.models) + implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) + implementation(projects.domain.qrScanning) + implementation(projects.domain.qrScanning.models) + implementation(projects.domain.settings) + implementation(projects.domain.notifications) + + /** Feature modules */ + implementation(projects.features.send.api) + implementation(projects.features.tokendetails.api) + implementation(projects.features.txhistory.api) + implementation(projects.features.qrScanning.api) + + /** DI */ + implementation(deps.hilt.android) + kapt(deps.hilt.kapt) +} \ No newline at end of file diff --git a/features/staking/impl/build.gradle.kts b/features/staking/impl/build.gradle.kts index 6ffb00cc29..05decae6d5 100644 --- a/features/staking/impl/build.gradle.kts +++ b/features/staking/impl/build.gradle.kts @@ -65,6 +65,7 @@ dependencies { implementation(projects.domain.transaction.models) implementation(projects.domain.txhistory) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) /** Common */ implementation(projects.common.ui) diff --git a/features/swap/impl/build.gradle.kts b/features/swap/impl/build.gradle.kts index 74a34ecd45..5d0745ca74 100644 --- a/features/swap/impl/build.gradle.kts +++ b/features/swap/impl/build.gradle.kts @@ -38,6 +38,7 @@ dependencies { implementation(projects.domain.settings) implementation(projects.domain.staking) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.promo) implementation(projects.domain.promo.models) implementation(projects.domain.txhistory) diff --git a/features/usedesk/api/.gitignore b/features/usedesk/api/.gitignore new file mode 100644 index 0000000000..796b96d1c4 --- /dev/null +++ b/features/usedesk/api/.gitignore @@ -0,0 +1 @@ +/build diff --git a/features/usedesk/api/build.gradle.kts b/features/usedesk/api/build.gradle.kts new file mode 100644 index 0000000000..b7114cd803 --- /dev/null +++ b/features/usedesk/api/build.gradle.kts @@ -0,0 +1,17 @@ +plugins { + alias(deps.plugins.android.library) + alias(deps.plugins.kotlin.android) + id("configuration") +} + +android { + namespace = "com.tangem.feature.usedesk.api" +} + +dependencies { + + /** Core */ + implementation(projects.core.decompose) + implementation(projects.core.ui) + +} \ No newline at end of file diff --git a/features/usedesk/api/src/main/java/com/tangem/feature/usedesk/api/UsedeskComponent.kt b/features/usedesk/api/src/main/java/com/tangem/feature/usedesk/api/UsedeskComponent.kt new file mode 100644 index 0000000000..7542b8adcd --- /dev/null +++ b/features/usedesk/api/src/main/java/com/tangem/feature/usedesk/api/UsedeskComponent.kt @@ -0,0 +1,13 @@ +package com.tangem.feature.usedesk.api + +import com.tangem.core.decompose.factory.ComponentFactory +import com.tangem.core.ui.decompose.ComposableContentComponent + +interface UsedeskComponent : ComposableContentComponent { + + data class Params( + val feedback: String? = null, // TODO [REDACTED_TASK_KEY] + ) + + interface Factory : ComponentFactory +} \ No newline at end of file diff --git a/features/usedesk/impl/.gitignore b/features/usedesk/impl/.gitignore new file mode 100644 index 0000000000..796b96d1c4 --- /dev/null +++ b/features/usedesk/impl/.gitignore @@ -0,0 +1 @@ +/build diff --git a/features/usedesk/impl/build.gradle.kts b/features/usedesk/impl/build.gradle.kts new file mode 100644 index 0000000000..8bba93f420 --- /dev/null +++ b/features/usedesk/impl/build.gradle.kts @@ -0,0 +1,36 @@ +plugins { + alias(deps.plugins.android.library) + alias(deps.plugins.kotlin.android) + alias(deps.plugins.kotlin.kapt) + alias(deps.plugins.hilt.android) + id("configuration") +} + +android { + namespace = "com.tangem.feature.usedesk.impl" +} + +dependencies { + + /** Core */ + implementation(projects.core.ui) + implementation(projects.core.decompose) + implementation(projects.core.utils) + implementation(projects.core.navigation) + implementation(projects.common.routing) + implementation(projects.features.usedesk.api) + + /** DI */ + implementation(deps.hilt.android) + kapt(deps.hilt.kapt) + + /** Compose */ + implementation(deps.compose.foundation) + implementation(deps.compose.ui) + + /** Usedesk */ + implementation(deps.usedesk.chat.sdk) + implementation(deps.usedesk.chat.gui) + + +} \ No newline at end of file diff --git a/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/DefaultUsedeskComponent.kt b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/DefaultUsedeskComponent.kt new file mode 100644 index 0000000000..114b564964 --- /dev/null +++ b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/DefaultUsedeskComponent.kt @@ -0,0 +1,60 @@ +package com.tangem.feature.usedesk + +import android.view.View +import androidx.compose.foundation.layout.* +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.ui.Modifier +import androidx.compose.ui.viewinterop.AndroidView +import androidx.fragment.app.FragmentActivity +import androidx.fragment.app.FragmentContainerView +import androidx.lifecycle.compose.collectAsStateWithLifecycle +import com.tangem.core.decompose.context.AppComponentContext +import com.tangem.core.decompose.model.getOrCreateModel +import com.tangem.feature.usedesk.api.UsedeskComponent +import com.tangem.feature.usedesk.model.UsedeskModel +import dagger.assisted.Assisted +import dagger.assisted.AssistedFactory +import dagger.assisted.AssistedInject +import ru.usedesk.chat_gui.chat.UsedeskChatScreen + +internal class DefaultUsedeskComponent @AssistedInject constructor( + @Assisted appComponentContext: AppComponentContext, + @Assisted params: UsedeskComponent.Params, +) : UsedeskComponent, AppComponentContext by appComponentContext { + + private val model: UsedeskModel = getOrCreateModel(params) + + @Composable + override fun Content(modifier: Modifier) { + val state by model.state.collectAsStateWithLifecycle() + + Box( + modifier = Modifier + .fillMaxSize() + .systemBarsPadding() + .imePadding(), + ) { + AndroidView( + factory = { context -> + FragmentContainerView(context).apply { + id = View.generateViewId() + + val fragment = UsedeskChatScreen.newInstance( + state.usedeskChatConfiguration, + ) + (context as FragmentActivity).supportFragmentManager.beginTransaction() + .replace(id, fragment) + .commit() + } + }, + modifier = Modifier.fillMaxSize(), + ) + } + } + + @AssistedFactory + interface Factory : UsedeskComponent.Factory { + override fun create(context: AppComponentContext, params: UsedeskComponent.Params): DefaultUsedeskComponent + } +} \ No newline at end of file diff --git a/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/di/UsedeskFeatureModule.kt b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/di/UsedeskFeatureModule.kt new file mode 100644 index 0000000000..e08428b6bb --- /dev/null +++ b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/di/UsedeskFeatureModule.kt @@ -0,0 +1,25 @@ +package com.tangem.feature.usedesk.di + +import com.tangem.core.decompose.model.Model +import com.tangem.feature.usedesk.DefaultUsedeskComponent +import com.tangem.feature.usedesk.api.UsedeskComponent +import com.tangem.feature.usedesk.model.UsedeskModel +import dagger.Binds +import dagger.Module +import dagger.hilt.InstallIn +import dagger.hilt.components.SingletonComponent +import dagger.multibindings.ClassKey +import dagger.multibindings.IntoMap + +@Module +@InstallIn(SingletonComponent::class) +internal interface UsedeskFeatureModule { + + @Binds + fun bindComponentFactory(impl: DefaultUsedeskComponent.Factory): UsedeskComponent.Factory + + @Binds + @IntoMap + @ClassKey(UsedeskModel::class) + fun bindModel(model: UsedeskModel): Model +} \ No newline at end of file diff --git a/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskModel.kt b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskModel.kt new file mode 100644 index 0000000000..47139c815e --- /dev/null +++ b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskModel.kt @@ -0,0 +1,35 @@ +package com.tangem.feature.usedesk.model + +import androidx.compose.runtime.Stable +import com.tangem.core.decompose.di.ModelScoped +import com.tangem.core.decompose.model.Model +import com.tangem.utils.coroutines.CoroutineDispatcherProvider +import kotlinx.coroutines.flow.MutableStateFlow +import kotlinx.coroutines.flow.StateFlow +import ru.usedesk.chat_sdk.entity.UsedeskChatConfiguration +import javax.inject.Inject + +@Stable +@ModelScoped +internal class UsedeskModel @Inject constructor( + override val dispatchers: CoroutineDispatcherProvider, +) : Model() { + + private val _state = MutableStateFlow(getInitialState()) + + val state: StateFlow = _state + + private fun getInitialState(): UsedeskState { + return UsedeskState( + UsedeskChatConfiguration( + companyId = COMPANY_ID, + channelId = CHANNEL_ID, + ), + ) + } + + private companion object { + const val COMPANY_ID = "170509" + const val CHANNEL_ID = "65637" + } +} \ No newline at end of file diff --git a/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskState.kt b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskState.kt new file mode 100644 index 0000000000..26098b62e5 --- /dev/null +++ b/features/usedesk/impl/src/main/java/com/tangem/feature/usedesk/model/UsedeskState.kt @@ -0,0 +1,9 @@ +package com.tangem.feature.usedesk.model + +import androidx.compose.runtime.Stable +import ru.usedesk.chat_sdk.entity.UsedeskChatConfiguration + +@Stable +internal data class UsedeskState( + val usedeskChatConfiguration: UsedeskChatConfiguration, +) \ No newline at end of file diff --git a/features/wallet/impl/build.gradle.kts b/features/wallet/impl/build.gradle.kts index 03c5af01a5..a81c3a07e1 100644 --- a/features/wallet/impl/build.gradle.kts +++ b/features/wallet/impl/build.gradle.kts @@ -74,6 +74,7 @@ dependencies { implementation(projects.domain.card) implementation(projects.domain.demo) implementation(projects.domain.feedback) + implementation(projects.domain.feedback.models) implementation(projects.domain.legacy) implementation(projects.domain.markets.models) implementation(projects.domain.models) diff --git a/gradle/dependencies.toml b/gradle/dependencies.toml index dfa579810a..34c29de01a 100644 --- a/gradle/dependencies.toml +++ b/gradle/dependencies.toml @@ -89,6 +89,7 @@ decompose = "3.3.0" room = "2.6.1" markdown = "0.7.2" markdownComposeView = "0.5.4" +usedesk = "4.4.0" # endregion Other libraries # region Tools @@ -274,4 +275,6 @@ room-compiler = { module = "androidx.room:room-compiler", version.ref = "room" } room-ktx = { module = "androidx.room:room-ktx", version.ref = "room" } markdown = { module = "org.jetbrains:markdown", version.ref = "markdown" } markdown-composeview = { module = "com.github.jeziellago:compose-markdown", version.ref = "markdownComposeView" } +usedesk-chat-sdk = { module = "com.github.Usedesk.Android_SDK:chat-sdk", version.ref = "usedesk" } +usedesk-chat-gui = { module = "com.github.Usedesk.Android_SDK:chat-gui", version.ref = "usedesk" } # endregion Other diff --git a/settings.gradle.kts b/settings.gradle.kts index f34d536ed8..c46c443982 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -213,6 +213,9 @@ include(":features:details:impl") include(":features:disclaimer:api") include(":features:disclaimer:impl") +include(":features:usedesk:api") +include(":features:usedesk:impl") + include(":features:push-notifications:api") include(":features:push-notifications:impl") @@ -272,6 +275,7 @@ include(":domain:visa") include(":domain:visa:models") include(":domain:onboarding") include(":domain:feedback") +include(":domain:feedback:models") include(":domain:qr-scanning") include(":domain:qr-scanning:models") include(":domain:staking")