mirror of
https://github.com/element-hq/element-android
synced 2024-11-27 11:59:12 +03:00
Merge pull request #7276 from vector-im/feature/mna/device-manager-account-data
[Device Management] Save matrix_client_information events on login/registration (PSG-769, PSG-771)
This commit is contained in:
commit
6626732b3b
23 changed files with 820 additions and 25 deletions
1
changelog.d/7257.wip
Normal file
1
changelog.d/7257.wip
Normal file
|
@ -0,0 +1 @@
|
||||||
|
[Device Management] Save "matrix_client_information" events on login/registration
|
|
@ -66,7 +66,7 @@ internal class DefaultSessionAccountDataService @Inject constructor(
|
||||||
|
|
||||||
override suspend fun updateUserAccountData(type: String, content: Content) {
|
override suspend fun updateUserAccountData(type: String, content: Content) {
|
||||||
val params = UpdateUserAccountDataTask.AnyParams(type = type, any = content)
|
val params = UpdateUserAccountDataTask.AnyParams(type = type, any = content)
|
||||||
awaitCallback<Unit> { callback ->
|
awaitCallback { callback ->
|
||||||
updateUserAccountDataTask.configureWith(params) {
|
updateUserAccountDataTask.configureWith(params) {
|
||||||
this.retryCount = 5 // TODO Need to refactor retrying out into a helper method.
|
this.retryCount = 5 // TODO Need to refactor retrying out into a helper method.
|
||||||
this.callback = callback
|
this.callback = callback
|
||||||
|
|
|
@ -19,10 +19,10 @@ package im.vector.app.core.di
|
||||||
import android.content.Context
|
import android.content.Context
|
||||||
import arrow.core.Option
|
import arrow.core.Option
|
||||||
import im.vector.app.ActiveSessionDataSource
|
import im.vector.app.ActiveSessionDataSource
|
||||||
import im.vector.app.core.extensions.configureAndStart
|
|
||||||
import im.vector.app.core.extensions.startSyncing
|
import im.vector.app.core.extensions.startSyncing
|
||||||
import im.vector.app.core.pushers.UnifiedPushHelper
|
import im.vector.app.core.pushers.UnifiedPushHelper
|
||||||
import im.vector.app.core.services.GuardServiceStarter
|
import im.vector.app.core.services.GuardServiceStarter
|
||||||
|
import im.vector.app.core.session.ConfigureAndStartSessionUseCase
|
||||||
import im.vector.app.features.call.webrtc.WebRtcCallManager
|
import im.vector.app.features.call.webrtc.WebRtcCallManager
|
||||||
import im.vector.app.features.crypto.keysrequest.KeyRequestHandler
|
import im.vector.app.features.crypto.keysrequest.KeyRequestHandler
|
||||||
import im.vector.app.features.crypto.verification.IncomingVerificationRequestHandler
|
import im.vector.app.features.crypto.verification.IncomingVerificationRequestHandler
|
||||||
|
@ -50,6 +50,7 @@ class ActiveSessionHolder @Inject constructor(
|
||||||
private val sessionInitializer: SessionInitializer,
|
private val sessionInitializer: SessionInitializer,
|
||||||
private val applicationContext: Context,
|
private val applicationContext: Context,
|
||||||
private val authenticationService: AuthenticationService,
|
private val authenticationService: AuthenticationService,
|
||||||
|
private val configureAndStartSessionUseCase: ConfigureAndStartSessionUseCase,
|
||||||
) {
|
) {
|
||||||
|
|
||||||
private var activeSessionReference: AtomicReference<Session?> = AtomicReference()
|
private var activeSessionReference: AtomicReference<Session?> = AtomicReference()
|
||||||
|
@ -109,7 +110,9 @@ class ActiveSessionHolder @Inject constructor(
|
||||||
}
|
}
|
||||||
?: sessionInitializer.tryInitialize(readCurrentSession = { activeSessionReference.get() }) { session ->
|
?: sessionInitializer.tryInitialize(readCurrentSession = { activeSessionReference.get() }) { session ->
|
||||||
setActiveSession(session)
|
setActiveSession(session)
|
||||||
session.configureAndStart(applicationContext, startSyncing = startSync)
|
runBlocking {
|
||||||
|
configureAndStartSessionUseCase.execute(session, startSyncing = startSync)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -24,20 +24,8 @@ import im.vector.app.core.services.VectorSyncAndroidService
|
||||||
import im.vector.app.features.session.VectorSessionStore
|
import im.vector.app.features.session.VectorSessionStore
|
||||||
import org.matrix.android.sdk.api.session.Session
|
import org.matrix.android.sdk.api.session.Session
|
||||||
import org.matrix.android.sdk.api.session.crypto.keysbackup.KeysBackupState
|
import org.matrix.android.sdk.api.session.crypto.keysbackup.KeysBackupState
|
||||||
import org.matrix.android.sdk.api.session.sync.FilterService
|
|
||||||
import timber.log.Timber
|
import timber.log.Timber
|
||||||
|
|
||||||
fun Session.configureAndStart(context: Context, startSyncing: Boolean = true) {
|
|
||||||
Timber.i("Configure and start session for $myUserId. startSyncing: $startSyncing")
|
|
||||||
open()
|
|
||||||
filterService().setFilter(FilterService.FilterPreset.ElementFilter)
|
|
||||||
if (startSyncing) {
|
|
||||||
startSyncing(context)
|
|
||||||
}
|
|
||||||
pushersService().refreshPushers()
|
|
||||||
context.singletonEntryPoint().webRtcCallManager().checkForProtocolsSupportIfNeeded()
|
|
||||||
}
|
|
||||||
|
|
||||||
fun Session.startSyncing(context: Context) {
|
fun Session.startSyncing(context: Context) {
|
||||||
val applicationContext = context.applicationContext
|
val applicationContext = context.applicationContext
|
||||||
if (!syncService().hasAlreadySynced()) {
|
if (!syncService().hasAlreadySynced()) {
|
||||||
|
|
|
@ -0,0 +1,46 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session
|
||||||
|
|
||||||
|
import android.content.Context
|
||||||
|
import dagger.hilt.android.qualifiers.ApplicationContext
|
||||||
|
import im.vector.app.core.extensions.startSyncing
|
||||||
|
import im.vector.app.core.session.clientinfo.UpdateMatrixClientInfoUseCase
|
||||||
|
import im.vector.app.features.call.webrtc.WebRtcCallManager
|
||||||
|
import org.matrix.android.sdk.api.session.Session
|
||||||
|
import org.matrix.android.sdk.api.session.sync.FilterService
|
||||||
|
import timber.log.Timber
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
class ConfigureAndStartSessionUseCase @Inject constructor(
|
||||||
|
@ApplicationContext private val context: Context,
|
||||||
|
private val webRtcCallManager: WebRtcCallManager,
|
||||||
|
private val updateMatrixClientInfoUseCase: UpdateMatrixClientInfoUseCase,
|
||||||
|
) {
|
||||||
|
|
||||||
|
suspend fun execute(session: Session, startSyncing: Boolean = true) {
|
||||||
|
Timber.i("Configure and start session for ${session.myUserId}. startSyncing: $startSyncing")
|
||||||
|
session.open()
|
||||||
|
session.filterService().setFilter(FilterService.FilterPreset.ElementFilter)
|
||||||
|
if (startSyncing) {
|
||||||
|
session.startSyncing(context)
|
||||||
|
}
|
||||||
|
session.pushersService().refreshPushers()
|
||||||
|
webRtcCallManager.checkForProtocolsSupportIfNeeded()
|
||||||
|
updateMatrixClientInfoUseCase.execute(session)
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,34 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import org.matrix.android.sdk.api.session.Session
|
||||||
|
import org.matrix.android.sdk.api.session.events.model.toModel
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This use case retrieves the current account data event containing extended client info
|
||||||
|
* for a given deviceId.
|
||||||
|
*/
|
||||||
|
class GetMatrixClientInfoUseCase @Inject constructor() {
|
||||||
|
|
||||||
|
fun execute(session: Session, deviceId: String): MatrixClientInfoContent? {
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + deviceId
|
||||||
|
val content = session.accountDataService().getUserAccountDataEvent(type)?.content
|
||||||
|
return content.toModel()
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,33 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import com.squareup.moshi.Json
|
||||||
|
import com.squareup.moshi.JsonClass
|
||||||
|
|
||||||
|
@JsonClass(generateAdapter = true)
|
||||||
|
data class MatrixClientInfoContent(
|
||||||
|
// app name
|
||||||
|
@Json(name = "name")
|
||||||
|
val name: String? = null,
|
||||||
|
// app version
|
||||||
|
@Json(name = "version")
|
||||||
|
val version: String? = null,
|
||||||
|
// app url (optional, applicable only for web)
|
||||||
|
@Json(name = "url")
|
||||||
|
val url: String? = null,
|
||||||
|
)
|
|
@ -0,0 +1,19 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
class NoDeviceIdError : IllegalStateException("device id is empty")
|
|
@ -0,0 +1,22 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Prefix for the key account data event which holds client info.
|
||||||
|
*/
|
||||||
|
const val MATRIX_CLIENT_INFO_KEY_PREFIX = "io.element.matrix_client_information."
|
|
@ -0,0 +1,38 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import org.matrix.android.sdk.api.session.Session
|
||||||
|
import org.matrix.android.sdk.api.session.events.model.toContent
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This use case sets the account data event containing extended client info.
|
||||||
|
*/
|
||||||
|
class SetMatrixClientInfoUseCase @Inject constructor() {
|
||||||
|
|
||||||
|
suspend fun execute(session: Session, clientInfo: MatrixClientInfoContent): Result<Unit> = runCatching {
|
||||||
|
val deviceId = session.sessionParams.deviceId.orEmpty()
|
||||||
|
if (deviceId.isNotEmpty()) {
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + deviceId
|
||||||
|
session.accountDataService()
|
||||||
|
.updateUserAccountData(type, clientInfo.toContent())
|
||||||
|
} else {
|
||||||
|
throw NoDeviceIdError()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,52 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import im.vector.app.core.resources.AppNameProvider
|
||||||
|
import im.vector.app.core.resources.BuildMeta
|
||||||
|
import org.matrix.android.sdk.api.session.Session
|
||||||
|
import timber.log.Timber
|
||||||
|
import javax.inject.Inject
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This use case updates if needed the account data event containing extended client info.
|
||||||
|
*/
|
||||||
|
class UpdateMatrixClientInfoUseCase @Inject constructor(
|
||||||
|
private val appNameProvider: AppNameProvider,
|
||||||
|
private val buildMeta: BuildMeta,
|
||||||
|
private val getMatrixClientInfoUseCase: GetMatrixClientInfoUseCase,
|
||||||
|
private val setMatrixClientInfoUseCase: SetMatrixClientInfoUseCase,
|
||||||
|
) {
|
||||||
|
|
||||||
|
suspend fun execute(session: Session) = runCatching {
|
||||||
|
val clientInfo = MatrixClientInfoContent(
|
||||||
|
name = appNameProvider.getAppName(),
|
||||||
|
version = buildMeta.versionName
|
||||||
|
)
|
||||||
|
val deviceId = session.sessionParams.deviceId.orEmpty()
|
||||||
|
if (deviceId.isNotEmpty()) {
|
||||||
|
val storedClientInfo = getMatrixClientInfoUseCase.execute(session, deviceId)
|
||||||
|
Timber.d("storedClientInfo=$storedClientInfo, current client info=$clientInfo")
|
||||||
|
if (clientInfo != storedClientInfo) {
|
||||||
|
Timber.d("client info need to be updated")
|
||||||
|
return setMatrixClientInfoUseCase.execute(session, clientInfo)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
throw NoDeviceIdError()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -30,9 +30,9 @@ import im.vector.app.R
|
||||||
import im.vector.app.core.di.ActiveSessionHolder
|
import im.vector.app.core.di.ActiveSessionHolder
|
||||||
import im.vector.app.core.di.MavericksAssistedViewModelFactory
|
import im.vector.app.core.di.MavericksAssistedViewModelFactory
|
||||||
import im.vector.app.core.di.hiltMavericksViewModelFactory
|
import im.vector.app.core.di.hiltMavericksViewModelFactory
|
||||||
import im.vector.app.core.extensions.configureAndStart
|
|
||||||
import im.vector.app.core.platform.VectorViewModel
|
import im.vector.app.core.platform.VectorViewModel
|
||||||
import im.vector.app.core.resources.StringProvider
|
import im.vector.app.core.resources.StringProvider
|
||||||
|
import im.vector.app.core.session.ConfigureAndStartSessionUseCase
|
||||||
import im.vector.app.core.utils.ensureTrailingSlash
|
import im.vector.app.core.utils.ensureTrailingSlash
|
||||||
import kotlinx.coroutines.Job
|
import kotlinx.coroutines.Job
|
||||||
import kotlinx.coroutines.launch
|
import kotlinx.coroutines.launch
|
||||||
|
@ -64,7 +64,8 @@ class LoginViewModel @AssistedInject constructor(
|
||||||
private val homeServerConnectionConfigFactory: HomeServerConnectionConfigFactory,
|
private val homeServerConnectionConfigFactory: HomeServerConnectionConfigFactory,
|
||||||
private val reAuthHelper: ReAuthHelper,
|
private val reAuthHelper: ReAuthHelper,
|
||||||
private val stringProvider: StringProvider,
|
private val stringProvider: StringProvider,
|
||||||
private val homeServerHistoryService: HomeServerHistoryService
|
private val homeServerHistoryService: HomeServerHistoryService,
|
||||||
|
private val configureAndStartSessionUseCase: ConfigureAndStartSessionUseCase,
|
||||||
) : VectorViewModel<LoginViewState, LoginAction, LoginViewEvents>(initialState) {
|
) : VectorViewModel<LoginViewState, LoginAction, LoginViewEvents>(initialState) {
|
||||||
|
|
||||||
@AssistedFactory
|
@AssistedFactory
|
||||||
|
@ -732,7 +733,7 @@ class LoginViewModel @AssistedInject constructor(
|
||||||
activeSessionHolder.setActiveSession(session)
|
activeSessionHolder.setActiveSession(session)
|
||||||
|
|
||||||
authenticationService.reset()
|
authenticationService.reset()
|
||||||
session.configureAndStart(applicationContext)
|
configureAndStartSessionUseCase.execute(session)
|
||||||
setState {
|
setState {
|
||||||
copy(
|
copy(
|
||||||
asyncLoginAction = Success(Unit)
|
asyncLoginAction = Success(Unit)
|
||||||
|
|
|
@ -26,13 +26,13 @@ import im.vector.app.core.di.ActiveSessionHolder
|
||||||
import im.vector.app.core.di.MavericksAssistedViewModelFactory
|
import im.vector.app.core.di.MavericksAssistedViewModelFactory
|
||||||
import im.vector.app.core.di.hiltMavericksViewModelFactory
|
import im.vector.app.core.di.hiltMavericksViewModelFactory
|
||||||
import im.vector.app.core.extensions.cancelCurrentOnSet
|
import im.vector.app.core.extensions.cancelCurrentOnSet
|
||||||
import im.vector.app.core.extensions.configureAndStart
|
|
||||||
import im.vector.app.core.extensions.inferNoConnectivity
|
import im.vector.app.core.extensions.inferNoConnectivity
|
||||||
import im.vector.app.core.extensions.isMatrixId
|
import im.vector.app.core.extensions.isMatrixId
|
||||||
import im.vector.app.core.extensions.toReducedUrl
|
import im.vector.app.core.extensions.toReducedUrl
|
||||||
import im.vector.app.core.extensions.vectorStore
|
import im.vector.app.core.extensions.vectorStore
|
||||||
import im.vector.app.core.platform.VectorViewModel
|
import im.vector.app.core.platform.VectorViewModel
|
||||||
import im.vector.app.core.resources.StringProvider
|
import im.vector.app.core.resources.StringProvider
|
||||||
|
import im.vector.app.core.session.ConfigureAndStartSessionUseCase
|
||||||
import im.vector.app.core.utils.ensureProtocol
|
import im.vector.app.core.utils.ensureProtocol
|
||||||
import im.vector.app.core.utils.ensureTrailingSlash
|
import im.vector.app.core.utils.ensureTrailingSlash
|
||||||
import im.vector.app.features.VectorFeatures
|
import im.vector.app.features.VectorFeatures
|
||||||
|
@ -91,6 +91,7 @@ class OnboardingViewModel @AssistedInject constructor(
|
||||||
private val vectorOverrides: VectorOverrides,
|
private val vectorOverrides: VectorOverrides,
|
||||||
private val registrationActionHandler: RegistrationActionHandler,
|
private val registrationActionHandler: RegistrationActionHandler,
|
||||||
private val sdkIntProvider: BuildVersionSdkIntProvider,
|
private val sdkIntProvider: BuildVersionSdkIntProvider,
|
||||||
|
private val configureAndStartSessionUseCase: ConfigureAndStartSessionUseCase,
|
||||||
) : VectorViewModel<OnboardingViewState, OnboardingAction, OnboardingViewEvents>(initialState) {
|
) : VectorViewModel<OnboardingViewState, OnboardingAction, OnboardingViewEvents>(initialState) {
|
||||||
|
|
||||||
@AssistedFactory
|
@AssistedFactory
|
||||||
|
@ -616,7 +617,7 @@ class OnboardingViewModel @AssistedInject constructor(
|
||||||
activeSessionHolder.setActiveSession(session)
|
activeSessionHolder.setActiveSession(session)
|
||||||
|
|
||||||
authenticationService.reset()
|
authenticationService.reset()
|
||||||
session.configureAndStart(applicationContext)
|
configureAndStartSessionUseCase.execute(session)
|
||||||
|
|
||||||
when (authenticationDescription) {
|
when (authenticationDescription) {
|
||||||
is AuthenticationDescription.Register -> {
|
is AuthenticationDescription.Register -> {
|
||||||
|
|
|
@ -0,0 +1,105 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session
|
||||||
|
|
||||||
|
import im.vector.app.core.extensions.startSyncing
|
||||||
|
import im.vector.app.core.session.clientinfo.UpdateMatrixClientInfoUseCase
|
||||||
|
import im.vector.app.test.fakes.FakeContext
|
||||||
|
import im.vector.app.test.fakes.FakeSession
|
||||||
|
import im.vector.app.test.fakes.FakeWebRtcCallManager
|
||||||
|
import io.mockk.coJustRun
|
||||||
|
import io.mockk.coVerify
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.just
|
||||||
|
import io.mockk.mockk
|
||||||
|
import io.mockk.mockkStatic
|
||||||
|
import io.mockk.runs
|
||||||
|
import io.mockk.unmockkAll
|
||||||
|
import io.mockk.verify
|
||||||
|
import kotlinx.coroutines.test.runTest
|
||||||
|
import org.junit.After
|
||||||
|
import org.junit.Before
|
||||||
|
import org.junit.Test
|
||||||
|
import org.matrix.android.sdk.api.session.sync.FilterService
|
||||||
|
|
||||||
|
class ConfigureAndStartSessionUseCaseTest {
|
||||||
|
|
||||||
|
private val fakeContext = FakeContext()
|
||||||
|
private val fakeWebRtcCallManager = FakeWebRtcCallManager()
|
||||||
|
private val fakeUpdateMatrixClientInfoUseCase = mockk<UpdateMatrixClientInfoUseCase>()
|
||||||
|
|
||||||
|
private val configureAndStartSessionUseCase = ConfigureAndStartSessionUseCase(
|
||||||
|
context = fakeContext.instance,
|
||||||
|
webRtcCallManager = fakeWebRtcCallManager.instance,
|
||||||
|
updateMatrixClientInfoUseCase = fakeUpdateMatrixClientInfoUseCase,
|
||||||
|
)
|
||||||
|
|
||||||
|
@Before
|
||||||
|
fun setup() {
|
||||||
|
mockkStatic("im.vector.app.core.extensions.SessionKt")
|
||||||
|
}
|
||||||
|
|
||||||
|
@After
|
||||||
|
fun tearDown() {
|
||||||
|
unmockkAll()
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given a session and start sync needed when configuring and starting the session then it should be configured properly`() = runTest {
|
||||||
|
// Given
|
||||||
|
val fakeSession = givenASession()
|
||||||
|
fakeWebRtcCallManager.givenCheckForProtocolsSupportIfNeededSucceeds()
|
||||||
|
coJustRun { fakeUpdateMatrixClientInfoUseCase.execute(any()) }
|
||||||
|
|
||||||
|
// When
|
||||||
|
configureAndStartSessionUseCase.execute(fakeSession, startSyncing = true)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
verify { fakeSession.startSyncing(fakeContext.instance) }
|
||||||
|
fakeSession.fakeFilterService.verifySetFilter(FilterService.FilterPreset.ElementFilter)
|
||||||
|
fakeSession.fakePushersService.verifyRefreshPushers()
|
||||||
|
fakeWebRtcCallManager.verifyCheckForProtocolsSupportIfNeeded()
|
||||||
|
coVerify { fakeUpdateMatrixClientInfoUseCase.execute(fakeSession) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given a session and no start sync needed when configuring and starting the session then it should be configured properly`() = runTest {
|
||||||
|
// Given
|
||||||
|
val fakeSession = givenASession()
|
||||||
|
fakeWebRtcCallManager.givenCheckForProtocolsSupportIfNeededSucceeds()
|
||||||
|
coJustRun { fakeUpdateMatrixClientInfoUseCase.execute(any()) }
|
||||||
|
|
||||||
|
// When
|
||||||
|
configureAndStartSessionUseCase.execute(fakeSession, startSyncing = false)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
verify(inverse = true) { fakeSession.startSyncing(fakeContext.instance) }
|
||||||
|
fakeSession.fakeFilterService.verifySetFilter(FilterService.FilterPreset.ElementFilter)
|
||||||
|
fakeSession.fakePushersService.verifyRefreshPushers()
|
||||||
|
fakeWebRtcCallManager.verifyCheckForProtocolsSupportIfNeeded()
|
||||||
|
coVerify { fakeUpdateMatrixClientInfoUseCase.execute(fakeSession) }
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenASession(): FakeSession {
|
||||||
|
val fakeSession = FakeSession()
|
||||||
|
every { fakeSession.open() } just runs
|
||||||
|
fakeSession.fakeFilterService.givenSetFilterSucceeds()
|
||||||
|
every { fakeSession.startSyncing(any()) } just runs
|
||||||
|
fakeSession.fakePushersService.givenRefreshPushersSucceeds()
|
||||||
|
return fakeSession
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,62 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import im.vector.app.test.fakes.FakeSession
|
||||||
|
import org.amshove.kluent.shouldBeEqualTo
|
||||||
|
import org.junit.Test
|
||||||
|
|
||||||
|
private const val A_DEVICE_ID = "device-id"
|
||||||
|
private const val A_CLIENT_NAME = "client-name"
|
||||||
|
private const val A_CLIENT_VERSION = "client-version"
|
||||||
|
private const val A_CLIENT_URL = "client-url"
|
||||||
|
|
||||||
|
class GetMatrixClientInfoUseCaseTest {
|
||||||
|
|
||||||
|
private val fakeSession = FakeSession()
|
||||||
|
|
||||||
|
private val getMatrixClientInfoUseCase = GetMatrixClientInfoUseCase()
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given a device id and existing content when getting the info then result should contain that info`() {
|
||||||
|
// Given
|
||||||
|
givenClientInfoContent(A_DEVICE_ID)
|
||||||
|
val expectedClientInfo = MatrixClientInfoContent(
|
||||||
|
name = A_CLIENT_NAME,
|
||||||
|
version = A_CLIENT_VERSION,
|
||||||
|
url = A_CLIENT_URL,
|
||||||
|
)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = getMatrixClientInfoUseCase.execute(fakeSession, A_DEVICE_ID)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result shouldBeEqualTo expectedClientInfo
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenClientInfoContent(deviceId: String) {
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + deviceId
|
||||||
|
val content = mapOf(
|
||||||
|
Pair("name", A_CLIENT_NAME),
|
||||||
|
Pair("version", A_CLIENT_VERSION),
|
||||||
|
Pair("url", A_CLIENT_URL),
|
||||||
|
)
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.givenGetUserAccountDataEventReturns(type, content)
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,106 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import im.vector.app.test.fakes.FakeSession
|
||||||
|
import kotlinx.coroutines.test.runTest
|
||||||
|
import org.amshove.kluent.shouldBe
|
||||||
|
import org.amshove.kluent.shouldBeEqualTo
|
||||||
|
import org.amshove.kluent.shouldBeInstanceOf
|
||||||
|
import org.junit.Test
|
||||||
|
import org.matrix.android.sdk.api.session.events.model.toContent
|
||||||
|
|
||||||
|
private const val A_DEVICE_ID = "device-id"
|
||||||
|
|
||||||
|
class SetMatrixClientInfoUseCaseTest {
|
||||||
|
|
||||||
|
private val fakeSession = FakeSession()
|
||||||
|
|
||||||
|
private val setMatrixClientInfoUseCase = SetMatrixClientInfoUseCase()
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given client info and no error when setting the info then account data is correctly updated`() = runTest {
|
||||||
|
// Given
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + A_DEVICE_ID
|
||||||
|
val clientInfo = givenClientInfo()
|
||||||
|
val content = clientInfo.toContent()
|
||||||
|
fakeSession
|
||||||
|
.givenSessionId(A_DEVICE_ID)
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.givenUpdateUserAccountDataEventSucceeds()
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = setMatrixClientInfoUseCase.execute(fakeSession, clientInfo)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isSuccess shouldBe true
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.verifyUpdateUserAccountDataEventSucceeds(type, content)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given client info and error during update when setting the info then result is failure`() = runTest {
|
||||||
|
// Given
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + A_DEVICE_ID
|
||||||
|
val clientInfo = givenClientInfo()
|
||||||
|
val content = clientInfo.toContent()
|
||||||
|
fakeSession
|
||||||
|
.givenSessionId(A_DEVICE_ID)
|
||||||
|
val error = Exception()
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.givenUpdateUserAccountDataEventFailsWithError(error)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = setMatrixClientInfoUseCase.execute(fakeSession, clientInfo)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isFailure shouldBe true
|
||||||
|
result.exceptionOrNull() shouldBeEqualTo error
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.verifyUpdateUserAccountDataEventSucceeds(type, content)
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given client info and null device id when setting the info then result is failure`() = runTest {
|
||||||
|
// Given
|
||||||
|
val type = MATRIX_CLIENT_INFO_KEY_PREFIX + A_DEVICE_ID
|
||||||
|
val clientInfo = givenClientInfo()
|
||||||
|
val content = clientInfo.toContent()
|
||||||
|
fakeSession
|
||||||
|
.givenSessionId(null)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = setMatrixClientInfoUseCase.execute(fakeSession, clientInfo)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isFailure shouldBe true
|
||||||
|
result.exceptionOrNull() shouldBeInstanceOf NoDeviceIdError::class
|
||||||
|
fakeSession
|
||||||
|
.fakeSessionAccountDataService
|
||||||
|
.verifyUpdateUserAccountDataEventSucceeds(type, content, inverse = true)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenClientInfo() = MatrixClientInfoContent(
|
||||||
|
name = "name",
|
||||||
|
version = "version",
|
||||||
|
url = null,
|
||||||
|
)
|
||||||
|
}
|
|
@ -0,0 +1,149 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.core.session.clientinfo
|
||||||
|
|
||||||
|
import im.vector.app.core.resources.BuildMeta
|
||||||
|
import im.vector.app.test.fakes.FakeAppNameProvider
|
||||||
|
import im.vector.app.test.fakes.FakeSession
|
||||||
|
import io.mockk.coEvery
|
||||||
|
import io.mockk.coVerify
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.mockk
|
||||||
|
import kotlinx.coroutines.test.runTest
|
||||||
|
import org.amshove.kluent.shouldBe
|
||||||
|
import org.amshove.kluent.shouldBeEqualTo
|
||||||
|
import org.amshove.kluent.shouldBeInstanceOf
|
||||||
|
import org.junit.Test
|
||||||
|
|
||||||
|
private const val AN_APP_NAME_1 = "app_name_1"
|
||||||
|
private const val AN_APP_NAME_2 = "app_name_2"
|
||||||
|
private const val A_VERSION_NAME_1 = "version_name_1"
|
||||||
|
private const val A_VERSION_NAME_2 = "version_name_2"
|
||||||
|
private const val A_SESSION_ID = "session-id"
|
||||||
|
|
||||||
|
class UpdateMatrixClientInfoUseCaseTest {
|
||||||
|
|
||||||
|
private val fakeSession = FakeSession()
|
||||||
|
private val fakeAppNameProvider = FakeAppNameProvider()
|
||||||
|
private val fakeBuildMeta = mockk<BuildMeta>()
|
||||||
|
private val getMatrixClientInfoUseCase = mockk<GetMatrixClientInfoUseCase>()
|
||||||
|
private val setMatrixClientInfoUseCase = mockk<SetMatrixClientInfoUseCase>()
|
||||||
|
|
||||||
|
private val updateMatrixClientInfoUseCase = UpdateMatrixClientInfoUseCase(
|
||||||
|
appNameProvider = fakeAppNameProvider,
|
||||||
|
buildMeta = fakeBuildMeta,
|
||||||
|
getMatrixClientInfoUseCase = getMatrixClientInfoUseCase,
|
||||||
|
setMatrixClientInfoUseCase = setMatrixClientInfoUseCase,
|
||||||
|
)
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given current client info is different than the stored one when trying to update then new client info is set`() = runTest {
|
||||||
|
// Given
|
||||||
|
givenCurrentAppName(AN_APP_NAME_1)
|
||||||
|
givenCurrentVersionName(A_VERSION_NAME_1)
|
||||||
|
givenStoredClientInfo(AN_APP_NAME_2, A_VERSION_NAME_2)
|
||||||
|
givenSetClientInfoSucceeds()
|
||||||
|
val expectedClientInfoToSet = MatrixClientInfoContent(
|
||||||
|
name = AN_APP_NAME_1,
|
||||||
|
version = A_VERSION_NAME_1,
|
||||||
|
)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = updateMatrixClientInfoUseCase.execute(fakeSession)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isSuccess shouldBe true
|
||||||
|
coVerify { setMatrixClientInfoUseCase.execute(fakeSession, match { it == expectedClientInfoToSet }) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given error during set of new client info when trying to update then result is failure`() = runTest {
|
||||||
|
// Given
|
||||||
|
givenCurrentAppName(AN_APP_NAME_1)
|
||||||
|
givenCurrentVersionName(A_VERSION_NAME_1)
|
||||||
|
givenStoredClientInfo(AN_APP_NAME_2, A_VERSION_NAME_2)
|
||||||
|
val error = Exception()
|
||||||
|
givenSetClientInfoFails(error)
|
||||||
|
val expectedClientInfoToSet = MatrixClientInfoContent(
|
||||||
|
name = AN_APP_NAME_1,
|
||||||
|
version = A_VERSION_NAME_1,
|
||||||
|
)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = updateMatrixClientInfoUseCase.execute(fakeSession)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isFailure shouldBe true
|
||||||
|
result.exceptionOrNull() shouldBeEqualTo error
|
||||||
|
coVerify { setMatrixClientInfoUseCase.execute(fakeSession, match { it == expectedClientInfoToSet }) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given current client info is equal to the stored one when trying to update then nothing is done`() = runTest {
|
||||||
|
// Given
|
||||||
|
givenCurrentAppName(AN_APP_NAME_1)
|
||||||
|
givenCurrentVersionName(A_VERSION_NAME_1)
|
||||||
|
givenStoredClientInfo(AN_APP_NAME_1, A_VERSION_NAME_1)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = updateMatrixClientInfoUseCase.execute(fakeSession)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isSuccess shouldBe true
|
||||||
|
coVerify(inverse = true) { setMatrixClientInfoUseCase.execute(fakeSession, any()) }
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
fun `given no session id for current session when trying to update then nothing is done`() = runTest {
|
||||||
|
// Given
|
||||||
|
givenCurrentAppName(AN_APP_NAME_1)
|
||||||
|
givenCurrentVersionName(A_VERSION_NAME_1)
|
||||||
|
fakeSession.givenSessionId(null)
|
||||||
|
|
||||||
|
// When
|
||||||
|
val result = updateMatrixClientInfoUseCase.execute(fakeSession)
|
||||||
|
|
||||||
|
// Then
|
||||||
|
result.isFailure shouldBe true
|
||||||
|
result.exceptionOrNull() shouldBeInstanceOf NoDeviceIdError::class
|
||||||
|
coVerify(inverse = true) { setMatrixClientInfoUseCase.execute(fakeSession, any()) }
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenCurrentAppName(appName: String) {
|
||||||
|
fakeAppNameProvider.givenAppName(appName)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenCurrentVersionName(versionName: String) {
|
||||||
|
every { fakeBuildMeta.versionName } returns versionName
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenStoredClientInfo(appName: String, versionName: String) {
|
||||||
|
fakeSession.givenSessionId(A_SESSION_ID)
|
||||||
|
every { getMatrixClientInfoUseCase.execute(fakeSession, A_SESSION_ID) } returns MatrixClientInfoContent(
|
||||||
|
name = appName,
|
||||||
|
version = versionName,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenSetClientInfoSucceeds() {
|
||||||
|
coEvery { setMatrixClientInfoUseCase.execute(any(), any()) } returns Result.success(Unit)
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun givenSetClientInfoFails(error: Throwable) {
|
||||||
|
coEvery { setMatrixClientInfoUseCase.execute(any(), any()) } returns Result.failure(error)
|
||||||
|
}
|
||||||
|
}
|
|
@ -20,6 +20,7 @@ import android.net.Uri
|
||||||
import android.os.Build
|
import android.os.Build
|
||||||
import com.airbnb.mvrx.test.MavericksTestRule
|
import com.airbnb.mvrx.test.MavericksTestRule
|
||||||
import im.vector.app.R
|
import im.vector.app.R
|
||||||
|
import im.vector.app.core.session.ConfigureAndStartSessionUseCase
|
||||||
import im.vector.app.features.login.LoginConfig
|
import im.vector.app.features.login.LoginConfig
|
||||||
import im.vector.app.features.login.LoginMode
|
import im.vector.app.features.login.LoginMode
|
||||||
import im.vector.app.features.login.ReAuthHelper
|
import im.vector.app.features.login.ReAuthHelper
|
||||||
|
@ -50,6 +51,7 @@ import im.vector.app.test.fixtures.a401ServerError
|
||||||
import im.vector.app.test.fixtures.aHomeServerCapabilities
|
import im.vector.app.test.fixtures.aHomeServerCapabilities
|
||||||
import im.vector.app.test.fixtures.anUnrecognisedCertificateError
|
import im.vector.app.test.fixtures.anUnrecognisedCertificateError
|
||||||
import im.vector.app.test.test
|
import im.vector.app.test.test
|
||||||
|
import io.mockk.mockk
|
||||||
import kotlinx.coroutines.test.runTest
|
import kotlinx.coroutines.test.runTest
|
||||||
import org.amshove.kluent.shouldBeEqualTo
|
import org.amshove.kluent.shouldBeEqualTo
|
||||||
import org.junit.Before
|
import org.junit.Before
|
||||||
|
@ -111,6 +113,7 @@ class OnboardingViewModelTest {
|
||||||
private val fakeStartAuthenticationFlowUseCase = FakeStartAuthenticationFlowUseCase()
|
private val fakeStartAuthenticationFlowUseCase = FakeStartAuthenticationFlowUseCase()
|
||||||
private val fakeHomeServerHistoryService = FakeHomeServerHistoryService()
|
private val fakeHomeServerHistoryService = FakeHomeServerHistoryService()
|
||||||
private val fakeLoginWizard = FakeLoginWizard()
|
private val fakeLoginWizard = FakeLoginWizard()
|
||||||
|
private val fakeConfigureAndStartSessionUseCase = mockk<ConfigureAndStartSessionUseCase>()
|
||||||
|
|
||||||
private var initialState = OnboardingViewState()
|
private var initialState = OnboardingViewState()
|
||||||
private lateinit var viewModel: OnboardingViewModel
|
private lateinit var viewModel: OnboardingViewModel
|
||||||
|
@ -1093,6 +1096,7 @@ class OnboardingViewModelTest {
|
||||||
FakeVectorOverrides(),
|
FakeVectorOverrides(),
|
||||||
fakeRegistrationActionHandler.instance,
|
fakeRegistrationActionHandler.instance,
|
||||||
TestBuildVersionSdkIntProvider().also { it.value = Build.VERSION_CODES.O },
|
TestBuildVersionSdkIntProvider().also { it.value = Build.VERSION_CODES.O },
|
||||||
|
fakeConfigureAndStartSessionUseCase,
|
||||||
).also {
|
).also {
|
||||||
viewModel = it
|
viewModel = it
|
||||||
initialState = state
|
initialState = state
|
||||||
|
@ -1132,7 +1136,7 @@ class OnboardingViewModelTest {
|
||||||
private fun givenInitialisesSession(session: Session) {
|
private fun givenInitialisesSession(session: Session) {
|
||||||
fakeActiveSessionHolder.expectSetsActiveSession(session)
|
fakeActiveSessionHolder.expectSetsActiveSession(session)
|
||||||
fakeAuthenticationService.expectReset()
|
fakeAuthenticationService.expectReset()
|
||||||
fakeSession.expectStartsSyncing()
|
fakeSession.expectStartsSyncing(fakeConfigureAndStartSessionUseCase)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun givenRegistrationResultFor(action: RegisterAction, result: RegistrationActionHandler.Result) {
|
private fun givenRegistrationResultFor(action: RegisterAction, result: RegistrationActionHandler.Result) {
|
||||||
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.test.fakes
|
||||||
|
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.just
|
||||||
|
import io.mockk.mockk
|
||||||
|
import io.mockk.runs
|
||||||
|
import io.mockk.verify
|
||||||
|
import org.matrix.android.sdk.api.session.sync.FilterService
|
||||||
|
|
||||||
|
class FakeFilterService : FilterService by mockk() {
|
||||||
|
|
||||||
|
fun givenSetFilterSucceeds() {
|
||||||
|
every { setFilter(any()) } just runs
|
||||||
|
}
|
||||||
|
|
||||||
|
fun verifySetFilter(filterPreset: FilterService.FilterPreset) {
|
||||||
|
verify { setFilter(filterPreset) }
|
||||||
|
}
|
||||||
|
}
|
|
@ -20,6 +20,7 @@ import androidx.lifecycle.liveData
|
||||||
import io.mockk.Ordering
|
import io.mockk.Ordering
|
||||||
import io.mockk.coVerify
|
import io.mockk.coVerify
|
||||||
import io.mockk.every
|
import io.mockk.every
|
||||||
|
import io.mockk.justRun
|
||||||
import io.mockk.mockk
|
import io.mockk.mockk
|
||||||
import io.mockk.slot
|
import io.mockk.slot
|
||||||
import io.mockk.verify
|
import io.mockk.verify
|
||||||
|
@ -56,4 +57,12 @@ class FakePushersService : PushersService by mockk(relaxed = true) {
|
||||||
verify { enqueueAddHttpPusher(capture(httpPusherSlot)) }
|
verify { enqueueAddHttpPusher(capture(httpPusherSlot)) }
|
||||||
return httpPusherSlot.captured
|
return httpPusherSlot.captured
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun givenRefreshPushersSucceeds() {
|
||||||
|
justRun { refreshPushers() }
|
||||||
|
}
|
||||||
|
|
||||||
|
fun verifyRefreshPushers() {
|
||||||
|
verify { refreshPushers() }
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -16,9 +16,9 @@
|
||||||
|
|
||||||
package im.vector.app.test.fakes
|
package im.vector.app.test.fakes
|
||||||
|
|
||||||
import im.vector.app.core.extensions.configureAndStart
|
|
||||||
import im.vector.app.core.extensions.startSyncing
|
import im.vector.app.core.extensions.startSyncing
|
||||||
import im.vector.app.core.extensions.vectorStore
|
import im.vector.app.core.extensions.vectorStore
|
||||||
|
import im.vector.app.core.session.ConfigureAndStartSessionUseCase
|
||||||
import im.vector.app.features.session.VectorSessionStore
|
import im.vector.app.features.session.VectorSessionStore
|
||||||
import im.vector.app.test.testCoroutineDispatchers
|
import im.vector.app.test.testCoroutineDispatchers
|
||||||
import io.mockk.coEvery
|
import io.mockk.coEvery
|
||||||
|
@ -43,6 +43,8 @@ class FakeSession(
|
||||||
val fakeRoomService: FakeRoomService = FakeRoomService(),
|
val fakeRoomService: FakeRoomService = FakeRoomService(),
|
||||||
val fakePushersService: FakePushersService = FakePushersService(),
|
val fakePushersService: FakePushersService = FakePushersService(),
|
||||||
private val fakeEventService: FakeEventService = FakeEventService(),
|
private val fakeEventService: FakeEventService = FakeEventService(),
|
||||||
|
val fakeSessionAccountDataService: FakeSessionAccountDataService = FakeSessionAccountDataService(),
|
||||||
|
val fakeFilterService: FakeFilterService = FakeFilterService(),
|
||||||
) : Session by mockk(relaxed = true) {
|
) : Session by mockk(relaxed = true) {
|
||||||
|
|
||||||
init {
|
init {
|
||||||
|
@ -60,6 +62,8 @@ class FakeSession(
|
||||||
override fun roomService() = fakeRoomService
|
override fun roomService() = fakeRoomService
|
||||||
override fun eventService() = fakeEventService
|
override fun eventService() = fakeEventService
|
||||||
override fun pushersService() = fakePushersService
|
override fun pushersService() = fakePushersService
|
||||||
|
override fun accountDataService() = fakeSessionAccountDataService
|
||||||
|
override fun filterService() = fakeFilterService
|
||||||
|
|
||||||
fun givenVectorStore(vectorSessionStore: VectorSessionStore) {
|
fun givenVectorStore(vectorSessionStore: VectorSessionStore) {
|
||||||
coEvery {
|
coEvery {
|
||||||
|
@ -69,9 +73,9 @@ class FakeSession(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun expectStartsSyncing() {
|
fun expectStartsSyncing(configureAndStartSessionUseCase: ConfigureAndStartSessionUseCase) {
|
||||||
coJustRun {
|
coJustRun {
|
||||||
this@FakeSession.configureAndStart(any(), startSyncing = true)
|
configureAndStartSessionUseCase.execute(this@FakeSession, startSyncing = true)
|
||||||
this@FakeSession.startSyncing(any())
|
this@FakeSession.startSyncing(any())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -80,7 +84,7 @@ class FakeSession(
|
||||||
every { this@FakeSession.sessionParams } returns sessionParams
|
every { this@FakeSession.sessionParams } returns sessionParams
|
||||||
}
|
}
|
||||||
|
|
||||||
fun givenSessionId(sessionId: String): SessionParams {
|
fun givenSessionId(sessionId: String?): SessionParams {
|
||||||
val sessionParams = mockk<SessionParams>()
|
val sessionParams = mockk<SessionParams>()
|
||||||
every { sessionParams.deviceId } returns sessionId
|
every { sessionParams.deviceId } returns sessionId
|
||||||
givenSessionParams(sessionParams)
|
givenSessionParams(sessionParams)
|
||||||
|
|
|
@ -0,0 +1,46 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.test.fakes
|
||||||
|
|
||||||
|
import io.mockk.coEvery
|
||||||
|
import io.mockk.coVerify
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.just
|
||||||
|
import io.mockk.mockk
|
||||||
|
import io.mockk.runs
|
||||||
|
import org.matrix.android.sdk.api.session.accountdata.SessionAccountDataService
|
||||||
|
import org.matrix.android.sdk.api.session.accountdata.UserAccountDataEvent
|
||||||
|
import org.matrix.android.sdk.api.session.events.model.Content
|
||||||
|
|
||||||
|
class FakeSessionAccountDataService : SessionAccountDataService by mockk() {
|
||||||
|
|
||||||
|
fun givenGetUserAccountDataEventReturns(type: String, content: Content) {
|
||||||
|
every { getUserAccountDataEvent(type) } returns UserAccountDataEvent(type, content)
|
||||||
|
}
|
||||||
|
|
||||||
|
fun givenUpdateUserAccountDataEventSucceeds() {
|
||||||
|
coEvery { updateUserAccountData(any(), any()) } just runs
|
||||||
|
}
|
||||||
|
|
||||||
|
fun givenUpdateUserAccountDataEventFailsWithError(error: Exception) {
|
||||||
|
coEvery { updateUserAccountData(any(), any()) } throws error
|
||||||
|
}
|
||||||
|
|
||||||
|
fun verifyUpdateUserAccountDataEventSucceeds(type: String, content: Content, inverse: Boolean = false) {
|
||||||
|
coVerify(inverse = inverse) { updateUserAccountData(type, content) }
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,37 @@
|
||||||
|
/*
|
||||||
|
* 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.
|
||||||
|
*/
|
||||||
|
|
||||||
|
package im.vector.app.test.fakes
|
||||||
|
|
||||||
|
import im.vector.app.features.call.webrtc.WebRtcCallManager
|
||||||
|
import io.mockk.every
|
||||||
|
import io.mockk.just
|
||||||
|
import io.mockk.mockk
|
||||||
|
import io.mockk.runs
|
||||||
|
import io.mockk.verify
|
||||||
|
|
||||||
|
class FakeWebRtcCallManager {
|
||||||
|
|
||||||
|
val instance = mockk<WebRtcCallManager>()
|
||||||
|
|
||||||
|
fun givenCheckForProtocolsSupportIfNeededSucceeds() {
|
||||||
|
every { instance.checkForProtocolsSupportIfNeeded() } just runs
|
||||||
|
}
|
||||||
|
|
||||||
|
fun verifyCheckForProtocolsSupportIfNeeded() {
|
||||||
|
verify { instance.checkForProtocolsSupportIfNeeded() }
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in a new issue