Browse Source

Merge pull request #3163 from element-hq/feature/bma/clearCacheEmptyScreen

Fix empty screen issue after clearing the cache
pull/3171/head
Benoit Marty 2 months ago committed by GitHub
parent
commit
eaf2d367fc
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
  1. 1
      appnav/build.gradle.kts
  2. 4
      appnav/src/main/kotlin/io/element/android/appnav/root/RootNavStateFlowFactory.kt
  3. 10
      features/ftue/impl/src/main/kotlin/io/element/android/features/ftue/impl/FtueFlowNode.kt
  4. 15
      features/ftue/impl/src/main/kotlin/io/element/android/features/ftue/impl/state/DefaultFtueService.kt
  5. 2
      features/ftue/impl/src/test/kotlin/io/element/android/features/ftue/impl/DefaultFtueServiceTest.kt

1
appnav/build.gradle.kts

@ -42,6 +42,7 @@ dependencies { @@ -42,6 +42,7 @@ dependencies {
implementation(projects.libraries.architecture)
implementation(projects.libraries.deeplink)
implementation(projects.libraries.matrix.api)
implementation(projects.libraries.preferences.api)
implementation(projects.libraries.push.api)
implementation(projects.libraries.pushproviders.api)
implementation(projects.libraries.designsystem)

4
appnav/src/main/kotlin/io/element/android/appnav/root/RootNavStateFlowFactory.kt

@ -23,6 +23,7 @@ import io.element.android.features.login.api.LoginUserStory @@ -23,6 +23,7 @@ import io.element.android.features.login.api.LoginUserStory
import io.element.android.features.preferences.api.CacheService
import io.element.android.libraries.matrix.api.auth.MatrixAuthenticationService
import io.element.android.libraries.matrix.ui.media.ImageLoaderHolder
import io.element.android.libraries.preferences.api.store.SessionPreferencesStoreFactory
import io.element.android.libraries.sessionstorage.api.LoggedInState
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.combine
@ -42,6 +43,7 @@ class RootNavStateFlowFactory @Inject constructor( @@ -42,6 +43,7 @@ class RootNavStateFlowFactory @Inject constructor(
private val matrixClientsHolder: MatrixClientsHolder,
private val imageLoaderHolder: ImageLoaderHolder,
private val loginUserStory: LoginUserStory,
private val sessionPreferencesStoreFactory: SessionPreferencesStoreFactory,
) {
private var currentCacheIndex = 0
@ -73,6 +75,8 @@ class RootNavStateFlowFactory @Inject constructor( @@ -73,6 +75,8 @@ class RootNavStateFlowFactory @Inject constructor(
matrixClientsHolder.remove(sessionId)
// Ensure image loader will be recreated with the new MatrixClient
imageLoaderHolder.remove(sessionId)
// Also remove cached value for SessionPreferencesStore
sessionPreferencesStoreFactory.remove(sessionId)
}
.toIndexFlow(initialCacheIndex)
.onEach { cacheIndex ->

10
features/ftue/impl/src/main/kotlin/io/element/android/features/ftue/impl/FtueFlowNode.kt

@ -45,7 +45,7 @@ import io.element.android.libraries.di.SessionScope @@ -45,7 +45,7 @@ import io.element.android.libraries.di.SessionScope
import io.element.android.services.analytics.api.AnalyticsService
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.StateFlow
import kotlinx.coroutines.flow.drop
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
import kotlinx.coroutines.launch
@ -93,11 +93,9 @@ class FtueFlowNode @AssistedInject constructor( @@ -93,11 +93,9 @@ class FtueFlowNode @AssistedInject constructor(
})
analyticsService.didAskUserConsent()
.drop(1) // We only care about consent passing from not asked to asked state
.onEach { didAskUserConsent ->
if (didAskUserConsent) {
lifecycleScope.launch { moveToNextStep() }
}
.distinctUntilChanged()
.onEach {
lifecycleScope.launch { moveToNextStep() }
}
.launchIn(lifecycleScope)
}

15
features/ftue/impl/src/main/kotlin/io/element/android/features/ftue/impl/state/DefaultFtueService.kt

@ -24,6 +24,7 @@ import io.element.android.features.ftue.api.state.FtueService @@ -24,6 +24,7 @@ import io.element.android.features.ftue.api.state.FtueService
import io.element.android.features.ftue.api.state.FtueState
import io.element.android.features.lockscreen.api.LockScreenService
import io.element.android.libraries.di.SessionScope
import io.element.android.libraries.di.annotations.SessionCoroutineScope
import io.element.android.libraries.matrix.api.verification.SessionVerificationService
import io.element.android.libraries.matrix.api.verification.SessionVerifiedStatus
import io.element.android.libraries.permissions.api.PermissionStateProvider
@ -34,6 +35,7 @@ import kotlinx.coroutines.CoroutineScope @@ -34,6 +35,7 @@ import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.FlowPreview
import kotlinx.coroutines.flow.MutableStateFlow
import kotlinx.coroutines.flow.catch
import kotlinx.coroutines.flow.distinctUntilChanged
import kotlinx.coroutines.flow.filter
import kotlinx.coroutines.flow.first
import kotlinx.coroutines.flow.launchIn
@ -47,7 +49,7 @@ import kotlin.time.Duration.Companion.seconds @@ -47,7 +49,7 @@ import kotlin.time.Duration.Companion.seconds
@ContributesBinding(SessionScope::class)
class DefaultFtueService @Inject constructor(
private val sdkVersionProvider: BuildVersionSdkIntProvider,
coroutineScope: CoroutineScope,
@SessionCoroutineScope sessionCoroutineScope: CoroutineScope,
private val analyticsService: AnalyticsService,
private val permissionStateProvider: PermissionStateProvider,
private val lockScreenService: LockScreenService,
@ -66,11 +68,12 @@ class DefaultFtueService @Inject constructor( @@ -66,11 +68,12 @@ class DefaultFtueService @Inject constructor(
init {
sessionVerificationService.sessionVerifiedStatus
.onEach { updateState() }
.launchIn(coroutineScope)
.launchIn(sessionCoroutineScope)
analyticsService.didAskUserConsent()
.distinctUntilChanged()
.onEach { updateState() }
.launchIn(coroutineScope)
.launchIn(sessionCoroutineScope)
}
suspend fun getNextStep(currentStep: FtueStep? = null): FtueStep? =
@ -119,10 +122,7 @@ class DefaultFtueService @Inject constructor( @@ -119,10 +122,7 @@ class DefaultFtueService @Inject constructor(
emit(SessionVerifiedStatus.NotVerified)
}
.first()
// For some obscure reason we need to call this *before* we check the `readyVerifiedSessionStatus`, otherwise there's a deadlock
// It seems like a DataStore bug
val skipVerification = canSkipVerification()
return readyVerifiedSessionStatus == SessionVerifiedStatus.NotVerified && !skipVerification
return readyVerifiedSessionStatus == SessionVerifiedStatus.NotVerified && !canSkipVerification()
}
private suspend fun canSkipVerification(): Boolean {
@ -130,7 +130,6 @@ class DefaultFtueService @Inject constructor( @@ -130,7 +130,6 @@ class DefaultFtueService @Inject constructor(
}
private suspend fun needsAnalyticsOptIn(): Boolean {
// We need this function to not be suspend, so we need to load the value through runBlocking
return analyticsService.didAskUserConsent().first().not()
}

2
features/ftue/impl/src/test/kotlin/io/element/android/features/ftue/impl/DefaultFtueServiceTest.kt

@ -251,7 +251,7 @@ class DefaultFtueServiceTest { @@ -251,7 +251,7 @@ class DefaultFtueServiceTest {
// First version where notification permission is required
sdkIntVersion: Int = Build.VERSION_CODES.TIRAMISU,
) = DefaultFtueService(
coroutineScope = coroutineScope,
sessionCoroutineScope = coroutineScope,
sessionVerificationService = sessionVerificationService,
sdkVersionProvider = FakeBuildVersionSdkIntProvider(sdkIntVersion),
analyticsService = analyticsService,

Loading…
Cancel
Save