diff --git a/feature/savings-account/src/commonMain/composeResources/values/strings.xml b/feature/savings-account/src/commonMain/composeResources/values/strings.xml
index a1fe7fe73f..2575acd2f2 100644
--- a/feature/savings-account/src/commonMain/composeResources/values/strings.xml
+++ b/feature/savings-account/src/commonMain/composeResources/values/strings.xml
@@ -75,6 +75,8 @@
Request Update
New Product
+ Currently Loan Products are not available
+
Request Submitted Successfully
Request to update the account details is submitted successfully
Back To Home
diff --git a/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateScreen.kt b/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateScreen.kt
index a7a2c53292..fae83b1593 100644
--- a/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateScreen.kt
+++ b/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateScreen.kt
@@ -27,6 +27,7 @@ import androidx.compose.ui.Modifier
import androidx.lifecycle.compose.collectAsStateWithLifecycle
import mifos_mobile.feature.savings_account.generated.resources.Res
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_new_product_label
+import mifos_mobile.feature.savings_account.generated.resources.feature_savings_savings_product_empty
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_update_product_label
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_update_topbar_title
import org.jetbrains.compose.resources.stringResource
@@ -126,6 +127,14 @@ internal fun AccountUpdateScreenContent(
},
) {
when (state.uiState) {
+ ScreenUiState.Empty -> {
+ MifosErrorComponent(
+ isRetryEnabled = true,
+ message = stringResource(Res.string.feature_savings_savings_product_empty),
+ onRetry = { onAction(AccountUpdateAction.Retry) },
+ )
+ }
+
is ScreenUiState.Error -> {
MifosErrorComponent(
isRetryEnabled = true,
diff --git a/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateViewModel.kt b/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateViewModel.kt
index b62e378f42..8f6ff5e99f 100644
--- a/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateViewModel.kt
+++ b/feature/savings-account/src/commonMain/kotlin/org/mifos/mobile/feature/savingsaccount/savingsAccountUpdate/AccountUpdateViewModel.kt
@@ -18,6 +18,7 @@ import kotlinx.coroutines.launch
import kotlinx.serialization.ExperimentalSerializationApi
import kotlinx.serialization.InternalSerializationApi
import mifos_mobile.feature.savings_account.generated.resources.Res
+import mifos_mobile.feature.savings_account.generated.resources.feature_generic_error_server
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_update_account_number_label
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_update_client_name_label
import mifos_mobile.feature.savings_account.generated.resources.feature_savings_update_product_label
@@ -74,17 +75,10 @@ internal class AccountUpdateViewModel(
Res.string.feature_savings_update_account_number_label to clientDetails.accountNumber,
Res.string.feature_savings_update_product_label to clientDetails.product,
)
- val productOptions = mapOf(
- 1L to "Wallet",
- 2L to "FDP",
- 4L to "1 year Fixed Deposit",
-
- )
AccountUpdateState(
clientId = requireNotNull(userPreferencesRepository.clientId.value),
accountId = requireNotNull(clientDetails.accountId),
details = detailsMap,
- productOptions = productOptions,
dialogState = null,
)
},
@@ -95,19 +89,14 @@ internal class AccountUpdateViewModel(
observeAuthResult()
}
-// TODO get savings product from server
-// init {
-// observeSavingsProducts()
-// }
-
-// private fun observeSavingsProducts() {
-// viewModelScope.launch {
-// savingsAccountRepositoryImp.getSavingAccountApplicationTemplate(state.clientId)
-// .collect {
-// sendAction(AccountUpdateAction.Internal.ReceiveProducts(it))
-// }
-// }
-// }
+ private fun fetchSavingsProducts() {
+ viewModelScope.launch {
+ savingsAccountRepositoryImp.getSavingAccountApplicationTemplate(state.clientId)
+ .collect {
+ sendAction(AccountUpdateAction.Internal.ReceiveProducts(it))
+ }
+ }
+ }
/**
* Observes the network connectivity status and updates state accordingly.
@@ -131,6 +120,7 @@ internal class AccountUpdateViewModel(
*
* @param isOnline A boolean indicating the current network status.
*/
+ @Suppress("ComplexCondition")
private fun handleNetworkStatus(isOnline: Boolean) {
updateState { it.copy(networkStatus = isOnline) }
@@ -138,6 +128,7 @@ internal class AccountUpdateViewModel(
if (!isOnline) {
updateState { current ->
if (current.uiState is ScreenUiState.Loading ||
+ state.showOverlay ||
current.uiState is ScreenUiState.Error ||
current.uiState is ScreenUiState.Empty ||
current.uiState is ScreenUiState.Network
@@ -148,7 +139,7 @@ internal class AccountUpdateViewModel(
}
}
} else {
- // TODO get the products from server
+ fetchSavingsProducts()
}
}
}
@@ -158,7 +149,7 @@ internal class AccountUpdateViewModel(
if (!state.networkStatus) {
updateState { it.copy(uiState = ScreenUiState.Network) }
} else {
- // TODO get the products from server
+ fetchSavingsProducts()
}
}
}
@@ -201,8 +192,7 @@ internal class AccountUpdateViewModel(
is AccountUpdateAction.Retry -> retry()
-// TODO handle received products
- is AccountUpdateAction.Internal.ReceiveProducts -> { }
+ is AccountUpdateAction.Internal.ReceiveProducts -> handleSavingsProduct(action.dataState)
is AccountUpdateAction.Internal.ReceiveUpdateRequestResult -> {
viewModelScope.launch {
@@ -220,6 +210,49 @@ internal class AccountUpdateViewModel(
}
}
+ /**
+ * Handles the result of the `fetchSavingsProducts` network call.
+ * Updates the state with product options on success. If the list of
+ * options is empty, it sets the `isEmpty` flag to true. On failure,
+ * it displays an error dialog.
+ *
+ * @param template The [DataState] containing the loan template data.
+ */
+ private fun handleSavingsProduct(template: DataState) {
+ when (template) {
+ is DataState.Loading -> updateState { it.copy(uiState = ScreenUiState.Loading) }
+ is DataState.Success -> {
+ val loanTemplate = template.data
+ if (loanTemplate.productOptions.isEmpty()) {
+ updateState {
+ it.copy(
+ uiState = ScreenUiState.Empty,
+ )
+ }
+ return
+ }
+
+ val productOptions = loanTemplate.productOptions.associate {
+ it.id.toLong() to it.name
+ }
+
+ updateState {
+ it.copy(
+ uiState = ScreenUiState.Success,
+ productOptions = productOptions,
+ )
+ }
+ }
+ is DataState.Error -> {
+ updateState {
+ it.copy(
+ uiState = ScreenUiState.Error(Res.string.feature_generic_error_server),
+ )
+ }
+ }
+ }
+ }
+
/**
* Updates state based on selected product from dropdown.
*