Fix tests

This commit is contained in:
Jorge Martín 2025-12-16 16:53:24 +01:00 committed by Jorge Martin Espinosa
parent a91dac6cac
commit fa8d7b73c7
3 changed files with 54 additions and 30 deletions

View file

@ -19,29 +19,31 @@ import io.element.android.services.analytics.test.FakeAnalyticsService
import io.element.android.services.appnavstate.test.FakeAppForegroundStateService import io.element.android.services.appnavstate.test.FakeAppForegroundStateService
import io.element.android.tests.testutils.testCoroutineDispatchers import io.element.android.tests.testutils.testCoroutineDispatchers
import kotlinx.coroutines.CoroutineScope import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.ExperimentalCoroutinesApi
import kotlinx.coroutines.test.TestScope import kotlinx.coroutines.test.TestScope
import kotlinx.coroutines.test.runCurrent
import kotlinx.coroutines.test.runTest import kotlinx.coroutines.test.runTest
import org.junit.Test import org.junit.Test
@OptIn(ExperimentalCoroutinesApi::class)
class MatrixSessionCacheTest { class MatrixSessionCacheTest {
@Test @Test
fun `test getOrNull`() = runTest { fun `test getOrNull`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val matrixSessionCache = createMatrixSessionCache()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory())
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull() assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull()
} }
@Test @Test
fun `test getSyncOrchestratorOrNull`() = runTest { fun `test getSyncOrchestratorOrNull`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService)
// With no matrix client there is no sync orchestrator // With no matrix client there is no sync orchestrator
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull() assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull()
assertThat(matrixSessionCache.getSyncOrchestrator(A_SESSION_ID)).isNull() assertThat(matrixSessionCache.getSyncOrchestrator(A_SESSION_ID)).isNull()
// But as soon as we receive a client, we can get the sync orchestrator // But as soon as we receive a client, we can get the sync orchestrator
val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope) val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope, userIdServerNameLambda = { A_SESSION_ID.value })
fakeAuthenticationService.givenMatrixClient(fakeMatrixClient) fakeAuthenticationService.givenMatrixClient(fakeMatrixClient)
assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient)
assertThat(matrixSessionCache.getSyncOrchestrator(A_SESSION_ID)).isNotNull() assertThat(matrixSessionCache.getSyncOrchestrator(A_SESSION_ID)).isNotNull()
@ -50,8 +52,8 @@ class MatrixSessionCacheTest {
@Test @Test
fun `test getOrRestore`() = runTest { fun `test getOrRestore`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService)
val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope) val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope, userIdServerNameLambda = { A_SESSION_ID.value })
fakeAuthenticationService.givenMatrixClient(fakeMatrixClient) fakeAuthenticationService.givenMatrixClient(fakeMatrixClient)
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull() assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull()
assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient)
@ -63,8 +65,8 @@ class MatrixSessionCacheTest {
@Test @Test
fun `test remove`() = runTest { fun `test remove`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService)
val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope) val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope, userIdServerNameLambda = { A_SESSION_ID.value })
fakeAuthenticationService.givenMatrixClient(fakeMatrixClient) fakeAuthenticationService.givenMatrixClient(fakeMatrixClient)
assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient)
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isEqualTo(fakeMatrixClient)
@ -76,8 +78,8 @@ class MatrixSessionCacheTest {
@Test @Test
fun `test remove all`() = runTest { fun `test remove all`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService)
val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope) val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope, userIdServerNameLambda = { A_SESSION_ID.value })
fakeAuthenticationService.givenMatrixClient(fakeMatrixClient) fakeAuthenticationService.givenMatrixClient(fakeMatrixClient)
assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrRestore(A_SESSION_ID).getOrNull()).isEqualTo(fakeMatrixClient)
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isEqualTo(fakeMatrixClient) assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isEqualTo(fakeMatrixClient)
@ -89,8 +91,8 @@ class MatrixSessionCacheTest {
@Test @Test
fun `test save and restore`() = runTest { fun `test save and restore`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService)
val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope) val fakeMatrixClient = FakeMatrixClient(sessionCoroutineScope = backgroundScope, userIdServerNameLambda = { A_SESSION_ID.value })
fakeAuthenticationService.givenMatrixClient(fakeMatrixClient) fakeAuthenticationService.givenMatrixClient(fakeMatrixClient)
matrixSessionCache.getOrRestore(A_SESSION_ID) matrixSessionCache.getOrRestore(A_SESSION_ID)
val savedStateMap = MutableSavedStateMapImpl { true } val savedStateMap = MutableSavedStateMapImpl { true }
@ -109,29 +111,45 @@ class MatrixSessionCacheTest {
@Test @Test
fun `test AuthenticationService listenToNewMatrixClients emits a Client value and we save it`() = runTest { fun `test AuthenticationService listenToNewMatrixClients emits a Client value and we save it`() = runTest {
val fakeAuthenticationService = FakeMatrixAuthenticationService() val fakeAuthenticationService = FakeMatrixAuthenticationService()
val matrixSessionCache = MatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory()) val matrixSessionCache = createMatrixSessionCache(fakeAuthenticationService, createSyncOrchestratorFactory())
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull() assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNull()
fakeAuthenticationService.givenMatrixClient(FakeMatrixClient(sessionId = A_SESSION_ID, sessionCoroutineScope = backgroundScope))
val loginSucceeded = fakeAuthenticationService.login("user", "pass") val loginSucceeded = fakeAuthenticationService.login("user", "pass")
assertThat(loginSucceeded.isSuccess).isTrue() assertThat(loginSucceeded.isSuccess).isTrue()
runCurrent()
assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNotNull() assertThat(matrixSessionCache.getOrNull(A_SESSION_ID)).isNotNull()
} }
private fun TestScope.createSyncOrchestratorFactory() = object : SyncOrchestrator.Factory { private fun TestScope.createMatrixSessionCache(
override fun create( authenticationService: FakeMatrixAuthenticationService = FakeMatrixAuthenticationService(),
syncService: SyncService, syncOrchestratorFactory: SyncOrchestrator.Factory = createSyncOrchestratorFactory(),
sessionCoroutineScope: CoroutineScope, analyticsService: FakeAnalyticsService = FakeAnalyticsService(),
): SyncOrchestrator { ) = MatrixSessionCache(
return SyncOrchestrator( authenticationService = authenticationService,
syncService = syncService, syncOrchestratorFactory = syncOrchestratorFactory,
sessionCoroutineScope = sessionCoroutineScope, analyticsService = analyticsService,
appForegroundStateService = FakeAppForegroundStateService(), )
networkMonitor = FakeNetworkMonitor(),
dispatchers = testCoroutineDispatchers(), private fun TestScope.createSyncOrchestratorFactory(): SyncOrchestrator.Factory {
analyticsService = FakeAnalyticsService(), val dispatchers = testCoroutineDispatchers()
)
return object : SyncOrchestrator.Factory {
override fun create(
syncService: SyncService,
sessionCoroutineScope: CoroutineScope,
): SyncOrchestrator {
return SyncOrchestrator(
syncService = syncService,
sessionCoroutineScope = sessionCoroutineScope,
appForegroundStateService = FakeAppForegroundStateService(),
networkMonitor = FakeNetworkMonitor(),
dispatchers = dispatchers,
analyticsService = FakeAnalyticsService(),
)
}
} }
} }
} }

