PM-27845: Move SnackbarRelayManager to ui module (#6127)

This commit is contained in:
David Perez 2025-11-06 12:50:06 -06:00 committed by GitHub
parent b715a51188
commit efd15b027c
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
44 changed files with 158 additions and 149 deletions

View File

@ -12,6 +12,7 @@ import com.bitwarden.ui.platform.base.util.isValidUri
import com.bitwarden.ui.platform.base.util.orNullIfBlank
import com.bitwarden.ui.platform.base.util.prefixHttpsIfNecessaryOrNull
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.FileData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -22,8 +23,7 @@ import com.x8bit.bitwarden.data.platform.manager.model.ImportPrivateKeyResult
import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.vault.manager.FileManager
import com.x8bit.bitwarden.ui.platform.manager.keychain.model.PrivateKeyAliasSelectionResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
@ -43,7 +43,7 @@ class EnvironmentViewModel @Inject constructor(
private val environmentRepository: EnvironmentRepository,
private val fileManager: FileManager,
private val certificateManager: CertificateManager,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val savedStateHandle: SavedStateHandle,
) : BaseViewModel<EnvironmentState, EnvironmentEvent, EnvironmentAction>(
initialState = savedStateHandle[KEY_STATE] ?: run {

View File

@ -9,6 +9,7 @@ import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.base.util.isValidEmail
import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.auth.repository.model.LogoutReason
import com.x8bit.bitwarden.data.auth.repository.model.UserState
import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.vault.util.toAccountSummaries
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
@ -39,7 +39,7 @@ class LandingViewModel @Inject constructor(
private val authRepository: AuthRepository,
private val vaultRepository: VaultRepository,
private val environmentRepository: EnvironmentRepository,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
savedStateHandle: SavedStateHandle,
) : BaseViewModel<LandingState, LandingEvent, LandingAction>(
initialState = savedStateHandle[KEY_STATE]

View File

@ -5,6 +5,7 @@ import androidx.lifecycle.SavedStateHandle
import androidx.lifecycle.viewModelScope
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -13,8 +14,7 @@ import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.auth.repository.model.LoginResult
import com.x8bit.bitwarden.ui.auth.feature.loginwithdevice.model.LoginWithDeviceType
import com.x8bit.bitwarden.ui.auth.feature.loginwithdevice.util.toAuthRequestType
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.Job
import kotlinx.coroutines.flow.launchIn
@ -34,7 +34,7 @@ private const val KEY_STATE = "state"
@HiltViewModel
class LoginWithDeviceViewModel @Inject constructor(
private val authRepository: AuthRepository,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
savedStateHandle: SavedStateHandle,
) : BaseViewModel<LoginWithDeviceState, LoginWithDeviceEvent, LoginWithDeviceAction>(
initialState = savedStateHandle[KEY_STATE]

View File

@ -9,6 +9,7 @@ import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.base.util.isValidEmail
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -16,8 +17,7 @@ import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.auth.repository.model.RegisterResult
import com.x8bit.bitwarden.data.auth.repository.model.SendVerificationEmailResult
import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.map
@ -36,7 +36,7 @@ private const val KEY_STATE = "state"
@HiltViewModel
class StartRegistrationViewModel @Inject constructor(
savedStateHandle: SavedStateHandle,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val authRepository: AuthRepository,
private val environmentRepository: EnvironmentRepository,
) : BaseViewModel<StartRegistrationState, StartRegistrationEvent, StartRegistrationAction>(

View File

@ -13,6 +13,7 @@ import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.TotpData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -50,8 +51,7 @@ import com.x8bit.bitwarden.ui.platform.feature.search.util.filterAndOrganize
import com.x8bit.bitwarden.ui.platform.feature.search.util.toSearchTypeData
import com.x8bit.bitwarden.ui.platform.feature.search.util.toViewState
import com.x8bit.bitwarden.ui.platform.feature.search.util.updateWithAdditionalDataIfNecessary
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.util.toSendItemType
import com.x8bit.bitwarden.ui.vault.feature.itemlisting.model.ListingItemOverflowAction
@ -97,7 +97,7 @@ class SearchViewModel @Inject constructor(
private val authRepo: AuthRepository,
environmentRepo: EnvironmentRepository,
settingsRepo: SettingsRepository,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
specialCircumstanceManager: SpecialCircumstanceManager,
) : BaseViewModel<SearchState, SearchEvent, SearchAction>(
// We load the state from the savedStateHandle for testing purposes.

View File

@ -10,6 +10,7 @@ import com.bitwarden.core.data.manager.toast.ToastManager
import com.bitwarden.core.data.util.toFormattedDateTimeStyle
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -18,8 +19,7 @@ import com.x8bit.bitwarden.data.auth.manager.model.AuthRequestUpdatesResult
import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.platform.manager.SpecialCircumstanceManager
import com.x8bit.bitwarden.data.platform.manager.model.SpecialCircumstance
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.map
@ -41,7 +41,7 @@ class LoginApprovalViewModel @Inject constructor(
private val clock: Clock,
private val authRepository: AuthRepository,
private val specialCircumstanceManager: SpecialCircumstanceManager,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val toastManager: ToastManager,
savedStateHandle: SavedStateHandle,
) : BaseViewModel<LoginApprovalState, LoginApprovalEvent, LoginApprovalAction>(

View File

@ -12,12 +12,12 @@ import com.bitwarden.core.util.isOverFiveMinutesOld
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequest
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequestsUpdatesResult
import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.platform.repository.SettingsRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.Job
import kotlinx.coroutines.flow.launchIn
@ -40,7 +40,7 @@ private const val KEY_STATE = "state"
class PendingRequestsViewModel @Inject constructor(
private val clock: Clock,
private val authRepository: AuthRepository,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
settingsRepository: SettingsRepository,
buildInfoManager: BuildInfoManager,
savedStateHandle: SavedStateHandle,

View File

@ -6,6 +6,7 @@ import com.bitwarden.core.data.repository.model.DataState
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -13,8 +14,7 @@ import com.bitwarden.ui.util.concat
import com.bitwarden.vault.FolderView
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.feature.settings.folders.model.FolderDisplayItem
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.map
@ -30,7 +30,7 @@ import javax.inject.Inject
@HiltViewModel
class FoldersViewModel @Inject constructor(
vaultRepository: VaultRepository,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<FoldersState, FoldersEvent, FoldersAction>(
initialState = FoldersState(viewState = FoldersState.ViewState.Loading),
) {

View File

@ -7,6 +7,7 @@ import com.bitwarden.core.DateTime
import com.bitwarden.core.data.repository.model.DataState
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.CreateFolderResult
import com.x8bit.bitwarden.data.vault.repository.model.DeleteFolderResult
import com.x8bit.bitwarden.data.vault.repository.model.UpdateFolderResult
import com.x8bit.bitwarden.ui.platform.feature.settings.folders.model.FolderAddEditType
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.onEach
@ -38,7 +38,7 @@ private const val KEY_STATE = "state"
class FolderAddEditViewModel @Inject constructor(
savedStateHandle: SavedStateHandle,
private val vaultRepository: VaultRepository,
private val relayManager: SnackbarRelayManager,
private val relayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<FolderAddEditState, FolderAddEditEvent, FolderAddEditAction>(
// We load the state from the savedStateHandle for testing purposes.
initialState = savedStateHandle[KEY_STATE]

View File

@ -5,10 +5,10 @@ import com.bitwarden.core.data.manager.model.FlagKey
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.data.platform.manager.FeatureFlagManager
import com.x8bit.bitwarden.data.platform.manager.FirstTimeActionManager
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.launchIn
import kotlinx.coroutines.flow.map
@ -22,7 +22,7 @@ import javax.inject.Inject
@Suppress("TooManyFunctions")
@HiltViewModel
class VaultSettingsViewModel @Inject constructor(
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val firstTimeActionManager: FirstTimeActionManager,
private val featureFlagManager: FeatureFlagManager,
) : BaseViewModel<VaultSettingsState, VaultSettingsEvent, VaultSettingsAction>(

View File

@ -5,11 +5,12 @@ import com.bitwarden.core.data.manager.BuildInfoManager
import com.bitwarden.core.data.manager.dispatcher.DispatcherManager
import com.bitwarden.ui.platform.manager.share.ShareManager
import com.bitwarden.ui.platform.manager.share.ShareManagerImpl
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManagerImpl
import com.x8bit.bitwarden.ui.platform.manager.BitwardenBuildInfoManagerImpl
import com.x8bit.bitwarden.ui.platform.manager.resource.ResourceManager
import com.x8bit.bitwarden.ui.platform.manager.resource.ResourceManagerImpl
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManagerImpl
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.Module
import dagger.Provides
import dagger.hilt.InstallIn
@ -37,7 +38,7 @@ object PlatformUiManagerModule {
@Singleton
fun provideSnackbarRelayManager(
dispatcherManager: DispatcherManager,
): SnackbarRelayManager = SnackbarRelayManagerImpl(
): SnackbarRelayManager<SnackbarRelay> = SnackbarRelayManagerImpl(
dispatcherManager = dispatcherManager,
)

View File

@ -1,4 +1,4 @@
package com.x8bit.bitwarden.ui.platform.manager.snackbar
package com.x8bit.bitwarden.ui.platform.model
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import kotlinx.serialization.Serializable

View File

@ -11,6 +11,7 @@ import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenDrawable
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -26,8 +27,7 @@ import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.data.vault.repository.model.RemovePasswordSendResult
import com.x8bit.bitwarden.data.vault.repository.model.SendData
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.util.toViewState
import com.x8bit.bitwarden.ui.vault.feature.item.VaultItemScreen
@ -54,7 +54,7 @@ class SendViewModel @Inject constructor(
authRepo: AuthRepository,
settingsRepo: SettingsRepository,
policyManager: PolicyManager,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val clipboardManager: BitwardenClipboardManager,
private val environmentRepo: EnvironmentRepository,
private val vaultRepo: VaultRepository,

View File

@ -12,6 +12,7 @@ import com.bitwarden.send.SendView
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.FileData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -30,8 +31,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.CreateSendResult
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.data.vault.repository.model.RemovePasswordSendResult
import com.x8bit.bitwarden.data.vault.repository.model.UpdateSendResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.model.AddEditSendType
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.util.shouldFinishOnComplete
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.util.toSendName
@ -74,7 +74,7 @@ class AddEditSendViewModel @Inject constructor(
private val vaultRepo: VaultRepository,
private val policyManager: PolicyManager,
private val networkConnectionManager: NetworkConnectionManager,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<AddEditSendState, AddEditSendEvent, AddEditSendAction>(
// We load the state from the savedStateHandle for testing purposes.
initialState = savedStateHandle[KEY_STATE] ?: run {

View File

@ -9,6 +9,7 @@ import com.bitwarden.send.SendView
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.platform.manager.clipboard.BitwardenClipboardMan
import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.viewsend.util.toViewSendViewStateContent
import dagger.hilt.android.lifecycle.HiltViewModel
@ -40,7 +40,7 @@ private const val KEY_STATE = "state"
@HiltViewModel
class ViewSendViewModel @Inject constructor(
private val clipboardManager: BitwardenClipboardManager,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val clock: Clock,
private val vaultRepository: VaultRepository,
environmentRepository: EnvironmentRepository,

View File

@ -14,6 +14,7 @@ import com.bitwarden.network.model.PolicyTypeJson
import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.TotpData
import com.bitwarden.ui.platform.resource.BitwardenPlurals
import com.bitwarden.ui.platform.resource.BitwardenString
@ -60,8 +61,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.UpdateCipherResult
import com.x8bit.bitwarden.data.vault.repository.model.VaultData
import com.x8bit.bitwarden.ui.credentials.manager.model.RegisterFido2CredentialResult
import com.x8bit.bitwarden.ui.platform.manager.resource.ResourceManager
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.generator.model.GeneratorMode
import com.x8bit.bitwarden.ui.vault.feature.addedit.model.CustomFieldAction
import com.x8bit.bitwarden.ui.vault.feature.addedit.model.CustomFieldType
@ -117,7 +117,7 @@ private const val KEY_STATE = "state"
class VaultAddEditViewModel @Inject constructor(
savedStateHandle: SavedStateHandle,
generatorRepository: GeneratorRepository,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val toastManager: ToastManager,
private val authRepository: AuthRepository,
private val clipboardManager: BitwardenClipboardManager,

View File

@ -3,6 +3,7 @@ package com.x8bit.bitwarden.ui.vault.feature.importlogins
import androidx.lifecycle.viewModelScope
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -11,8 +12,7 @@ import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.platform.util.toUriOrNull
import com.x8bit.bitwarden.data.vault.manager.model.SyncVaultDataResult
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import dagger.hilt.android.lifecycle.HiltViewModel
import kotlinx.coroutines.flow.update
import kotlinx.coroutines.launch
@ -27,7 +27,7 @@ class ImportLoginsViewModel @Inject constructor(
private val vaultRepository: VaultRepository,
private val firstTimeActionManager: FirstTimeActionManager,
private val environmentRepository: EnvironmentRepository,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<ImportLoginsState, ImportLoginsEvent, ImportLoginsAction>(
initialState = run {
val vaultUrl = environmentRepository.environment.environmentUrlData.webVault

View File

@ -13,6 +13,7 @@ import com.bitwarden.ui.platform.base.BackgroundEvent
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenPlurals
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -33,8 +34,7 @@ import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteCipherResult
import com.x8bit.bitwarden.data.vault.repository.model.DownloadAttachmentResult
import com.x8bit.bitwarden.data.vault.repository.model.RestoreCipherResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.item.model.TotpCodeItemData
import com.x8bit.bitwarden.ui.vault.feature.item.model.VaultItemLocation
import com.x8bit.bitwarden.ui.vault.feature.item.model.VaultItemStateData
@ -75,7 +75,7 @@ class VaultItemViewModel @Inject constructor(
private val organizationEventManager: OrganizationEventManager,
private val environmentRepository: EnvironmentRepository,
private val settingsRepository: SettingsRepository,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<VaultItemState, VaultItemEvent, VaultItemAction>(
// We load the state from the savedStateHandle for testing purposes.
initialState = savedStateHandle[KEY_STATE] ?: run {

View File

@ -23,6 +23,7 @@ import com.bitwarden.ui.platform.base.util.toHostOrPathOrNull
import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.TotpData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -82,8 +83,7 @@ import com.x8bit.bitwarden.ui.credentials.manager.model.RegisterFido2CredentialR
import com.x8bit.bitwarden.ui.platform.feature.search.SearchTypeData
import com.x8bit.bitwarden.ui.platform.feature.search.model.SearchType
import com.x8bit.bitwarden.ui.platform.feature.search.util.filterAndOrganize
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.util.toSendItemType
import com.x8bit.bitwarden.ui.vault.components.model.CreateVaultItemType
@ -144,7 +144,7 @@ class VaultItemListingViewModel @Inject constructor(
private val networkConnectionManager: NetworkConnectionManager,
private val relyingPartyParser: RelyingPartyParser,
private val toastManager: ToastManager,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<VaultItemListingState, VaultItemListingEvent, VaultItemListingsAction>(
initialState = run {
val userState = requireNotNull(authRepository.userStateFlow.value)

View File

@ -8,6 +8,7 @@ import com.bitwarden.core.data.repository.model.DataState
import com.bitwarden.core.data.repository.util.combineDataStates
import com.bitwarden.ui.platform.base.BaseViewModel
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.auth.repository.model.UserState
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.ShareCipherResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.movetoorganization.util.toViewState
import com.x8bit.bitwarden.ui.vault.model.VaultCollection
import dagger.hilt.android.lifecycle.HiltViewModel
@ -41,7 +41,7 @@ private const val KEY_STATE = "state"
class VaultMoveToOrganizationViewModel @Inject constructor(
savedStateHandle: SavedStateHandle,
authRepository: AuthRepository,
private val snackbarRelayManager: SnackbarRelayManager,
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
private val vaultRepository: VaultRepository,
) : BaseViewModel<VaultMoveToOrganizationState, VaultMoveToOrganizationEvent, VaultMoveToOrganizationAction>(
initialState = savedStateHandle[KEY_STATE]

View File

@ -15,6 +15,7 @@ import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.account.util.initials
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenDrawable
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -46,8 +47,7 @@ import com.x8bit.bitwarden.data.vault.manager.model.GetCipherResult
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.GenerateTotpResult
import com.x8bit.bitwarden.data.vault.repository.model.VaultData
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.components.model.CreateVaultItemType
import com.x8bit.bitwarden.ui.vault.components.util.toVaultItemCipherTypeOrNull
import com.x8bit.bitwarden.ui.vault.feature.itemlisting.model.ListingItemOverflowAction
@ -106,7 +106,7 @@ class VaultViewModel @Inject constructor(
private val browserAutofillDialogManager: BrowserAutofillDialogManager,
private val credentialExchangeRegistryManager: CredentialExchangeRegistryManager,
featureFlagManager: FeatureFlagManager,
snackbarRelayManager: SnackbarRelayManager,
snackbarRelayManager: SnackbarRelayManager<SnackbarRelay>,
) : BaseViewModel<VaultState, VaultEvent, VaultAction>(
initialState = run {
val userState = requireNotNull(authRepository.userStateFlow.value)

View File

@ -8,6 +8,7 @@ import com.bitwarden.data.datasource.disk.model.EnvironmentUrlDataJson
import com.bitwarden.data.repository.model.Environment
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.FileData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.platform.manager.model.ImportPrivateKeyResult
import com.x8bit.bitwarden.data.platform.repository.util.FakeEnvironmentRepository
import com.x8bit.bitwarden.data.vault.manager.FileManager
import com.x8bit.bitwarden.ui.platform.manager.keychain.model.PrivateKeyAliasSelectionResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -38,7 +38,7 @@ class EnvironmentViewModelTest : BaseViewModelTest() {
every { getMutualTlsKeyAliases() } returns emptyList()
}
private val mockFileManager = mockk<FileManager>()
private val snackbarRelayManager = mockk<SnackbarRelayManager> {
private val snackbarRelayManager = mockk<SnackbarRelayManager<SnackbarRelay>> {
every { sendSnackbarData(data = any(), relay = any()) } just runs
}

View File

@ -7,6 +7,7 @@ import com.bitwarden.data.repository.model.Environment
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.auth.datasource.disk.model.OnboardingStatus
@ -17,8 +18,7 @@ import com.x8bit.bitwarden.data.auth.repository.model.VaultUnlockType
import com.x8bit.bitwarden.data.platform.manager.model.FirstTimeState
import com.x8bit.bitwarden.data.platform.repository.util.FakeEnvironmentRepository
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.vault.util.toAccountSummaries
import com.x8bit.bitwarden.ui.vault.feature.vault.util.toAccountSummary
import io.mockk.every
@ -42,7 +42,7 @@ class LandingViewModelTest : BaseViewModelTest() {
}
private val fakeEnvironmentRepository = FakeEnvironmentRepository()
private val mutableSnackbarSharedFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager = mockk<SnackbarRelayManager> {
private val snackbarRelayManager = mockk<SnackbarRelayManager<SnackbarRelay>> {
every {
getSnackbarDataFlow(SnackbarRelay.ENVIRONMENT_SAVED)
} returns mutableSnackbarSharedFlow

View File

@ -5,6 +5,7 @@ import app.cash.turbine.test
import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequest
@ -13,8 +14,7 @@ import com.x8bit.bitwarden.data.auth.manager.model.CreateAuthRequestResult
import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.auth.repository.model.LoginResult
import com.x8bit.bitwarden.ui.auth.feature.loginwithdevice.model.LoginWithDeviceType
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -41,7 +41,7 @@ class LoginWithDeviceViewModelTest : BaseViewModelTest() {
createAuthRequestWithUpdates(email = EMAIL, authRequestType = any())
} returns mutableCreateAuthRequestWithUpdatesFlow
}
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = any()) } just runs
}

View File

@ -6,6 +6,7 @@ import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.data.repository.model.Environment
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.auth.repository.AuthRepository
@ -26,8 +27,7 @@ import com.x8bit.bitwarden.ui.auth.feature.startregistration.StartRegistrationEv
import com.x8bit.bitwarden.ui.auth.feature.startregistration.StartRegistrationEvent.NavigateToPrivacyPolicy
import com.x8bit.bitwarden.ui.auth.feature.startregistration.StartRegistrationEvent.NavigateToTerms
import com.x8bit.bitwarden.ui.auth.feature.startregistration.StartRegistrationEvent.NavigateToUnsubscribe
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.every
import io.mockk.mockk
@ -39,7 +39,7 @@ import org.junit.jupiter.api.Test
class StartRegistrationViewModelTest : BaseViewModelTest() {
private val mockAuthRepository = mockk<AuthRepository>()
private val mutableSnackbarSharedFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager = mockk<SnackbarRelayManager> {
private val snackbarRelayManager = mockk<SnackbarRelayManager<SnackbarRelay>> {
every {
getSnackbarDataFlow(SnackbarRelay.ENVIRONMENT_SAVED)
} returns mutableSnackbarSharedFlow

View File

@ -13,6 +13,7 @@ import com.bitwarden.network.model.SyncResponseJson
import com.bitwarden.send.SendType
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -61,7 +62,7 @@ import com.x8bit.bitwarden.ui.platform.feature.search.model.SearchType
import com.x8bit.bitwarden.ui.platform.feature.search.util.createMockDisplayItemForCipher
import com.x8bit.bitwarden.ui.platform.feature.search.util.filterAndOrganize
import com.x8bit.bitwarden.ui.platform.feature.search.util.toViewState
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.vault.feature.itemlisting.model.ListingItemOverflowAction
import com.x8bit.bitwarden.ui.vault.feature.vault.model.VaultFilterType
@ -150,7 +151,7 @@ class SearchViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -7,6 +7,7 @@ import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.data.repository.model.Environment
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.auth.datasource.disk.model.OnboardingStatus
@ -20,8 +21,7 @@ import com.x8bit.bitwarden.data.platform.manager.SpecialCircumstanceManager
import com.x8bit.bitwarden.data.platform.manager.model.FirstTimeState
import com.x8bit.bitwarden.data.platform.manager.model.PasswordlessRequestData
import com.x8bit.bitwarden.data.platform.manager.model.SpecialCircumstance
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -61,7 +61,7 @@ class LoginApprovalViewModelTest : BaseViewModelTest() {
coEvery { getAuthRequestByIdFlow(REQUEST_ID) } returns mutableAuthRequestSharedFlow
every { userStateFlow } returns mutableUserStateFlow
}
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = SnackbarRelay.LOGIN_APPROVAL) } just runs
}
private val toastManager: ToastManager = mockk {

View File

@ -7,6 +7,7 @@ import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.core.data.util.toFormattedDateTimeStyle
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequest
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequestResult
@ -14,7 +15,7 @@ import com.x8bit.bitwarden.data.auth.manager.model.AuthRequestsResult
import com.x8bit.bitwarden.data.auth.manager.model.AuthRequestsUpdatesResult
import com.x8bit.bitwarden.data.auth.repository.AuthRepository
import com.x8bit.bitwarden.data.platform.repository.SettingsRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -51,7 +52,7 @@ class PendingRequestsViewModelTest : BaseViewModelTest() {
every { getPullToRefreshEnabledFlow() } returns mutablePullToRefreshStateFlow
}
private val mutableSnackbarDataFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -6,13 +6,14 @@ import com.bitwarden.core.data.repository.model.DataState
import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.bitwarden.ui.util.concat
import com.bitwarden.vault.FolderView
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.feature.settings.folders.model.FolderDisplayItem
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.every
import io.mockk.mockk
import kotlinx.coroutines.flow.MutableStateFlow
@ -29,7 +30,7 @@ class FoldersViewModelTest : BaseViewModelTest() {
every { foldersStateFlow } returns mutableFoldersStateFlow
}
private val mutableSnackbarDataFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -6,6 +6,7 @@ import com.bitwarden.core.DateTime
import com.bitwarden.core.data.repository.model.DataState
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.bitwarden.ui.util.concat
@ -15,8 +16,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.CreateFolderResult
import com.x8bit.bitwarden.data.vault.repository.model.DeleteFolderResult
import com.x8bit.bitwarden.data.vault.repository.model.UpdateFolderResult
import com.x8bit.bitwarden.ui.platform.feature.settings.folders.model.FolderAddEditType
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -43,7 +43,7 @@ class FolderAddEditViewModelTest : BaseViewModelTest() {
private val vaultRepository: VaultRepository = mockk {
every { getVaultFolderStateFlow(DEFAULT_EDIT_ITEM_ID) } returns mutableFoldersStateFlow
}
private val relayManager: SnackbarRelayManager = mockk {
private val relayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = any()) } just runs
}

View File

@ -5,12 +5,12 @@ import com.bitwarden.core.data.manager.model.FlagKey
import com.bitwarden.core.data.repository.util.bufferedMutableSharedFlow
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.platform.manager.FeatureFlagManager
import com.x8bit.bitwarden.data.platform.manager.FirstTimeActionManager
import com.x8bit.bitwarden.data.platform.manager.model.FirstTimeState
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.every
import io.mockk.just
import io.mockk.mockk
@ -40,7 +40,7 @@ class VaultSettingsViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarSharedFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager = mockk<SnackbarRelayManager> {
private val snackbarRelayManager = mockk<SnackbarRelayManager<SnackbarRelay>> {
every {
getSnackbarDataFlow(SnackbarRelay.LOGINS_IMPORTED)
} returns mutableSnackbarSharedFlow

View File

@ -9,6 +9,7 @@ import com.bitwarden.data.repository.util.baseWebSendUrl
import com.bitwarden.network.model.PolicyTypeJson
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -25,7 +26,7 @@ import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.data.vault.repository.model.RemovePasswordSendResult
import com.x8bit.bitwarden.data.vault.repository.model.SendData
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.util.toViewState
import io.mockk.coEvery
@ -78,7 +79,7 @@ class SendViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -10,6 +10,7 @@ import com.bitwarden.network.model.SyncResponseJson
import com.bitwarden.send.SendView
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.FileData
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
@ -30,8 +31,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.CreateSendResult
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.data.vault.repository.model.RemovePasswordSendResult
import com.x8bit.bitwarden.data.vault.repository.model.UpdateSendResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.model.AddEditSendType
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.util.toSendView
import com.x8bit.bitwarden.ui.tools.feature.send.addedit.util.toViewState
@ -92,7 +92,7 @@ class AddEditSendViewModelTest : BaseViewModelTest() {
private val networkConnectionManager = mockk<NetworkConnectionManager> {
every { isNetworkConnected } returns true
}
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = any()) } just runs
}

View File

@ -8,6 +8,7 @@ import com.bitwarden.data.repository.model.Environment
import com.bitwarden.send.SendView
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.bitwarden.ui.util.concat
@ -16,8 +17,7 @@ import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.vault.datasource.sdk.model.createMockSendView
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteSendResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.tools.feature.send.viewsend.util.toViewSendViewStateContent
import io.mockk.coEvery
@ -53,7 +53,7 @@ class ViewSendViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = any()) } just runs
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())

View File

@ -20,6 +20,7 @@ import com.bitwarden.network.model.SyncResponseJson
import com.bitwarden.send.SendView
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.TotpData
import com.bitwarden.ui.platform.resource.BitwardenPlurals
import com.bitwarden.ui.platform.resource.BitwardenString
@ -79,8 +80,7 @@ import com.x8bit.bitwarden.data.vault.repository.model.UpdateCipherResult
import com.x8bit.bitwarden.data.vault.repository.model.VaultData
import com.x8bit.bitwarden.ui.credentials.manager.model.RegisterFido2CredentialResult
import com.x8bit.bitwarden.ui.platform.manager.resource.ResourceManager
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.generator.model.GeneratorMode
import com.x8bit.bitwarden.ui.vault.feature.addedit.model.CustomFieldAction
import com.x8bit.bitwarden.ui.vault.feature.addedit.model.CustomFieldType
@ -210,7 +210,7 @@ class VaultAddEditViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -5,14 +5,14 @@ import app.cash.turbine.test
import com.bitwarden.data.repository.model.Environment
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.x8bit.bitwarden.data.platform.manager.FirstTimeActionManager
import com.x8bit.bitwarden.data.platform.repository.EnvironmentRepository
import com.x8bit.bitwarden.data.vault.manager.model.SyncVaultDataResult
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManagerImpl
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import io.mockk.coEvery
import io.mockk.coVerify
import io.mockk.every
@ -60,7 +60,7 @@ class ImportLoginsViewModelTest : BaseViewModelTest() {
unmockkStatic(Uri::parse)
}
private val snackbarRelayManager: SnackbarRelayManagerImpl = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
coEvery { sendSnackbarData(any(), any()) } just runs
}

View File

@ -12,6 +12,7 @@ import com.bitwarden.network.model.OrganizationType
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenDrawable
import com.bitwarden.ui.platform.resource.BitwardenPlurals
import com.bitwarden.ui.platform.resource.BitwardenString
@ -43,8 +44,7 @@ import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.DeleteCipherResult
import com.x8bit.bitwarden.data.vault.repository.model.DownloadAttachmentResult
import com.x8bit.bitwarden.data.vault.repository.model.RestoreCipherResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.item.model.TotpCodeItemData
import com.x8bit.bitwarden.ui.vault.feature.item.model.VaultItemLocation
import com.x8bit.bitwarden.ui.vault.feature.item.util.createCommonContent
@ -121,7 +121,7 @@ class VaultItemViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -31,6 +31,7 @@ import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.icon.model.IconData
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.model.TotpData
import com.bitwarden.ui.platform.resource.BitwardenDrawable
import com.bitwarden.ui.platform.resource.BitwardenString
@ -102,7 +103,7 @@ import com.x8bit.bitwarden.ui.credentials.manager.model.GetCredentialsResult
import com.x8bit.bitwarden.ui.credentials.manager.model.GetPasswordCredentialResult
import com.x8bit.bitwarden.ui.credentials.manager.model.RegisterFido2CredentialResult
import com.x8bit.bitwarden.ui.platform.feature.search.model.SearchType
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.tools.feature.send.model.SendItemType
import com.x8bit.bitwarden.ui.vault.components.model.CreateVaultItemType
import com.x8bit.bitwarden.ui.vault.feature.addedit.util.createMockPasskeyAttestationOptions
@ -281,7 +282,7 @@ class VaultItemListingViewModelTest : BaseViewModelTest() {
}
private val mutableSnackbarDataFlow: MutableSharedFlow<BitwardenSnackbarData> =
bufferedMutableSharedFlow()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every {
getSnackbarDataFlow(relay = any(), relays = anyVararg())
} returns mutableSnackbarDataFlow

View File

@ -8,6 +8,7 @@ import com.bitwarden.data.repository.model.Environment
import com.bitwarden.network.model.OrganizationType
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.asText
import com.bitwarden.ui.util.concat
@ -21,8 +22,7 @@ import com.x8bit.bitwarden.data.vault.datasource.sdk.model.createMockCipherView
import com.x8bit.bitwarden.data.vault.datasource.sdk.model.createMockCollectionView
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.ShareCipherResult
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.feature.movetoorganization.util.createMockOrganizationList
import com.x8bit.bitwarden.ui.vault.model.VaultCollection
import io.mockk.coEvery
@ -63,7 +63,7 @@ class VaultMoveToOrganizationViewModelTest : BaseViewModelTest() {
every { userStateFlow } returns mutableUserStateFlow
}
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
every { sendSnackbarData(data = any(), relay = any()) } just runs
}

View File

@ -12,6 +12,7 @@ import com.bitwarden.network.model.SyncResponseJson
import com.bitwarden.ui.platform.base.BaseViewModelTest
import com.bitwarden.ui.platform.components.account.model.AccountSummary
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import com.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.bitwarden.ui.platform.resource.BitwardenString
import com.bitwarden.ui.util.Text
import com.bitwarden.ui.util.asText
@ -57,8 +58,7 @@ import com.x8bit.bitwarden.data.vault.manager.model.GetCipherResult
import com.x8bit.bitwarden.data.vault.repository.VaultRepository
import com.x8bit.bitwarden.data.vault.repository.model.GenerateTotpResult
import com.x8bit.bitwarden.data.vault.repository.model.VaultData
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelay
import com.x8bit.bitwarden.ui.platform.manager.snackbar.SnackbarRelayManager
import com.x8bit.bitwarden.ui.platform.model.SnackbarRelay
import com.x8bit.bitwarden.ui.vault.components.model.CreateVaultItemType
import com.x8bit.bitwarden.ui.vault.feature.itemlisting.model.ListingItemOverflowAction
import com.x8bit.bitwarden.ui.vault.feature.vault.model.VaultFilterData
@ -100,7 +100,7 @@ class VaultViewModelTest : BaseViewModelTest() {
)
private val mutableSnackbarDataFlow = bufferedMutableSharedFlow<BitwardenSnackbarData>()
private val snackbarRelayManager: SnackbarRelayManager = mockk {
private val snackbarRelayManager: SnackbarRelayManager<SnackbarRelay> = mockk {
// We return an empty flow here to avoid confusion in the tests.
// Everything should be tested via the mutableSnackbarDataFlow.
every { getSnackbarDataFlow(SnackbarRelay.LOGIN_SUCCESS) } returns emptyFlow()

View File

@ -82,6 +82,9 @@ dependencies {
debugImplementation(libs.androidx.compose.ui.test.manifest)
debugImplementation(libs.androidx.compose.ui.tooling)
// Pull in test fixtures from other modules
testImplementation(testFixtures(project(":core")))
testImplementation(platform(libs.junit.bom))
testImplementation(libs.junit.jupiter)
testRuntimeOnly(libs.junit.platform.launcher)
@ -89,6 +92,7 @@ dependencies {
testImplementation(libs.mockk.mockk)
testImplementation(libs.robolectric.robolectric)
testImplementation(libs.androidx.compose.ui.test)
testImplementation(libs.square.turbine)
testFixturesImplementation(libs.androidx.activity.compose)
testFixturesImplementation(libs.androidx.camera.camera2)

View File

@ -1,25 +1,22 @@
package com.x8bit.bitwarden.ui.platform.manager.snackbar
package com.bitwarden.ui.platform.manager.snackbar
import com.bitwarden.ui.platform.components.snackbar.model.BitwardenSnackbarData
import kotlinx.coroutines.flow.Flow
/**
* Manager responsible for relaying snackbar data between a producer and consumer who may
* communicate with reference to a specific [SnackbarRelay].
* communicate with reference to a specific relay [T].
*/
interface SnackbarRelayManager {
interface SnackbarRelayManager<T : Any> {
/**
* Called from a producer to send snackbar data to a consumer, the producer must
* specify the [relay] to send the data to.
*/
fun sendSnackbarData(data: BitwardenSnackbarData, relay: SnackbarRelay)
fun sendSnackbarData(data: BitwardenSnackbarData, relay: T)
/**
* Called from a consumer to receive snackbar data from a producer, the consumer must specify
* the [relay] or [relays] to receive the data from.
*/
fun getSnackbarDataFlow(
relay: SnackbarRelay,
vararg relays: SnackbarRelay,
): Flow<BitwardenSnackbarData>
fun getSnackbarDataFlow(relay: T, vararg relays: T): Flow<BitwardenSnackbarData>
}

View File

@ -1,4 +1,4 @@
package com.x8bit.bitwarden.ui.platform.manager.snackbar
package com.bitwarden.ui.platform.manager.snackbar
import com.bitwarden.core.data.manager.dispatcher.DispatcherManager
import com.bitwarden.core.data.repository.util.emitWhenSubscribedTo
@ -18,13 +18,13 @@ import java.util.UUID
/**
* The default implementation of the [SnackbarRelayManager] interface.
*/
class SnackbarRelayManagerImpl(
class SnackbarRelayManagerImpl<T : Any>(
dispatcherManager: DispatcherManager,
) : SnackbarRelayManager {
) : SnackbarRelayManager<T> {
private val unconfinedScope = CoroutineScope(context = dispatcherManager.unconfined)
private val snackbarSharedFlow = SnackbarLastSubscriberMutableSharedFlow()
private val snackbarSharedFlow = SnackbarLastSubscriberMutableSharedFlow<T>()
override fun sendSnackbarData(data: BitwardenSnackbarData, relay: SnackbarRelay) {
override fun sendSnackbarData(data: BitwardenSnackbarData, relay: T) {
unconfinedScope.launch {
snackbarSharedFlow.emitWhenSubscribedTo(
value = SnackbarDataAndRelay(
@ -35,10 +35,7 @@ class SnackbarRelayManagerImpl(
}
}
override fun getSnackbarDataFlow(
relay: SnackbarRelay,
vararg relays: SnackbarRelay,
): Flow<BitwardenSnackbarData> =
override fun getSnackbarDataFlow(relay: T, vararg relays: T): Flow<BitwardenSnackbarData> =
merge(
snackbarSharedFlow.generateFlowFor(relay = relay),
*relays.map { snackbarSharedFlow.generateFlowFor(relay = it) }.toTypedArray(),
@ -47,10 +44,10 @@ class SnackbarRelayManagerImpl(
}
/**
* A wrapper for the [BitwardenSnackbarData] payload and [SnackbarRelay] associated with it.
* A wrapper for the [BitwardenSnackbarData] payload and relay [T] associated with it.
*/
private data class SnackbarDataAndRelay(
val relay: SnackbarRelay,
private data class SnackbarDataAndRelay<T : Any>(
val relay: T,
val data: BitwardenSnackbarData,
)
@ -59,14 +56,14 @@ private data class SnackbarDataAndRelay(
* data.
*/
@OptIn(ExperimentalForInheritanceCoroutinesApi::class)
private class SnackbarLastSubscriberMutableSharedFlow(
private val source: MutableSharedFlow<SnackbarDataAndRelay> = MutableSharedFlow(),
) : MutableSharedFlow<SnackbarDataAndRelay> by source {
private val mutableRelayUuidMap: MutableMap<SnackbarRelay, MutableList<UUID>> = mutableMapOf()
private class SnackbarLastSubscriberMutableSharedFlow<T : Any>(
private val source: MutableSharedFlow<SnackbarDataAndRelay<T>> = MutableSharedFlow(),
) : MutableSharedFlow<SnackbarDataAndRelay<T>> by source {
private val mutableRelayUuidMap: MutableMap<T, MutableList<UUID>> = mutableMapOf()
fun generateFlowFor(
relay: SnackbarRelay,
): Flow<SnackbarDataAndRelay> {
relay: T,
): Flow<SnackbarDataAndRelay<T>> {
lateinit var uuid: UUID
return source
.onSubscription {
@ -78,6 +75,6 @@ private class SnackbarLastSubscriberMutableSharedFlow(
}
private fun getUuidStack(
relay: SnackbarRelay,
relay: T,
): MutableList<UUID> = mutableRelayUuidMap.getOrPut(key = relay) { mutableListOf() }
}

View File

@ -1,4 +1,4 @@
package com.x8bit.bitwarden.ui.platform.manager.snackbar
package com.bitwarden.ui.platform.manager.snackbar
import app.cash.turbine.test
import app.cash.turbine.turbineScope
@ -11,14 +11,14 @@ import org.junit.jupiter.api.Assertions.assertEquals
class SnackbarRelayManagerTest {
private val relayManager: SnackbarRelayManager = SnackbarRelayManagerImpl(
private val relayManager: SnackbarRelayManager<TestRelay> = SnackbarRelayManagerImpl(
dispatcherManager = FakeDispatcherManager(),
)
@Test
fun `when relay is completed successfully when consumer registers first and event is sent`() =
runTest {
val relay = SnackbarRelay.LOGINS_IMPORTED
val relay = TestRelay.TEST1
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
relayManager.getSnackbarDataFlow(relay).test {
@ -30,7 +30,7 @@ class SnackbarRelayManagerTest {
@Test
fun `when relay is completed successfully when consumer registers second and event is sent`() =
runTest {
val relay = SnackbarRelay.LOGINS_IMPORTED
val relay = TestRelay.TEST1
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
// producer code
relayManager.sendSnackbarData(data = expectedData, relay = relay)
@ -41,8 +41,8 @@ class SnackbarRelayManagerTest {
@Test
fun `when relay is specified by producer only send data to that relay`() = runTest {
val relay1 = SnackbarRelay.LOGINS_IMPORTED
val relay2 = SnackbarRelay.SEND_DELETED
val relay1 = TestRelay.TEST1
val relay2 = TestRelay.TEST2
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
turbineScope {
val consumer1 = relayManager.getSnackbarDataFlow(relay1).testIn(backgroundScope)
@ -56,7 +56,7 @@ class SnackbarRelayManagerTest {
@Test
fun `when multiple consumers are registered to the same relay, send data to last consumers`() =
runTest {
val relay = SnackbarRelay.LOGINS_IMPORTED
val relay = TestRelay.TEST1
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
turbineScope {
val consumer1 = relayManager.getSnackbarDataFlow(relay).testIn(backgroundScope)
@ -71,7 +71,7 @@ class SnackbarRelayManagerTest {
@Test
fun `when multiple consumers are registered to the same relay, and one is completed before the other the second consumer registers should not receive any emissions`() =
runTest {
val relay = SnackbarRelay.LOGINS_IMPORTED
val relay = TestRelay.TEST1
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
turbineScope {
val consumer1 = relayManager.getSnackbarDataFlow(relay).testIn(backgroundScope)
@ -87,7 +87,7 @@ class SnackbarRelayManagerTest {
@Test
fun `when multiple consumers are registered to the same relay, and the last one is cancelled, the other most recent consumer should receive the emissions`() =
runTest {
val relay = SnackbarRelay.LOGINS_IMPORTED
val relay = TestRelay.TEST1
val expectedData = BitwardenSnackbarData(message = "Test message".asText())
turbineScope {
val consumer1 = relayManager.getSnackbarDataFlow(relay).testIn(backgroundScope)
@ -98,3 +98,8 @@ class SnackbarRelayManagerTest {
}
}
}
private enum class TestRelay {
TEST1,
TEST2,
}