Skip to content

Commit 4ab63a0

Browse files
committed
Feat: 강제 업데이트 로직 구현
1 parent 498c2d2 commit 4ab63a0

File tree

2 files changed

+47
-1
lines changed

2 files changed

+47
-1
lines changed

presentation/src/main/java/com/threegap/bitnagil/presentation/splash/SplashScreen.kt

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
package com.threegap.bitnagil.presentation.splash
22

3+
import androidx.activity.ComponentActivity
34
import androidx.compose.animation.core.tween
45
import androidx.compose.animation.fadeIn
56
import androidx.compose.foundation.background
@@ -16,15 +17,20 @@ import androidx.compose.runtime.remember
1617
import androidx.compose.runtime.setValue
1718
import androidx.compose.ui.Alignment
1819
import androidx.compose.ui.Modifier
20+
import androidx.compose.ui.platform.LocalContext
1921
import androidx.compose.ui.tooling.preview.Preview
2022
import androidx.compose.ui.unit.dp
2123
import androidx.hilt.navigation.compose.hiltViewModel
24+
import androidx.lifecycle.compose.collectAsStateWithLifecycle
2225
import com.threegap.bitnagil.designsystem.BitnagilTheme
2326
import com.threegap.bitnagil.designsystem.R
2427
import com.threegap.bitnagil.designsystem.component.atom.BitnagilIcon
2528
import com.threegap.bitnagil.presentation.splash.component.template.BitnagilLottieAnimation
29+
import com.threegap.bitnagil.presentation.splash.component.template.ForceUpdateDialog
2630
import com.threegap.bitnagil.presentation.splash.model.SplashSideEffect
31+
import com.threegap.bitnagil.presentation.splash.util.openAppInPlayStore
2732
import org.orbitmvi.orbit.compose.collectSideEffect
33+
import kotlin.system.exitProcess
2834

2935
@Composable
3036
fun SplashScreenContainer(
@@ -34,6 +40,10 @@ fun SplashScreenContainer(
3440
navigateToHome: () -> Unit,
3541
viewModel: SplashViewModel = hiltViewModel(),
3642
) {
43+
val context = LocalContext.current
44+
val activity = context as? ComponentActivity
45+
val uiState by viewModel.stateFlow.collectAsStateWithLifecycle()
46+
3747
viewModel.collectSideEffect { sideEffect ->
3848
when (sideEffect) {
3949
is SplashSideEffect.NavigateToLogin -> navigateToLogin()
@@ -46,6 +56,16 @@ fun SplashScreenContainer(
4656
SplashScreen(
4757
onCompleted = viewModel::onAnimationCompleted,
4858
)
59+
60+
if (uiState.forceUpdateRequired) {
61+
ForceUpdateDialog(
62+
onUpdateClick = { openAppInPlayStore(activity) },
63+
onDismissRequest = {
64+
activity?.finishAffinity()
65+
exitProcess(0)
66+
},
67+
)
68+
}
4969
}
5070

5171
@Composable

presentation/src/main/java/com/threegap/bitnagil/presentation/splash/SplashViewModel.kt

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import androidx.lifecycle.SavedStateHandle
44
import androidx.lifecycle.viewModelScope
55
import com.threegap.bitnagil.domain.auth.model.UserRole
66
import com.threegap.bitnagil.domain.auth.usecase.AutoLoginUseCase
7+
import com.threegap.bitnagil.domain.version.usecase.CheckUpdateRequirementUseCase
78
import com.threegap.bitnagil.presentation.common.mviviewmodel.MviViewModel
89
import com.threegap.bitnagil.presentation.splash.model.SplashIntent
910
import com.threegap.bitnagil.presentation.splash.model.SplashSideEffect
@@ -18,14 +19,15 @@ import javax.inject.Inject
1819
@HiltViewModel
1920
class SplashViewModel @Inject constructor(
2021
savedStateHandle: SavedStateHandle,
22+
private val checkUpdateRequirementUseCase: CheckUpdateRequirementUseCase,
2123
private val autoLoginUseCase: AutoLoginUseCase,
2224
) : MviViewModel<SplashState, SplashSideEffect, SplashIntent>(
2325
initState = SplashState(),
2426
savedStateHandle = savedStateHandle,
2527
) {
2628

2729
init {
28-
performAutoLogin()
30+
performForceUpdateCheck()
2931
}
3032

3133
override suspend fun SimpleSyntax<SplashState, SplashSideEffect>.reduceState(
@@ -40,6 +42,13 @@ class SplashViewModel @Inject constructor(
4042
)
4143
}
4244

45+
is SplashIntent.SetForceUpdateResult -> {
46+
state.copy(
47+
forceUpdateRequired = intent.isRequired,
48+
isForceUpdateCheckCompleted = true,
49+
)
50+
}
51+
4352
is SplashIntent.NavigateToLogin -> {
4453
sendSideEffect(SplashSideEffect.NavigateToLogin)
4554
null
@@ -61,6 +70,20 @@ class SplashViewModel @Inject constructor(
6170
}
6271
}
6372

73+
private fun performForceUpdateCheck() {
74+
viewModelScope.launch {
75+
val isUpdateRequired = withTimeoutOrNull(5000) {
76+
checkUpdateRequirementUseCase().getOrElse { false }
77+
} ?: false
78+
79+
sendIntent(SplashIntent.SetForceUpdateResult(isUpdateRequired))
80+
81+
if (!isUpdateRequired) {
82+
performAutoLogin()
83+
}
84+
}
85+
}
86+
6487
private fun performAutoLogin() {
6588
viewModelScope.launch {
6689
try {
@@ -76,6 +99,9 @@ class SplashViewModel @Inject constructor(
7699

77100
fun onAnimationCompleted() {
78101
val splashState = container.stateFlow.value
102+
103+
if (splashState.forceUpdateRequired) return
104+
79105
if (!splashState.isAutoLoginCompleted) {
80106
viewModelScope.launch {
81107
delay(100)

0 commit comments

Comments
 (0)