diff --git a/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreen.kt b/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreen.kt index cc030a99e1..f5918ea0ad 100644 --- a/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreen.kt +++ b/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreen.kt @@ -41,6 +41,7 @@ import com.navi.base.utils.orTrue import com.navi.common.checkmate.core.CheckMateManager import com.navi.common.checkmate.model.MetricInfo import com.navi.common.commoncomposables.utils.ScrollToTopListener +import com.navi.common.commoncomposables.utils.resetScrollToTop import com.navi.common.network.models.RepoResult import com.navi.common.ui.compose.DrawerState import com.navi.uitron.model.UiTronResponse @@ -125,6 +126,7 @@ fun ProfileScreen( drawerState = drawerState, appUpdateState = appUpdateState, inAppUpdateBridge = activity, + scrollToTop = { profileVM.resetScrollToTop(true, PROFILE) }, ) } } diff --git a/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreenWidgetRenderer.kt b/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreenWidgetRenderer.kt index c06e15f27b..c2561f1077 100644 --- a/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreenWidgetRenderer.kt +++ b/android/app/src/main/java/com/naviapp/home/compose/profile/ProfileScreenWidgetRenderer.kt @@ -30,6 +30,7 @@ fun ProfileScreenWidgetRenderer( drawerState: () -> DrawerState, appUpdateState: AppUpdateState, inAppUpdateBridge: InAppUpdateBridge, + scrollToTop: () -> Unit = {}, ) { if (widget == null) return return when (widget.widgetType) { @@ -46,7 +47,8 @@ fun ProfileScreenWidgetRenderer( when (widget.widgetName) { HomeCustomWidgetType.ProfileHeaderWidget.value -> AnimatedProfileContent(widget, viewModel, drawerState) - HomeCustomWidgetType.UpiSettingsWidget.value -> UPISettingSDK(drawerState) + HomeCustomWidgetType.UpiSettingsWidget.value -> + UPISettingSDK(drawerState = drawerState, scrollToTop = scrollToTop) else -> Unit } } diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayRequest.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayRequest.kt new file mode 100644 index 0000000000..c310ac1890 --- /dev/null +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayRequest.kt @@ -0,0 +1,17 @@ +/* + * + * * Copyright © 2025 by Navi Technologies Limited + * * All rights reserved. Strictly confidential + * + */ + +package com.navi.pay.common.settingscreen.model + +import com.google.gson.annotations.SerializedName +import com.navi.pay.common.model.view.PspType + +data class DeregisterNaviPayRequest( + @SerializedName("deviceFingerPrint") val deviceFingerPrint: String, + @SerializedName("merchantCustomerId") val merchantCustomerId: String, + @SerializedName("provider") val pspType: PspType, +) diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayResponse.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayResponse.kt new file mode 100644 index 0000000000..3b18ea2559 --- /dev/null +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/model/DeregisterNaviPayResponse.kt @@ -0,0 +1,15 @@ +/* + * + * * Copyright © 2025 by Navi Technologies Limited + * * All rights reserved. Strictly confidential + * + */ + +package com.navi.pay.common.settingscreen.model + +import com.google.gson.annotations.SerializedName + +data class DeregisterNaviPayResponse( + @SerializedName("merchantCustomerId") val merchantCustomerId: String, + @SerializedName("status") val status: String, +) diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/repository/SettingSDKRepository.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/repository/SettingSDKRepository.kt new file mode 100644 index 0000000000..c32690a0ef --- /dev/null +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/repository/SettingSDKRepository.kt @@ -0,0 +1,30 @@ +/* + * + * * Copyright © 2025 by Navi Technologies Limited + * * All rights reserved. Strictly confidential + * + */ + +package com.navi.pay.common.settingscreen.repository + +import com.navi.common.checkmate.model.MetricInfo +import com.navi.common.network.models.RepoResult +import com.navi.common.network.retrofit.ResponseCallback +import com.navi.pay.common.settingscreen.model.DeregisterNaviPayRequest +import com.navi.pay.common.settingscreen.model.DeregisterNaviPayResponse +import com.navi.pay.network.retrofit.NaviPayRetrofitService +import javax.inject.Inject + +class SettingSDKRepository +@Inject +constructor(private val naviPayRetrofitService: NaviPayRetrofitService) : ResponseCallback() { + + suspend fun deregisterNaviPay( + deregisterNaviPayRequest: DeregisterNaviPayRequest, + metricInfo: MetricInfo>, + ) = + apiResponseCallback( + response = naviPayRetrofitService.deregisterNaviPay(deregisterNaviPayRequest), + metricInfo = metricInfo, + ) +} diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/ui/UPISettingSDK.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/ui/UPISettingSDK.kt index f5ca68fc4a..6658be5ed3 100644 --- a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/ui/UPISettingSDK.kt +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/ui/UPISettingSDK.kt @@ -26,6 +26,7 @@ import androidx.compose.material3.SnackbarDuration import androidx.compose.material3.SnackbarHost import androidx.compose.material3.SnackbarHostState import androidx.compose.material3.SnackbarResult +import androidx.compose.material3.rememberModalBottomSheetState import androidx.compose.runtime.Composable import androidx.compose.runtime.DisposableEffect import androidx.compose.runtime.LaunchedEffect @@ -62,8 +63,13 @@ import com.navi.pay.common.settingscreen.utils.downloadQR import com.navi.pay.common.settingscreen.utils.getQRBitmapForWallpaper import com.navi.pay.common.settingscreen.utils.saveQrInGallery import com.navi.pay.common.settingscreen.utils.shareQR +import com.navi.pay.common.settingscreen.view.UpiSettingBottomSheetUIState import com.navi.pay.common.settingscreen.viewmodel.SettingSDKViewmodel import com.navi.pay.common.theme.color.NaviPayColor +import com.navi.pay.common.ui.BottomSheetContentWithIconHeaderDescButton +import com.navi.pay.common.ui.BottomSheetContentWithIconHeaderPrimarySecondaryButtonCtaLoader +import com.navi.pay.common.ui.NaviPayModalBottomSheet +import com.navi.pay.common.ui.SuccessBottomSheetContent import com.navi.pay.common.utils.NaviPayCommonUtils import com.navi.pay.common.utils.launchOnboardingSDK import com.navi.pay.utils.ACCOUNT_ID @@ -76,6 +82,7 @@ import kotlinx.coroutines.launch @Composable fun UPISettingSDK( drawerState: () -> DrawerState, + scrollToTop: () -> Unit, settingSDKViewmodel: SettingSDKViewmodel = hiltViewModel(), ) { val activity = LocalActivity.current ?: return @@ -137,6 +144,10 @@ fun UPISettingSDK( settingSDKViewmodel.isRccRewardsExperimentEnabled.collectAsStateWithLifecycle() val rccRewardStripType by settingSDKViewmodel.rccRewardStripType.collectAsStateWithLifecycle() val isRccAccountPresent by settingSDKViewmodel.isRccAccountPresent.collectAsStateWithLifecycle() + val bottomSheetStateHolder by + settingSDKViewmodel.bottomsheetStateHolder.collectAsStateWithLifecycle() + val showLoader by settingSDKViewmodel.showLoader.collectAsStateWithLifecycle() + val scrollToTop by settingSDKViewmodel.scrollToTop.collectAsStateWithLifecycle() val galleryLauncher = rememberLauncherForActivityResult(ActivityResultContracts.StartActivityForResult()) { result @@ -149,6 +160,12 @@ fun UPISettingSDK( } val lifecycleOwner = LocalLifecycleOwner.current + LaunchedEffect(scrollToTop) { + if (scrollToTop) { + scrollToTop() + } + } + DisposableEffect(key1 = lifecycleOwner) { val observer = LifecycleEventObserver { _, event -> when (event) { @@ -251,6 +268,41 @@ fun UPISettingSDK( } } + val bottomSheetState = + rememberModalBottomSheetState( + skipPartiallyExpanded = true, + confirmValueChange = { bottomSheetStateHolder.bottomSheetStateChange }, + ) + + val scope = rememberCoroutineScope() + + val onDismissBottomSheet: () -> Unit = { + scope + .launch { bottomSheetState.hide() } + .invokeOnCompletion { + if (!bottomSheetState.isVisible || !bottomSheetStateHolder.bottomSheetStateChange) { + settingSDKViewmodel.updateBottomSheetUIState(showBottomSheet = false) + } + } + } + + if (bottomSheetStateHolder.showBottomSheet) { + NaviPayModalBottomSheet( + modifier = Modifier.fillMaxWidth(), + bottomSheetState = bottomSheetState, + onDismissRequest = onDismissBottomSheet, + shouldDismissOnBackPress = true, + bottomSheetContent = { + RenderSettingSdkBottomsheet( + bottomSheetUIState = bottomSheetStateHolder.bottomSheetUIState, + showLoader = showLoader, + onDismissBottomSheet = onDismissBottomSheet, + onDeregisterClicked = settingSDKViewmodel::deregisterNaviPay, + ) + }, + ) + } + Box { UPISettingContent( upiSettingDetails = upiSettingDetails, @@ -369,3 +421,62 @@ private fun SnackBarSection( } } } + +@Composable +fun RenderSettingSdkBottomsheet( + bottomSheetUIState: UpiSettingBottomSheetUIState, + showLoader: Boolean, + onDismissBottomSheet: () -> Unit, + onDeregisterClicked: () -> Unit, +) { + when (bottomSheetUIState) { + UpiSettingBottomSheetUIState.DeregisterNaviPayBottomSheet -> { + BottomSheetContentWithIconHeaderPrimarySecondaryButtonCtaLoader( + header = stringResource(id = R.string.np_deregister_navi_upi), + description = stringResource(id = R.string.np_deregister_navi_upi_description), + primaryButton = stringResource(id = R.string.continue_text), + secondaryButton = stringResource(id = R.string.cancel), + onPrimaryButtonClicked = onDeregisterClicked, + onSecondaryButtonClicked = onDismissBottomSheet, + showLoader = showLoader, + ) + } + + UpiSettingBottomSheetUIState.ActiveLiteAccountFoundBottomSheet -> { + BottomSheetContentWithIconHeaderDescButton( + headerTextId = R.string.np_active_upi_lite_deregister_failed, + descriptionTextId = R.string.np_active_upi_lite_deregister_failed_description, + buttonTextId = R.string.np_okay_got_it, + onButtonClicked = onDismissBottomSheet, + ) + } + + UpiSettingBottomSheetUIState.ActiveMandateFoundBottomSheet -> { + BottomSheetContentWithIconHeaderDescButton( + headerTextId = R.string.np_active_mandate_deregister_failed, + descriptionTextId = R.string.np_active_mandate_deregister_failed_description, + buttonTextId = R.string.np_okay_got_it, + onButtonClicked = onDismissBottomSheet, + ) + } + + UpiSettingBottomSheetUIState.ActiveMandateAndLiteFoundBottomSheet -> { + BottomSheetContentWithIconHeaderDescButton( + headerTextId = R.string.np_active_mandate_and_lite_deregister_failed, + descriptionTextId = + R.string.np_active_mandate_and_lite_deregister_failed_description, + buttonTextId = R.string.np_okay_got_it, + onButtonClicked = onDismissBottomSheet, + ) + } + + UpiSettingBottomSheetUIState.DeregisterSuccessBottomSheet -> { + SuccessBottomSheetContent( + title = stringResource(R.string.np_deregister_navi_upi_success), + isDescriptionClickable = false, + ) + } + + UpiSettingBottomSheetUIState.None -> {} + } +} diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetStateHolder.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetStateHolder.kt new file mode 100644 index 0000000000..0a67f7aae4 --- /dev/null +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetStateHolder.kt @@ -0,0 +1,14 @@ +/* + * + * * Copyright © 2025 by Navi Technologies Limited + * * All rights reserved. Strictly confidential + * + */ + +package com.navi.pay.common.settingscreen.view + +data class UpiSettingBottomSheetStateHolder( + val showBottomSheet: Boolean, + val bottomSheetStateChange: Boolean, + val bottomSheetUIState: UpiSettingBottomSheetUIState, +) diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetUIState.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetUIState.kt new file mode 100644 index 0000000000..378b55d948 --- /dev/null +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/view/UpiSettingBottomSheetUIState.kt @@ -0,0 +1,23 @@ +/* + * + * * Copyright © 2025 by Navi Technologies Limited + * * All rights reserved. Strictly confidential + * + */ + +package com.navi.pay.common.settingscreen.view + +sealed class UpiSettingBottomSheetUIState { + + data object DeregisterNaviPayBottomSheet : UpiSettingBottomSheetUIState() + + data object ActiveLiteAccountFoundBottomSheet : UpiSettingBottomSheetUIState() + + data object ActiveMandateFoundBottomSheet : UpiSettingBottomSheetUIState() + + data object ActiveMandateAndLiteFoundBottomSheet : UpiSettingBottomSheetUIState() + + data object DeregisterSuccessBottomSheet : UpiSettingBottomSheetUIState() + + data object None : UpiSettingBottomSheetUIState() +} diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/viewmodel/SettingSDKViewmodel.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/viewmodel/SettingSDKViewmodel.kt index 03b636fc79..164e28e912 100644 --- a/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/viewmodel/SettingSDKViewmodel.kt +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/common/settingscreen/viewmodel/SettingSDKViewmodel.kt @@ -15,22 +15,30 @@ import com.navi.base.cache.model.NaviCacheEntity import com.navi.base.cache.repository.NaviCacheRepository import com.navi.base.model.ActionData import com.navi.common.network.models.LitmusExperimentResponse +import com.navi.common.network.models.isSuccessWithData import com.navi.common.upi.AUTO_PAY_REQUEST import com.navi.common.upi.PENDING_REQUEST import com.navi.pay.analytics.NaviPayAnalytics import com.navi.pay.analytics.NaviPayAnalytics.Companion.NAVI_PAY_UPI_SETTINGS_SDK import com.navi.pay.common.model.view.NaviPayFlowType +import com.navi.pay.common.model.view.PspType import com.navi.pay.common.repository.SharedPreferenceRepository +import com.navi.pay.common.settingscreen.model.DeregisterNaviPayRequest import com.navi.pay.common.settingscreen.model.QrAsWallpaperStateHolder import com.navi.pay.common.settingscreen.model.QrDetails import com.navi.pay.common.settingscreen.model.UpiSettingDetails +import com.navi.pay.common.settingscreen.repository.SettingSDKRepository import com.navi.pay.common.settingscreen.utils.WallpaperManager import com.navi.pay.common.settingscreen.utils.isOnboardingRequired +import com.navi.pay.common.settingscreen.view.UpiSettingBottomSheetStateHolder +import com.navi.pay.common.settingscreen.view.UpiSettingBottomSheetUIState import com.navi.pay.common.settingscreen.viewmodel.RccRewardStripType.Companion.getRewardStripType +import com.navi.pay.common.setup.NaviPayCustomerStatusHandler import com.navi.pay.common.setup.NaviPayManager import com.navi.pay.common.usecase.LinkedAccountsUseCase import com.navi.pay.common.utils.NaviPayNotificationHandler import com.navi.pay.common.utils.NaviPayOnboardingNavigator +import com.navi.pay.common.utils.getMetricInfo import com.navi.pay.common.viewmodel.NaviPayBaseVM import com.navi.pay.management.common.sendmoney.util.NaviPayOffersHelper import com.navi.pay.management.common.settings.util.SettingsCountManager @@ -38,7 +46,11 @@ import com.navi.pay.management.common.utils.NaviPayPspManager import com.navi.pay.network.di.NaviPayGsonBuilder import com.navi.pay.onboarding.account.add.model.view.AccountType import com.navi.pay.onboarding.account.detail.model.view.LinkedAccountEntity +import com.navi.pay.utils.ERR_ACTIVE_LITE_ACCOUNT_FOUND +import com.navi.pay.utils.ERR_LITE_AND_MANDATE_ACTIVE +import com.navi.pay.utils.ERR_MANDATE_PRESENT import com.navi.pay.utils.LITMUS_EXPERIMENT_NAVIPAY_RCC_LANDING_EXP +import com.navi.pay.utils.NAVI_PAY_DEREGISTER import com.navi.pay.utils.NAVI_PAY_SETTING_QR_PAGER_ANIMATION_COUNTER import com.navi.pay.utils.PENDING_REQUEST_REFRESHED_REQUIRED import com.navi.pay.utils.RCC @@ -46,8 +58,10 @@ import com.navi.rr.common.models.OfferData import dagger.hilt.android.lifecycle.HiltViewModel import javax.inject.Inject import kotlin.collections.map +import kotlin.time.Duration.Companion.seconds import kotlinx.coroutines.Dispatchers import kotlinx.coroutines.async +import kotlinx.coroutines.delay import kotlinx.coroutines.flow.MutableSharedFlow import kotlinx.coroutines.flow.MutableStateFlow import kotlinx.coroutines.flow.SharingStarted @@ -77,6 +91,8 @@ constructor( private val wallpaperManager: WallpaperManager, private val naviPayOffersHelper: NaviPayOffersHelper, @NaviPayGsonBuilder private val gson: Gson, + private val settingSDKRepository: SettingSDKRepository, + private val naviPayCustomerStatusHandler: NaviPayCustomerStatusHandler, ) : NaviPayBaseVM() { private val _upiSettingDetails = MutableStateFlow(UpiSettingDetails()) @@ -120,6 +136,25 @@ constructor( private val _isRccAccountPresent = MutableStateFlow(false) val isRccAccountPresent = _isRccAccountPresent.asStateFlow() + private var pspType: PspType? = null + + private val _bottomsheetStateHolder = + MutableStateFlow( + UpiSettingBottomSheetStateHolder( + showBottomSheet = false, + bottomSheetStateChange = false, + bottomSheetUIState = UpiSettingBottomSheetUIState.None, + ) + ) + + val bottomsheetStateHolder = _bottomsheetStateHolder.asStateFlow() + + private val _showLoader = MutableStateFlow(false) + val showLoader = _showLoader.asStateFlow() + + private val _scrollToTop = MutableStateFlow(false) + val scrollToTop = _scrollToTop.asStateFlow() + init { viewModelScope.launch(Dispatchers.IO) { linkedAccountsUseCase.execute(screenName = screenName).collectLatest { linkedAccounts -> @@ -313,12 +348,29 @@ constructor( naviPayFlowType = NaviPayFlowType.DEVICE_BINDING, screenName = screenName, onPspEvaluated = { pspEvaluationResult -> - if (pspEvaluationResult.onboardingDataEntity != null) { - _navigateToCtaUrl.emit(actionData) + if (pspEvaluationResult.onboardingDataEntity == null) { + return@evaluateAndBindAnySupportedPspForFlow } + pspType = pspEvaluationResult.onboardingDataEntity.pspType + handleCtaActionBasedOnUrl(actionData) }, ) } else { + handleCtaActionBasedOnUrl(actionData) + } + } + } + + private suspend fun handleCtaActionBasedOnUrl(actionData: ActionData) { + when (actionData.url) { + NAVI_PAY_DEREGISTER -> { + updateBottomSheetUIState( + showBottomSheet = true, + bottomSheetUIState = UpiSettingBottomSheetUIState.DeregisterNaviPayBottomSheet, + allowStateChange = true, + ) + } + else -> { _navigateToCtaUrl.emit(actionData) } } @@ -346,6 +398,97 @@ constructor( } } + fun deregisterNaviPay() { + viewModelScope.launch(Dispatchers.IO) { + updateLoaderState(showLoader = true) + val customerOnboardingEntity = + naviPayCustomerStatusHandler.getCustomerOnboardingEntity( + pspType = pspType ?: PspType.JUSPAY_AXIS + ) + val deregisterUpiRequest = + DeregisterNaviPayRequest( + deviceFingerPrint = customerOnboardingEntity?.deviceFingerPrint.orEmpty(), + merchantCustomerId = customerOnboardingEntity?.merchantCustomerId.orEmpty(), + pspType = customerOnboardingEntity?.pspType ?: PspType.JUSPAY_AXIS, + ) + val response = + settingSDKRepository.deregisterNaviPay( + deregisterNaviPayRequest = deregisterUpiRequest, + metricInfo = getMetricInfo(screenName), + ) + if (response.isSuccessWithData()) { + naviPayManager.triggerNaviPayHardLogout() + updateBottomSheetUIState( + showBottomSheet = true, + bottomSheetUIState = UpiSettingBottomSheetUIState.DeregisterSuccessBottomSheet, + allowStateChange = true, + ) + updateScrollToTopState(true) + delay(2.seconds) // Delay to show de-registration success BS + updateBottomSheetUIState(showBottomSheet = false) + } else { + handleDeregistrationFailure(response.errors?.get(0)?.code.orEmpty()) + } + updateLoaderState(showLoader = false) + } + } + + private fun handleDeregistrationFailure(errorCode: String) { + when (errorCode) { + ERR_ACTIVE_LITE_ACCOUNT_FOUND -> { + updateBottomSheetUIState( + showBottomSheet = true, + bottomSheetUIState = + UpiSettingBottomSheetUIState.ActiveLiteAccountFoundBottomSheet, + allowStateChange = true, + ) + } + + ERR_MANDATE_PRESENT -> { + updateBottomSheetUIState( + showBottomSheet = true, + bottomSheetUIState = UpiSettingBottomSheetUIState.ActiveMandateFoundBottomSheet, + allowStateChange = true, + ) + } + + ERR_LITE_AND_MANDATE_ACTIVE -> { + updateBottomSheetUIState( + showBottomSheet = true, + bottomSheetUIState = + UpiSettingBottomSheetUIState.ActiveMandateAndLiteFoundBottomSheet, + allowStateChange = true, + ) + } + + else -> { + notifyError() + } + } + } + + fun updateBottomSheetUIState( + bottomSheetUIState: UpiSettingBottomSheetUIState? = null, + showBottomSheet: Boolean, + allowStateChange: Boolean? = null, + ) { + _bottomsheetStateHolder.update { + it.copy( + showBottomSheet = showBottomSheet, + bottomSheetStateChange = allowStateChange ?: it.bottomSheetStateChange, + bottomSheetUIState = bottomSheetUIState ?: it.bottomSheetUIState, + ) + } + } + + private fun updateScrollToTopState(scrollToTop: Boolean) { + _scrollToTop.update { scrollToTop } + } + + private fun updateLoaderState(showLoader: Boolean) { + _showLoader.update { showLoader } + } + override val screenName: String get() = NAVI_PAY_UPI_SETTINGS_SDK } diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/network/retrofit/NaviPayRetrofitService.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/network/retrofit/NaviPayRetrofitService.kt index 819475c312..e59c37690e 100644 --- a/android/navi-pay/src/main/kotlin/com/navi/pay/network/retrofit/NaviPayRetrofitService.kt +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/network/retrofit/NaviPayRetrofitService.kt @@ -16,6 +16,8 @@ import com.navi.pay.common.model.network.DeactivateVpaRequest import com.navi.pay.common.model.network.RequestIdResponse import com.navi.pay.common.model.network.ValidateVpaRequest import com.navi.pay.common.model.network.ValidateVpaResponse +import com.navi.pay.common.settingscreen.model.DeregisterNaviPayRequest +import com.navi.pay.common.settingscreen.model.DeregisterNaviPayResponse import com.navi.pay.management.blockedusers.model.network.BlockedUsersListRequest import com.navi.pay.management.blockedusers.model.network.BlockedUsersListResponse import com.navi.pay.management.blockedusers.model.network.UnblockActionRequest @@ -442,4 +444,9 @@ interface NaviPayRetrofitService { suspend fun forecloseEmi( @Body forecloseEmiRequest: ForecloseEmiRequest ): Response> + + @POST("/gateway-service/$NAVI_PAY_API_VERSION2/navipay/customer/deregister") + suspend fun deregisterNaviPay( + @Body deregisterNaviPayRequest: DeregisterNaviPayRequest + ): Response> } diff --git a/android/navi-pay/src/main/kotlin/com/navi/pay/utils/NaviPayConstants.kt b/android/navi-pay/src/main/kotlin/com/navi/pay/utils/NaviPayConstants.kt index b31620b330..30b9996b0c 100644 --- a/android/navi-pay/src/main/kotlin/com/navi/pay/utils/NaviPayConstants.kt +++ b/android/navi-pay/src/main/kotlin/com/navi/pay/utils/NaviPayConstants.kt @@ -510,6 +510,7 @@ const val ALL_ENABLED_ACCOUNTS = "[\"SAVINGS\", \"CREDIT\", \"UPICREDIT\"]" const val LINKED_ACCOUNT_SCREEN_SOURCE = "linkedAccountScreenSource" const val CHECK_BALANCE = "CheckBalance" const val SELF_TRANSFER = "SelfTransfer" +const val NAVI_PAY_DEREGISTER = "NAVI_PAY_DEREGISTER" // Link upi number constants const val AVAILABILITY_ACTION_CHECK = "CHECK" @@ -632,3 +633,8 @@ const val ERR_FAILED_TO_FETCH_EXTERNAL_CUSTOMER_ID = "ERR_FAILED_TO_FETCH_EXTERN // Lrn mismatch error const val LRN_MISMATCH_ERROR = "lrn_mismatch_error" + +// Deregister navi upi error codes +const val ERR_ACTIVE_LITE_ACCOUNT_FOUND = "ERR_ACTIVE_LITE_ACCOUNT_FOUND" +const val ERR_MANDATE_PRESENT = "ERR_MANDATE_PRESENT" +const val ERR_LITE_AND_MANDATE_ACTIVE = "ERR_LITE_AND_MANDATE_ACTIVE" diff --git a/android/navi-pay/src/main/res/values/strings.xml b/android/navi-pay/src/main/res/values/strings.xml index 31c43855a4..049e913086 100644 --- a/android/navi-pay/src/main/res/values/strings.xml +++ b/android/navi-pay/src/main/res/values/strings.xml @@ -1151,4 +1151,14 @@ UPI txn ID: Bank txn ID (UTR): Note: + Are you sure you want to de-register from Navi UPI? + De-registering from Navi UPI will remove all your payment methods and deactivate all UPI IDs. + De-registered from Navi UPI succesfully + De-registration failed as UPI Lite is active + UPI Lite is currently active. Please disable UPI Lite and try de-registering again. + De-registration failed as autopay mandate(s) are active + Mandate(s) are currently active. Please delete all mandates and try de-registering again. + De-registration failed as autopay mandate(s) and UPI Lite are active + Mandate(s) and UPI Lite are currently active. Please disable UPI Lite, delete all mandates and try de-registering again. + \ No newline at end of file