StartDM : add tests
This commit is contained in:
@@ -67,6 +67,7 @@ dependencies {
|
||||
testImplementation(projects.libraries.mediaupload.test)
|
||||
testImplementation(projects.libraries.permissions.test)
|
||||
testImplementation(projects.libraries.usersearch.test)
|
||||
testImplementation(projects.features.createroom.test)
|
||||
testImplementation(projects.tests.testutils)
|
||||
|
||||
ksp(libs.showkase.processor)
|
||||
|
||||
@@ -21,7 +21,6 @@ import com.squareup.anvil.annotations.ContributesBinding
|
||||
import im.vector.app.features.analytics.plan.CreatedRoom
|
||||
import io.element.android.features.createroom.api.StartDMAction
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.di.AppScope
|
||||
import io.element.android.libraries.di.SessionScope
|
||||
import io.element.android.libraries.matrix.api.MatrixClient
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* Copyright (c) 2023 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package io.element.android.features.createroom.impl
|
||||
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import com.google.common.truth.Truth.assertThat
|
||||
import im.vector.app.features.analytics.plan.CreatedRoom
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.matrix.api.MatrixClient
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
import io.element.android.libraries.matrix.api.room.StartDMResult
|
||||
import io.element.android.libraries.matrix.test.A_FAILURE_REASON
|
||||
import io.element.android.libraries.matrix.test.A_ROOM_ID
|
||||
import io.element.android.libraries.matrix.test.A_THROWABLE
|
||||
import io.element.android.libraries.matrix.test.A_USER_ID
|
||||
import io.element.android.libraries.matrix.test.FakeMatrixClient
|
||||
import io.element.android.services.analytics.api.AnalyticsService
|
||||
import io.element.android.services.analytics.test.FakeAnalyticsService
|
||||
import kotlinx.coroutines.test.runTest
|
||||
import org.junit.Test
|
||||
|
||||
class DefaultStartDMActionTests {
|
||||
|
||||
@Test
|
||||
fun `when dm is found, assert state is updated with given room id`() = runTest {
|
||||
val matrixClient = FakeMatrixClient().apply {
|
||||
givenFindDmResult(A_ROOM_ID)
|
||||
}
|
||||
val action = createStartDMAction(matrixClient)
|
||||
val state = mutableStateOf<Async<RoomId>>(Async.Uninitialized)
|
||||
action.execute(A_USER_ID, state)
|
||||
assertThat(state.value).isEqualTo(Async.Success(A_ROOM_ID))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `when dm is not found, assert dm is created, state is updated with given room id and analytics get called`() = runTest {
|
||||
val matrixClient = FakeMatrixClient().apply {
|
||||
givenFindDmResult(null)
|
||||
givenCreateDmResult(Result.success(A_ROOM_ID))
|
||||
}
|
||||
val analyticsService = FakeAnalyticsService()
|
||||
val action = createStartDMAction(matrixClient, analyticsService)
|
||||
val state = mutableStateOf<Async<RoomId>>(Async.Uninitialized)
|
||||
action.execute(A_USER_ID, state)
|
||||
assertThat(state.value).isEqualTo(Async.Success(A_ROOM_ID))
|
||||
assertThat(analyticsService.capturedEvents).containsExactly(CreatedRoom(isDM = true))
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `when dm creation fails, assert state is updated with given error`() = runTest {
|
||||
val matrixClient = FakeMatrixClient().apply {
|
||||
givenFindDmResult(null)
|
||||
givenCreateDmResult(Result.failure(A_THROWABLE))
|
||||
}
|
||||
val action = createStartDMAction(matrixClient)
|
||||
val state = mutableStateOf<Async<RoomId>>(Async.Uninitialized)
|
||||
action.execute(A_USER_ID, state)
|
||||
assertThat(state.value).isEqualTo(Async.Failure<RoomId>(StartDMResult.Failure(A_FAILURE_REASON)))
|
||||
}
|
||||
|
||||
private fun createStartDMAction(
|
||||
matrixClient: MatrixClient = FakeMatrixClient(),
|
||||
analyticsService: AnalyticsService = FakeAnalyticsService(),
|
||||
): DefaultStartDMAction {
|
||||
return DefaultStartDMAction(
|
||||
matrixClient = matrixClient,
|
||||
analyticsService = analyticsService,
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -20,25 +20,22 @@ import app.cash.molecule.RecompositionMode
|
||||
import app.cash.molecule.moleculeFlow
|
||||
import app.cash.turbine.test
|
||||
import com.google.common.truth.Truth.assertThat
|
||||
import im.vector.app.features.analytics.plan.CreatedRoom
|
||||
import io.element.android.features.createroom.api.StartDMAction
|
||||
import io.element.android.features.createroom.impl.userlist.FakeUserListPresenter
|
||||
import io.element.android.features.createroom.impl.userlist.FakeUserListPresenterFactory
|
||||
import io.element.android.features.createroom.impl.userlist.UserListDataStore
|
||||
import io.element.android.features.createroom.impl.userlist.aUserListState
|
||||
import io.element.android.features.createroom.test.FakeStartDMAction
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
import io.element.android.libraries.matrix.api.core.UserId
|
||||
import io.element.android.libraries.matrix.api.room.StartDMResult
|
||||
import io.element.android.libraries.matrix.api.user.MatrixUser
|
||||
import io.element.android.libraries.matrix.test.A_THROWABLE
|
||||
import io.element.android.libraries.matrix.test.FakeMatrixClient
|
||||
import io.element.android.libraries.matrix.test.A_FAILURE_REASON
|
||||
import io.element.android.libraries.matrix.test.A_ROOM_ID
|
||||
import io.element.android.libraries.matrix.test.core.aBuildMeta
|
||||
import io.element.android.libraries.matrix.test.room.FakeMatrixRoom
|
||||
import io.element.android.libraries.usersearch.test.FakeUserRepository
|
||||
import io.element.android.services.analytics.test.FakeAnalyticsService
|
||||
import io.element.android.tests.testutils.WarmUpRule
|
||||
import kotlinx.collections.immutable.persistentListOf
|
||||
import kotlinx.coroutines.test.runTest
|
||||
import org.junit.Before
|
||||
import org.junit.Rule
|
||||
import org.junit.Test
|
||||
|
||||
@@ -47,142 +44,57 @@ class CreateRoomRootPresenterTests {
|
||||
@get:Rule
|
||||
val warmUpRule = WarmUpRule()
|
||||
|
||||
private lateinit var userRepository: FakeUserRepository
|
||||
private lateinit var presenter: CreateRoomRootPresenter
|
||||
private lateinit var fakeUserListPresenter: FakeUserListPresenter
|
||||
private lateinit var fakeMatrixClient: FakeMatrixClient
|
||||
private lateinit var fakeAnalyticsService: FakeAnalyticsService
|
||||
|
||||
@Before
|
||||
fun setup() {
|
||||
fakeUserListPresenter = FakeUserListPresenter()
|
||||
fakeMatrixClient = FakeMatrixClient()
|
||||
fakeAnalyticsService = FakeAnalyticsService()
|
||||
userRepository = FakeUserRepository()
|
||||
presenter = CreateRoomRootPresenter(
|
||||
presenterFactory = FakeUserListPresenterFactory(fakeUserListPresenter),
|
||||
userRepository = userRepository,
|
||||
userListDataStore = UserListDataStore(),
|
||||
matrixClient = fakeMatrixClient,
|
||||
analyticsService = fakeAnalyticsService,
|
||||
buildMeta = aBuildMeta(),
|
||||
)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - initial state`() = runTest {
|
||||
fun `present - start DM action complete scenario`() = runTest {
|
||||
val startDMAction = FakeStartDMAction()
|
||||
val presenter = createCreateRoomRootPresenter(startDMAction)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
|
||||
assertThat(initialState.startDmAction).isInstanceOf(Async.Uninitialized::class.java)
|
||||
assertThat(initialState.applicationName).isEqualTo(aBuildMeta().applicationName)
|
||||
assertThat(initialState.userListState.selectedUsers).isEmpty()
|
||||
assertThat(initialState.userListState.isSearchActive).isFalse()
|
||||
assertThat(initialState.userListState.isMultiSelectionEnabled).isFalse()
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - trigger create DM action`() = runTest {
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
val matrixUser = MatrixUser(UserId("@name:domain"))
|
||||
val createDmResult = Result.success(RoomId("!createDmResult:domain"))
|
||||
|
||||
fakeMatrixClient.givenFindDmResult(null)
|
||||
fakeMatrixClient.givenCreateDmResult(createDmResult)
|
||||
|
||||
initialState.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
assertThat(awaitItem().startDmAction).isInstanceOf(Async.Loading::class.java)
|
||||
val stateAfterStartDM = awaitItem()
|
||||
assertThat(stateAfterStartDM.startDmAction).isInstanceOf(Async.Success::class.java)
|
||||
assertThat(stateAfterStartDM.startDmAction.dataOrNull()).isEqualTo(createDmResult.getOrNull())
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - creating a DM records analytics event`() = runTest {
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
val matrixUser = MatrixUser(UserId("@name:domain"))
|
||||
val createDmResult = Result.success(RoomId("!createDmResult:domain"))
|
||||
|
||||
fakeMatrixClient.givenFindDmResult(null)
|
||||
fakeMatrixClient.givenCreateDmResult(createDmResult)
|
||||
|
||||
initialState.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
skipItems(2)
|
||||
|
||||
val analyticsEvent = fakeAnalyticsService.capturedEvents.filterIsInstance<CreatedRoom>().firstOrNull()
|
||||
assertThat(analyticsEvent).isNotNull()
|
||||
assertThat(analyticsEvent?.isDM).isTrue()
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - trigger retrieve DM action`() = runTest {
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
val matrixUser = MatrixUser(UserId("@name:domain"))
|
||||
val fakeDmResult = FakeMatrixRoom(roomId = RoomId("!fakeDmResult:domain"))
|
||||
|
||||
fakeMatrixClient.givenFindDmResult(fakeDmResult)
|
||||
|
||||
initialState.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
val stateAfterStartDM = awaitItem()
|
||||
assertThat(stateAfterStartDM.startDmAction).isInstanceOf(Async.Success::class.java)
|
||||
assertThat(stateAfterStartDM.startDmAction.dataOrNull()).isEqualTo(fakeDmResult.roomId)
|
||||
assertThat(fakeAnalyticsService.capturedEvents.filterIsInstance<CreatedRoom>()).isEmpty()
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - trigger retry create DM action`() = runTest {
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
val matrixUser = MatrixUser(UserId("@name:domain"))
|
||||
val createDmResult = Result.success(RoomId("!createDmResult:domain"))
|
||||
fakeUserListPresenter.givenState(aUserListState().copy(selectedUsers = persistentListOf(matrixUser)))
|
||||
|
||||
fakeMatrixClient.givenFindDmResult(null)
|
||||
fakeMatrixClient.givenCreateDmError(A_THROWABLE)
|
||||
fakeMatrixClient.givenCreateDmResult(createDmResult)
|
||||
val startDMSuccessResult = Async.Success(A_ROOM_ID)
|
||||
val startDMFailureResult = Async.Failure<RoomId>(StartDMResult.Failure(A_FAILURE_REASON))
|
||||
|
||||
// Failure
|
||||
startDMAction.givenExecuteResult(startDMFailureResult)
|
||||
initialState.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
assertThat(awaitItem().startDmAction).isInstanceOf(Async.Loading::class.java)
|
||||
val stateAfterStartDM = awaitItem()
|
||||
assertThat(stateAfterStartDM.startDmAction).isInstanceOf(Async.Failure::class.java)
|
||||
assertThat(fakeAnalyticsService.capturedEvents.filterIsInstance<CreatedRoom>()).isEmpty()
|
||||
awaitItem().also { state ->
|
||||
assertThat(state.startDmAction).isEqualTo(startDMFailureResult)
|
||||
state.eventSink(CreateRoomRootEvents.CancelStartDM)
|
||||
}
|
||||
|
||||
// Cancel
|
||||
stateAfterStartDM.eventSink(CreateRoomRootEvents.CancelStartDM)
|
||||
val stateAfterCancel = awaitItem()
|
||||
assertThat(stateAfterCancel.startDmAction).isInstanceOf(Async.Uninitialized::class.java)
|
||||
|
||||
// Failure
|
||||
stateAfterCancel.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
// Success
|
||||
startDMAction.givenExecuteResult(startDMSuccessResult)
|
||||
awaitItem().also { state ->
|
||||
assertThat(state.startDmAction).isEqualTo(Async.Uninitialized)
|
||||
state.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
}
|
||||
assertThat(awaitItem().startDmAction).isInstanceOf(Async.Loading::class.java)
|
||||
val stateAfterSecondAttempt = awaitItem()
|
||||
assertThat(stateAfterSecondAttempt.startDmAction).isInstanceOf(Async.Failure::class.java)
|
||||
assertThat(fakeAnalyticsService.capturedEvents.filterIsInstance<CreatedRoom>()).isEmpty()
|
||||
awaitItem().also { state ->
|
||||
assertThat(state.startDmAction).isEqualTo(startDMSuccessResult)
|
||||
}
|
||||
|
||||
// Retry with success
|
||||
fakeMatrixClient.givenCreateDmError(null)
|
||||
stateAfterSecondAttempt.eventSink(CreateRoomRootEvents.StartDM(matrixUser))
|
||||
assertThat(awaitItem().startDmAction).isInstanceOf(Async.Loading::class.java)
|
||||
val stateAfterRetryStartDM = awaitItem()
|
||||
assertThat(stateAfterRetryStartDM.startDmAction).isInstanceOf(Async.Success::class.java)
|
||||
assertThat(stateAfterRetryStartDM.startDmAction.dataOrNull()).isEqualTo(createDmResult.getOrNull())
|
||||
}
|
||||
}
|
||||
|
||||
private fun createCreateRoomRootPresenter(
|
||||
startDMAction: StartDMAction = FakeStartDMAction(),
|
||||
): CreateRoomRootPresenter {
|
||||
return CreateRoomRootPresenter(
|
||||
presenterFactory = FakeUserListPresenterFactory(FakeUserListPresenter()),
|
||||
userRepository = FakeUserRepository(),
|
||||
userListDataStore = UserListDataStore(),
|
||||
startDMAction = startDMAction,
|
||||
buildMeta = aBuildMeta(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
32
features/createroom/test/build.gradle.kts
Normal file
32
features/createroom/test/build.gradle.kts
Normal file
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
* Copyright (c) 2022 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
plugins {
|
||||
id("io.element.android-compose-library")
|
||||
}
|
||||
|
||||
android {
|
||||
namespace = "io.element.android.features.createroom.test"
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation(libs.coroutines.core)
|
||||
implementation(projects.libraries.matrix.api)
|
||||
implementation(projects.libraries.matrix.test)
|
||||
implementation(projects.tests.testutils)
|
||||
implementation(projects.libraries.architecture)
|
||||
api(projects.features.createroom.api)
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
/*
|
||||
* Copyright (c) 2023 New Vector Ltd
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package io.element.android.features.createroom.test
|
||||
|
||||
import androidx.compose.runtime.MutableState
|
||||
import io.element.android.features.createroom.api.StartDMAction
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
import io.element.android.libraries.matrix.api.core.UserId
|
||||
import io.element.android.libraries.matrix.test.A_ROOM_ID
|
||||
import io.element.android.tests.testutils.simulateLongTask
|
||||
|
||||
class FakeStartDMAction : StartDMAction {
|
||||
|
||||
private var executeResult: Async<RoomId> = Async.Success(A_ROOM_ID)
|
||||
|
||||
fun givenExecuteResult(result: Async<RoomId>) {
|
||||
executeResult = result
|
||||
}
|
||||
|
||||
override suspend fun execute(userId: UserId, actionState: MutableState<Async<RoomId>>) = simulateLongTask {
|
||||
actionState.value = Async.Loading()
|
||||
actionState.value = executeResult
|
||||
}
|
||||
}
|
||||
@@ -68,6 +68,7 @@ dependencies {
|
||||
testImplementation(projects.libraries.featureflag.test)
|
||||
testImplementation(projects.tests.testutils)
|
||||
testImplementation(projects.features.leaveroom.test)
|
||||
testImplementation(projects.features.createroom.test)
|
||||
|
||||
ksp(libs.showkase.processor)
|
||||
}
|
||||
|
||||
@@ -25,16 +25,13 @@ import androidx.compose.runtime.produceState
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.rememberCoroutineScope
|
||||
import androidx.compose.runtime.setValue
|
||||
import com.squareup.anvil.annotations.ContributesBinding
|
||||
import dagger.assisted.Assisted
|
||||
import dagger.assisted.AssistedFactory
|
||||
import dagger.assisted.AssistedInject
|
||||
import io.element.android.features.createroom.api.StartDMAction
|
||||
import io.element.android.features.roomdetails.impl.members.details.RoomMemberDetailsState.ConfirmationDialog
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.architecture.Presenter
|
||||
import io.element.android.libraries.core.bool.orFalse
|
||||
import io.element.android.libraries.di.RoomScope
|
||||
import io.element.android.libraries.matrix.api.MatrixClient
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
import io.element.android.libraries.matrix.api.core.UserId
|
||||
|
||||
@@ -28,6 +28,7 @@ open class RoomMemberDetailsStateProvider : PreviewParameterProvider<RoomMemberD
|
||||
aRoomMemberDetailsState().copy(displayConfirmationDialog = RoomMemberDetailsState.ConfirmationDialog.Block),
|
||||
aRoomMemberDetailsState().copy(displayConfirmationDialog = RoomMemberDetailsState.ConfirmationDialog.Unblock),
|
||||
aRoomMemberDetailsState().copy(isBlocked = Async.Loading(true)),
|
||||
aRoomMemberDetailsState().copy(startDmActionState = Async.Loading()),
|
||||
// Add other states here
|
||||
)
|
||||
}
|
||||
|
||||
@@ -30,6 +30,7 @@ import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.tooling.preview.PreviewParameter
|
||||
import androidx.compose.ui.unit.dp
|
||||
import io.element.android.compound.tokens.generated.CompoundIcons
|
||||
import io.element.android.features.roomdetails.impl.R
|
||||
import io.element.android.features.roomdetails.impl.blockuser.BlockUserDialogs
|
||||
import io.element.android.features.roomdetails.impl.blockuser.BlockUserSection
|
||||
import io.element.android.libraries.designsystem.components.async.AsyncView
|
||||
@@ -91,7 +92,7 @@ fun RoomMemberDetailsView(
|
||||
async = state.startDmActionState,
|
||||
progressText = stringResource(CommonStrings.common_starting_chat),
|
||||
onSuccess = onDMStarted,
|
||||
errorMessage = { stringResource(CommonStrings.common_error) },
|
||||
errorMessage = { stringResource(R.string.screen_start_chat_error_starting_chat) },
|
||||
onRetry = { state.eventSink(RoomMemberDetailsEvents.StartDM) },
|
||||
onErrorDismiss = { state.eventSink(RoomMemberDetailsEvents.ClearStartDMState) },
|
||||
)
|
||||
|
||||
@@ -38,6 +38,7 @@
|
||||
<string name="screen_room_notification_settings_mentions_only_disclaimer">"Your homeserver does not support this option in encrypted rooms, you won\'t get notified in this room."</string>
|
||||
<string name="screen_room_notification_settings_mode_all_messages">"All messages"</string>
|
||||
<string name="screen_room_notification_settings_room_custom_settings_title">"In this room, notify me for"</string>
|
||||
<string name="screen_start_chat_error_starting_chat">"An error occurred when trying to start a chat"</string>
|
||||
<string name="screen_dm_details_block_alert_action">"Block"</string>
|
||||
<string name="screen_dm_details_block_alert_description">"Blocked users won\'t be able to send you messages and all their messages will be hidden. You can unblock them anytime."</string>
|
||||
<string name="screen_dm_details_block_user">"Block user"</string>
|
||||
|
||||
@@ -20,6 +20,7 @@ import app.cash.molecule.RecompositionMode
|
||||
import app.cash.molecule.moleculeFlow
|
||||
import app.cash.turbine.test
|
||||
import com.google.common.truth.Truth.assertThat
|
||||
import io.element.android.features.createroom.test.FakeStartDMAction
|
||||
import io.element.android.features.leaveroom.api.LeaveRoomEvent
|
||||
import io.element.android.features.leaveroom.api.LeaveRoomPresenter
|
||||
import io.element.android.features.leaveroom.fake.FakeLeaveRoomPresenter
|
||||
@@ -45,10 +46,11 @@ import io.element.android.libraries.matrix.test.A_USER_ID_2
|
||||
import io.element.android.libraries.matrix.test.FakeMatrixClient
|
||||
import io.element.android.libraries.matrix.test.notificationsettings.FakeNotificationSettingsService
|
||||
import io.element.android.libraries.matrix.test.room.FakeMatrixRoom
|
||||
import io.element.android.tests.testutils.WarmUpRule
|
||||
import io.element.android.tests.testutils.consumeItemsUntilPredicate
|
||||
import io.element.android.tests.testutils.testCoroutineDispatchers
|
||||
import io.element.android.tests.testutils.WarmUpRule
|
||||
import kotlinx.coroutines.ExperimentalCoroutinesApi
|
||||
import kotlinx.coroutines.test.TestScope
|
||||
import kotlinx.coroutines.test.runTest
|
||||
import org.junit.Rule
|
||||
import org.junit.Test
|
||||
@@ -60,16 +62,16 @@ class RoomDetailsPresenterTests {
|
||||
@get:Rule
|
||||
val warmUpRule = WarmUpRule()
|
||||
|
||||
private fun createRoomDetailsPresenter(
|
||||
private fun TestScope.createRoomDetailsPresenter(
|
||||
room: MatrixRoom,
|
||||
leaveRoomPresenter: LeaveRoomPresenter = FakeLeaveRoomPresenter(),
|
||||
dispatchers: CoroutineDispatchers,
|
||||
dispatchers: CoroutineDispatchers = testCoroutineDispatchers(),
|
||||
notificationSettingsService: FakeNotificationSettingsService = FakeNotificationSettingsService()
|
||||
): RoomDetailsPresenter {
|
||||
val matrixClient = FakeMatrixClient(notificationSettingsService = notificationSettingsService)
|
||||
val roomMemberDetailsPresenterFactory = object : RoomMemberDetailsPresenter.Factory {
|
||||
override fun create(roomMemberId: UserId): RoomMemberDetailsPresenter {
|
||||
return RoomMemberDetailsPresenter(matrixClient, room, roomMemberId)
|
||||
return RoomMemberDetailsPresenter(roomMemberId, matrixClient, room, FakeStartDMAction())
|
||||
}
|
||||
}
|
||||
val featureFlagService = FakeFeatureFlagService(
|
||||
@@ -89,7 +91,7 @@ class RoomDetailsPresenterTests {
|
||||
@Test
|
||||
fun `present - initial state is created from room info`() = runTest {
|
||||
val room = aMatrixRoom()
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -108,7 +110,7 @@ class RoomDetailsPresenterTests {
|
||||
@Test
|
||||
fun `present - initial state with no room name`() = runTest {
|
||||
val room = aMatrixRoom(name = null)
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -130,7 +132,7 @@ class RoomDetailsPresenterTests {
|
||||
val roomMembers = listOf(myRoomMember, otherRoomMember)
|
||||
givenRoomMembersState(MatrixRoomMembersState.Ready(roomMembers))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -164,7 +166,7 @@ class RoomDetailsPresenterTests {
|
||||
val room = aMatrixRoom().apply {
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -179,7 +181,7 @@ class RoomDetailsPresenterTests {
|
||||
val room = aMatrixRoom().apply {
|
||||
givenCanInviteResult(Result.failure(Throwable("Whoops")))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -197,7 +199,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanSendStateResult(StateEventType.ROOM_AVATAR, Result.failure(Throwable("Whelp")))
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -226,7 +228,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanSendStateResult(StateEventType.ROOM_AVATAR, Result.success(true))
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -241,6 +243,7 @@ class RoomDetailsPresenterTests {
|
||||
cancelAndIgnoreRemainingEvents()
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - initial state when in a DM with no topic`() = runTest {
|
||||
val myRoomMember = aRoomMember(A_SESSION_ID)
|
||||
@@ -255,7 +258,7 @@ class RoomDetailsPresenterTests {
|
||||
|
||||
givenCanSendStateResult(StateEventType.ROOM_TOPIC, Result.success(true))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -276,7 +279,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanSendStateResult(StateEventType.ROOM_AVATAR, Result.success(true))
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -297,7 +300,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanSendStateResult(StateEventType.ROOM_AVATAR, Result.success(false))
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -315,7 +318,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -333,7 +336,7 @@ class RoomDetailsPresenterTests {
|
||||
givenCanInviteResult(Result.success(false))
|
||||
}
|
||||
|
||||
val presenter = createRoomDetailsPresenter(room, dispatchers = testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(room)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -351,7 +354,11 @@ class RoomDetailsPresenterTests {
|
||||
fun `present - leave room event is passed on to leave room presenter`() = runTest {
|
||||
val leaveRoomPresenter = FakeLeaveRoomPresenter()
|
||||
val room = aMatrixRoom()
|
||||
val presenter = createRoomDetailsPresenter(room, leaveRoomPresenter, testCoroutineDispatchers())
|
||||
val presenter = createRoomDetailsPresenter(
|
||||
room = room,
|
||||
leaveRoomPresenter = leaveRoomPresenter,
|
||||
dispatchers = testCoroutineDispatchers()
|
||||
)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -368,14 +375,18 @@ class RoomDetailsPresenterTests {
|
||||
val leaveRoomPresenter = FakeLeaveRoomPresenter()
|
||||
val notificationSettingsService = FakeNotificationSettingsService()
|
||||
val room = aMatrixRoom(notificationSettingsService = notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(room, leaveRoomPresenter, testCoroutineDispatchers(), notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(
|
||||
room = room,
|
||||
leaveRoomPresenter = leaveRoomPresenter,
|
||||
notificationSettingsService = notificationSettingsService,
|
||||
)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
|
||||
notificationSettingsService.setRoomNotificationMode(room.roomId, RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY)
|
||||
val updatedState = consumeItemsUntilPredicate {
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY
|
||||
}.last()
|
||||
assertThat(updatedState.roomNotificationSettings?.mode).isEqualTo(RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY)
|
||||
cancelAndIgnoreRemainingEvents()
|
||||
@@ -384,16 +395,15 @@ class RoomDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - mute room notifications`() = runTest {
|
||||
val leaveRoomPresenter = FakeLeaveRoomPresenter()
|
||||
val notificationSettingsService = FakeNotificationSettingsService(initialRoomMode = RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY)
|
||||
val room = aMatrixRoom(notificationSettingsService = notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(room, leaveRoomPresenter, testCoroutineDispatchers(), notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(room = room, notificationSettingsService = notificationSettingsService)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
awaitItem().eventSink(RoomDetailsEvent.MuteNotification)
|
||||
val updatedState = consumeItemsUntilPredicate(timeout = 250.milliseconds) {
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.MUTE
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.MUTE
|
||||
}.last()
|
||||
assertThat(updatedState.roomNotificationSettings?.mode).isEqualTo(RoomNotificationMode.MUTE)
|
||||
cancelAndIgnoreRemainingEvents()
|
||||
@@ -402,19 +412,18 @@ class RoomDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - unmute room notifications`() = runTest {
|
||||
val leaveRoomPresenter = FakeLeaveRoomPresenter()
|
||||
val notificationSettingsService = FakeNotificationSettingsService(
|
||||
initialRoomMode = RoomNotificationMode.MENTIONS_AND_KEYWORDS_ONLY,
|
||||
initialEncryptedGroupDefaultMode = RoomNotificationMode.ALL_MESSAGES
|
||||
)
|
||||
val room = aMatrixRoom(notificationSettingsService = notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(room, leaveRoomPresenter, testCoroutineDispatchers(), notificationSettingsService)
|
||||
val presenter = createRoomDetailsPresenter(room = room, notificationSettingsService = notificationSettingsService)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
awaitItem().eventSink(RoomDetailsEvent.UnmuteNotification)
|
||||
val updatedState = consumeItemsUntilPredicate {
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.ALL_MESSAGES
|
||||
it.roomNotificationSettings?.mode == RoomNotificationMode.ALL_MESSAGES
|
||||
}.last()
|
||||
assertThat(updatedState.roomNotificationSettings?.mode).isEqualTo(RoomNotificationMode.ALL_MESSAGES)
|
||||
cancelAndIgnoreRemainingEvents()
|
||||
|
||||
@@ -20,13 +20,22 @@ import app.cash.molecule.RecompositionMode
|
||||
import app.cash.molecule.moleculeFlow
|
||||
import app.cash.turbine.test
|
||||
import com.google.common.truth.Truth
|
||||
import io.element.android.features.createroom.api.StartDMAction
|
||||
import io.element.android.features.createroom.test.FakeStartDMAction
|
||||
import io.element.android.features.roomdetails.aMatrixRoom
|
||||
import io.element.android.features.roomdetails.impl.members.aRoomMember
|
||||
import io.element.android.features.roomdetails.impl.members.details.RoomMemberDetailsEvents
|
||||
import io.element.android.features.roomdetails.impl.members.details.RoomMemberDetailsPresenter
|
||||
import io.element.android.features.roomdetails.impl.members.details.RoomMemberDetailsState
|
||||
import io.element.android.libraries.architecture.Async
|
||||
import io.element.android.libraries.matrix.api.MatrixClient
|
||||
import io.element.android.libraries.matrix.api.core.RoomId
|
||||
import io.element.android.libraries.matrix.api.room.MatrixRoom
|
||||
import io.element.android.libraries.matrix.api.room.MatrixRoomMembersState
|
||||
import io.element.android.libraries.matrix.api.room.RoomMember
|
||||
import io.element.android.libraries.matrix.api.room.StartDMResult
|
||||
import io.element.android.libraries.matrix.test.A_FAILURE_REASON
|
||||
import io.element.android.libraries.matrix.test.A_ROOM_ID
|
||||
import io.element.android.libraries.matrix.test.A_THROWABLE
|
||||
import io.element.android.libraries.matrix.test.FakeMatrixClient
|
||||
import io.element.android.tests.testutils.WarmUpRule
|
||||
@@ -49,7 +58,10 @@ class RoomMemberDetailsPresenterTests {
|
||||
givenUserAvatarUrlResult(Result.success("A custom avatar"))
|
||||
givenRoomMembersState(MatrixRoomMembersState.Ready(listOf(roomMember)))
|
||||
}
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter(
|
||||
room = room,
|
||||
roomMember = roomMember
|
||||
)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -73,7 +85,10 @@ class RoomMemberDetailsPresenterTests {
|
||||
givenUserAvatarUrlResult(Result.failure(Throwable()))
|
||||
givenRoomMembersState(MatrixRoomMembersState.Ready(listOf(roomMember)))
|
||||
}
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter(
|
||||
room = room,
|
||||
roomMember = roomMember
|
||||
)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -93,7 +108,10 @@ class RoomMemberDetailsPresenterTests {
|
||||
givenUserAvatarUrlResult(Result.success(null))
|
||||
givenRoomMembersState(MatrixRoomMembersState.Ready(listOf(roomMember)))
|
||||
}
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter(
|
||||
room = room,
|
||||
roomMember = roomMember
|
||||
)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -107,9 +125,7 @@ class RoomMemberDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - BlockUser needing confirmation displays confirmation dialog`() = runTest {
|
||||
val room = aMatrixRoom()
|
||||
val roomMember = aRoomMember()
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter()
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -128,9 +144,7 @@ class RoomMemberDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - BlockUser and UnblockUser without confirmation change the 'blocked' state`() = runTest {
|
||||
val room = aMatrixRoom()
|
||||
val roomMember = aRoomMember()
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter()
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -147,11 +161,9 @@ class RoomMemberDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - BlockUser with error`() = runTest {
|
||||
val room = aMatrixRoom()
|
||||
val roomMember = aRoomMember()
|
||||
val matrixClient = FakeMatrixClient()
|
||||
matrixClient.givenIgnoreUserResult(Result.failure(A_THROWABLE))
|
||||
val presenter = RoomMemberDetailsPresenter(matrixClient, room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter(client = matrixClient)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -168,9 +180,7 @@ class RoomMemberDetailsPresenterTests {
|
||||
|
||||
@Test
|
||||
fun `present - UnblockUser needing confirmation displays confirmation dialog`() = runTest {
|
||||
val room = aMatrixRoom()
|
||||
val roomMember = aRoomMember()
|
||||
val presenter = RoomMemberDetailsPresenter(FakeMatrixClient(), room, roomMember.userId)
|
||||
val presenter = createRoomMemberDetailsPresenter()
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
@@ -186,4 +196,52 @@ class RoomMemberDetailsPresenterTests {
|
||||
ensureAllEventsConsumed()
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `present - start DM action complete scenario`() = runTest {
|
||||
val startDMAction = FakeStartDMAction()
|
||||
val presenter = createRoomMemberDetailsPresenter(startDMAction = startDMAction)
|
||||
moleculeFlow(RecompositionMode.Immediate) {
|
||||
presenter.present()
|
||||
}.test {
|
||||
val initialState = awaitItem()
|
||||
Truth.assertThat(initialState.startDmActionState).isInstanceOf(Async.Uninitialized::class.java)
|
||||
val startDMSuccessResult = Async.Success(A_ROOM_ID)
|
||||
val startDMFailureResult = Async.Failure<RoomId>(StartDMResult.Failure(A_FAILURE_REASON))
|
||||
|
||||
// Failure
|
||||
startDMAction.givenExecuteResult(startDMFailureResult)
|
||||
initialState.eventSink(RoomMemberDetailsEvents.StartDM)
|
||||
Truth.assertThat(awaitItem().startDmActionState).isInstanceOf(Async.Loading::class.java)
|
||||
awaitItem().also { state ->
|
||||
Truth.assertThat(state.startDmActionState).isEqualTo(startDMFailureResult)
|
||||
state.eventSink(RoomMemberDetailsEvents.ClearStartDMState)
|
||||
}
|
||||
|
||||
// Success
|
||||
startDMAction.givenExecuteResult(startDMSuccessResult)
|
||||
awaitItem().also { state ->
|
||||
Truth.assertThat(state.startDmActionState).isEqualTo(Async.Uninitialized)
|
||||
state.eventSink(RoomMemberDetailsEvents.StartDM)
|
||||
}
|
||||
Truth.assertThat(awaitItem().startDmActionState).isInstanceOf(Async.Loading::class.java)
|
||||
awaitItem().also { state ->
|
||||
Truth.assertThat(state.startDmActionState).isEqualTo(startDMSuccessResult)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private fun createRoomMemberDetailsPresenter(
|
||||
client: MatrixClient = FakeMatrixClient(),
|
||||
room: MatrixRoom = aMatrixRoom(),
|
||||
roomMember: RoomMember = aRoomMember(),
|
||||
startDMAction: StartDMAction = FakeStartDMAction()
|
||||
): RoomMemberDetailsPresenter {
|
||||
return RoomMemberDetailsPresenter(
|
||||
roomMemberId = roomMember.userId,
|
||||
client = client,
|
||||
room = room,
|
||||
startDMAction = startDMAction
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,7 +41,7 @@ interface MatrixClient : Closeable {
|
||||
val roomListService: RoomListService
|
||||
val mediaLoader: MatrixMediaLoader
|
||||
suspend fun getRoom(roomId: RoomId): MatrixRoom?
|
||||
suspend fun findDM(userId: UserId): MatrixRoom?
|
||||
suspend fun findDM(userId: UserId): RoomId?
|
||||
suspend fun ignoreUser(userId: UserId): Result<Unit>
|
||||
suspend fun unignoreUser(userId: UserId): Result<Unit>
|
||||
suspend fun createRoom(createRoomParams: CreateRoomParameters): Result<RoomId>
|
||||
|
||||
@@ -24,11 +24,9 @@ import io.element.android.libraries.matrix.api.core.UserId
|
||||
* Try to find an existing DM with the given user, or create one if none exists.
|
||||
*/
|
||||
suspend fun MatrixClient.startDM(userId: UserId): StartDMResult {
|
||||
val existingRoomId = findDM(userId)?.use { existingDM ->
|
||||
existingDM.roomId
|
||||
}
|
||||
return if (existingRoomId != null) {
|
||||
StartDMResult.Success(existingRoomId, isNew = false)
|
||||
val existingDM = findDM(userId)
|
||||
return if (existingDM != null) {
|
||||
StartDMResult.Success(existingDM, isNew = false)
|
||||
} else {
|
||||
createDM(userId).fold(
|
||||
{ StartDMResult.Success(it, isNew = true) },
|
||||
|
||||
@@ -240,9 +240,8 @@ class RustMatrixClient constructor(
|
||||
}
|
||||
}
|
||||
|
||||
override suspend fun findDM(userId: UserId): MatrixRoom? {
|
||||
val roomId = client.getDmRoom(userId.value)?.use { RoomId(it.id()) }
|
||||
return roomId?.let { getRoom(it) }
|
||||
override suspend fun findDM(userId: UserId): RoomId? {
|
||||
return client.getDmRoom(userId.value)?.use { RoomId(it.id()) }
|
||||
}
|
||||
|
||||
override suspend fun ignoreUser(userId: UserId): Result<Unit> = withContext(sessionDispatcher) {
|
||||
|
||||
@@ -39,7 +39,6 @@ import io.element.android.libraries.matrix.test.media.FakeMediaLoader
|
||||
import io.element.android.libraries.matrix.test.notification.FakeNotificationService
|
||||
import io.element.android.libraries.matrix.test.notificationsettings.FakeNotificationSettingsService
|
||||
import io.element.android.libraries.matrix.test.pushers.FakePushersService
|
||||
import io.element.android.libraries.matrix.test.room.FakeMatrixRoom
|
||||
import io.element.android.libraries.matrix.test.roomlist.FakeRoomListService
|
||||
import io.element.android.libraries.matrix.test.sync.FakeSyncService
|
||||
import io.element.android.libraries.matrix.test.verification.FakeSessionVerificationService
|
||||
@@ -72,8 +71,7 @@ class FakeMatrixClient(
|
||||
private var unignoreUserResult: Result<Unit> = Result.success(Unit)
|
||||
private var createRoomResult: Result<RoomId> = Result.success(A_ROOM_ID)
|
||||
private var createDmResult: Result<RoomId> = Result.success(A_ROOM_ID)
|
||||
private var createDmFailure: Throwable? = null
|
||||
private var findDmResult: MatrixRoom? = FakeMatrixRoom()
|
||||
private var findDmResult: RoomId? = A_ROOM_ID
|
||||
private var logoutFailure: Throwable? = null
|
||||
private val getRoomResults = mutableMapOf<RoomId, MatrixRoom>()
|
||||
private val searchUserResults = mutableMapOf<String, Result<MatrixSearchUserResults>>()
|
||||
@@ -87,7 +85,7 @@ class FakeMatrixClient(
|
||||
return getRoomResults[roomId]
|
||||
}
|
||||
|
||||
override suspend fun findDM(userId: UserId): MatrixRoom? {
|
||||
override suspend fun findDM(userId: UserId): RoomId? {
|
||||
return findDmResult
|
||||
}
|
||||
|
||||
@@ -99,14 +97,11 @@ class FakeMatrixClient(
|
||||
return unignoreUserResult
|
||||
}
|
||||
|
||||
override suspend fun createRoom(createRoomParams: CreateRoomParameters): Result<RoomId> {
|
||||
delay(100)
|
||||
override suspend fun createRoom(createRoomParams: CreateRoomParameters): Result<RoomId> = simulateLongTask {
|
||||
return createRoomResult
|
||||
}
|
||||
|
||||
override suspend fun createDM(userId: UserId): Result<RoomId> {
|
||||
delay(100)
|
||||
createDmFailure?.let { throw it }
|
||||
override suspend fun createDM(userId: UserId): Result<RoomId> = simulateLongTask {
|
||||
return createDmResult
|
||||
}
|
||||
|
||||
@@ -206,11 +201,7 @@ class FakeMatrixClient(
|
||||
unignoreUserResult = result
|
||||
}
|
||||
|
||||
fun givenCreateDmError(failure: Throwable?) {
|
||||
createDmFailure = failure
|
||||
}
|
||||
|
||||
fun givenFindDmResult(result: MatrixRoom?) {
|
||||
fun givenFindDmResult(result: RoomId?) {
|
||||
findDmResult = result
|
||||
}
|
||||
|
||||
|
||||
@@ -82,9 +82,9 @@ includeProjects(File(rootDir, "services"), ":services")
|
||||
|
||||
// Uncomment to include the compound-android module as a local dependency so you can work on it locally.
|
||||
// You will also need to clone it in the specified folder.
|
||||
//includeBuild("checkouts/compound-android") {
|
||||
// includeBuild("checkouts/compound-android") {
|
||||
// dependencySubstitution {
|
||||
// // substitute remote dependency with local module
|
||||
// substitute(module("io.element.android:compound-android")).using(project(":compound"))
|
||||
// }
|
||||
//}
|
||||
// }
|
||||
|
||||
@@ -115,7 +115,8 @@
|
||||
"screen_room_member_list_.*",
|
||||
"screen_dm_details_.*",
|
||||
"screen_room_notification_settings_.*",
|
||||
"screen_notification_settings_edit_failed_updating_default_mode"
|
||||
"screen_notification_settings_edit_failed_updating_default_mode",
|
||||
"screen_start_chat_error_starting_chat"
|
||||
]
|
||||
},
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user