View file

@ -14,6 +14,7 @@ import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.SupervisorJob import kotlinx.coroutines.SupervisorJob
import kotlinx.coroutines.job import kotlinx.coroutines.job
import kotlinx.coroutines.plus import kotlinx.coroutines.plus
import kotlinx.coroutines.test.TestScope
/** /**
* Create a child scope of the current scope. * Create a child scope of the current scope.
@ -28,6 +29,11 @@ fun CoroutineScope.childScope(
dispatcher: CoroutineDispatcher, dispatcher: CoroutineDispatcher,
name: String, name: String,
): CoroutineScope = run { ): CoroutineScope = run {
val supervisorJob = SupervisorJob(parent = coroutineContext.job) if (this is TestScope) {
this + dispatcher + supervisorJob + CoroutineName(name) // Special case for tests: we can't start a coroutine with a different SupervisorJob
this
} else {
val supervisorJob = SupervisorJob(parent = coroutineContext.job)
this + dispatcher + supervisorJob + CoroutineName(name)
}
} }

View file

@ -175,7 +175,7 @@ class RustBaseRoomTest {
), ),
roomMembershipObserver = roomMembershipObserver, roomMembershipObserver = roomMembershipObserver,
// Not using backgroundScope here, but the test scope // Not using backgroundScope here, but the test scope
sessionCoroutineScope = this, sessionCoroutineScope = backgroundScope,
roomInfoMapper = RoomInfoMapper(), roomInfoMapper = RoomInfoMapper(),
initialRoomInfo = initialRoomInfo, initialRoomInfo = initialRoomInfo,
) )