mirror of
https://github.com/bitwarden/android.git
synced 2026-05-31 09:46:08 -05:00
BIT-1304: Options menu UI for view item (#580)
This commit is contained in:
@@ -1,15 +1,18 @@
|
||||
package com.x8bit.bitwarden.ui.vault.feature.item
|
||||
|
||||
import androidx.compose.ui.test.assert
|
||||
import androidx.compose.ui.test.assertCountEquals
|
||||
import androidx.compose.ui.test.assertIsDisplayed
|
||||
import androidx.compose.ui.test.assertIsEnabled
|
||||
import androidx.compose.ui.test.assertIsNotEnabled
|
||||
import androidx.compose.ui.test.assertTextContains
|
||||
import androidx.compose.ui.test.assertTextEquals
|
||||
import androidx.compose.ui.test.filter
|
||||
import androidx.compose.ui.test.filterToOne
|
||||
import androidx.compose.ui.test.hasAnyAncestor
|
||||
import androidx.compose.ui.test.hasContentDescription
|
||||
import androidx.compose.ui.test.isDialog
|
||||
import androidx.compose.ui.test.isPopup
|
||||
import androidx.compose.ui.test.onAllNodesWithContentDescription
|
||||
import androidx.compose.ui.test.onAllNodesWithText
|
||||
import androidx.compose.ui.test.onChildren
|
||||
@@ -64,16 +67,17 @@ class VaultItemScreenTest : BaseComposeTest() {
|
||||
VaultItemScreen(
|
||||
viewModel = viewModel,
|
||||
onNavigateBack = { onNavigateBackCalled = true },
|
||||
onNavigateToVaultEditItem = { onNavigateToVaultEditItemId = it },
|
||||
onNavigateToVaultAddEditItem = { onNavigateToVaultEditItemId = it },
|
||||
intentHandler = intentHandler,
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
//region common
|
||||
@Test
|
||||
fun `NavigateToEdit event should invoke onNavigateToVaultEditItem`() {
|
||||
val id = "id1234"
|
||||
mutableEventFlow.tryEmit(VaultItemEvent.NavigateToEdit(id))
|
||||
mutableEventFlow.tryEmit(VaultItemEvent.NavigateToAddEdit(itemId = id, isClone = false))
|
||||
assertEquals(id, onNavigateToVaultEditItemId)
|
||||
}
|
||||
|
||||
@@ -544,6 +548,84 @@ class VaultItemScreenTest : BaseComposeTest() {
|
||||
.assertDoesNotExist()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Delete option menu click should send DeleteClick action`() {
|
||||
// Confirm dropdown version of item is absent
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Delete")
|
||||
.filter(hasAnyAncestor(isPopup()))
|
||||
.assertCountEquals(0)
|
||||
// Open the overflow menu
|
||||
composeTestRule.onNodeWithContentDescription("More").performClick()
|
||||
// Click on the delete item in the dropdown
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Delete")
|
||||
.filterToOne(hasAnyAncestor(isPopup()))
|
||||
.performClick()
|
||||
verify {
|
||||
viewModel.trySendAction(VaultItemAction.Common.DeleteClick)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Attachments option menu click should send AttachmentsClick action`() {
|
||||
// Confirm dropdown version of item is absent
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Attachments")
|
||||
.filter(hasAnyAncestor(isPopup()))
|
||||
.assertCountEquals(0)
|
||||
// Open the overflow menu
|
||||
composeTestRule.onNodeWithContentDescription("More").performClick()
|
||||
// Click on the attachments hint item in the dropdown
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Attachments")
|
||||
.filterToOne(hasAnyAncestor(isPopup()))
|
||||
.performClick()
|
||||
verify {
|
||||
viewModel.trySendAction(VaultItemAction.Common.AttachmentsClick)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Clone option menu click should send CloneClick action`() {
|
||||
// Confirm dropdown version of item is absent
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Clone")
|
||||
.filter(hasAnyAncestor(isPopup()))
|
||||
.assertCountEquals(0)
|
||||
// Open the overflow menu
|
||||
composeTestRule.onNodeWithContentDescription("More").performClick()
|
||||
// Click on the clone item in the dropdown
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Clone")
|
||||
.filterToOne(hasAnyAncestor(isPopup()))
|
||||
.performClick()
|
||||
verify {
|
||||
viewModel.trySendAction(VaultItemAction.Common.CloneClick)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `Move to organization option menu click should send MoveToOrganizationClick action`() {
|
||||
// Confirm dropdown version of item is absent
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Move to Organization")
|
||||
.filter(hasAnyAncestor(isPopup()))
|
||||
.assertCountEquals(0)
|
||||
// Open the overflow menu
|
||||
composeTestRule.onNodeWithContentDescription("More").performClick()
|
||||
// Click on the move to organization hint item in the dropdown
|
||||
composeTestRule
|
||||
.onAllNodesWithText("Move to Organization")
|
||||
.filterToOne(hasAnyAncestor(isPopup()))
|
||||
.performClick()
|
||||
verify {
|
||||
viewModel.trySendAction(VaultItemAction.Common.MoveToOrganizationClick)
|
||||
}
|
||||
}
|
||||
//endregion common
|
||||
|
||||
//region login
|
||||
@Test
|
||||
fun `in login state, linked custom fields should be displayed according to state`() {
|
||||
val linkedFieldUserName =
|
||||
@@ -947,7 +1029,9 @@ class VaultItemScreenTest : BaseComposeTest() {
|
||||
composeTestRule.assertScrollableNodeDoesNotExist("Password history: ")
|
||||
composeTestRule.assertScrollableNodeDoesNotExist("1")
|
||||
}
|
||||
//endregion login
|
||||
|
||||
//region identity
|
||||
@Test
|
||||
fun `in identity state, identityName should be displayed according to state`() {
|
||||
val identityName = "the identity name"
|
||||
@@ -1064,6 +1148,7 @@ class VaultItemScreenTest : BaseComposeTest() {
|
||||
|
||||
composeTestRule.assertScrollableNodeDoesNotExist(identityName)
|
||||
}
|
||||
//endregion identity
|
||||
|
||||
@Test
|
||||
fun `in card state, cardholderName should be displayed according to state`() {
|
||||
|
||||
@@ -149,7 +149,13 @@ class VaultItemViewModelTest : BaseViewModelTest() {
|
||||
|
||||
viewModel.eventFlow.test {
|
||||
viewModel.trySendAction(VaultItemAction.Common.EditClick)
|
||||
assertEquals(VaultItemEvent.NavigateToEdit(VAULT_ITEM_ID), awaitItem())
|
||||
assertEquals(
|
||||
VaultItemEvent.NavigateToAddEdit(
|
||||
itemId = VAULT_ITEM_ID,
|
||||
isClone = false,
|
||||
),
|
||||
awaitItem(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -327,6 +333,57 @@ class VaultItemViewModelTest : BaseViewModelTest() {
|
||||
mockCipherView.toViewState(isPremiumUser = true)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `on DeleteClick should emit ShowToast`() = runTest {
|
||||
val viewModel = createViewModel(state = DEFAULT_STATE)
|
||||
viewModel.eventFlow.test {
|
||||
viewModel.trySendAction(VaultItemAction.Common.DeleteClick)
|
||||
assertEquals(
|
||||
VaultItemEvent.ShowToast("Not yet implemented.".asText()),
|
||||
awaitItem(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `on AttachmentsClick should emit NavigateToAttachments`() = runTest {
|
||||
val viewModel = createViewModel(state = DEFAULT_STATE)
|
||||
viewModel.eventFlow.test {
|
||||
viewModel.trySendAction(VaultItemAction.Common.AttachmentsClick)
|
||||
assertEquals(
|
||||
VaultItemEvent.NavigateToAttachments(itemId = VAULT_ITEM_ID),
|
||||
awaitItem(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `on CloneClick should emit NavigateToAddEdit with isClone set to true`() = runTest {
|
||||
val viewModel = createViewModel(state = DEFAULT_STATE)
|
||||
viewModel.eventFlow.test {
|
||||
viewModel.trySendAction(VaultItemAction.Common.CloneClick)
|
||||
assertEquals(
|
||||
VaultItemEvent.NavigateToAddEdit(
|
||||
itemId = VAULT_ITEM_ID,
|
||||
isClone = true,
|
||||
),
|
||||
awaitItem(),
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
fun `on MoveToOrganizationClick should emit NavigateToMoveToOrganization`() = runTest {
|
||||
val viewModel = createViewModel(state = DEFAULT_STATE)
|
||||
viewModel.eventFlow.test {
|
||||
viewModel.trySendAction(VaultItemAction.Common.MoveToOrganizationClick)
|
||||
assertEquals(
|
||||
VaultItemEvent.NavigateToMoveToOrganization(itemId = VAULT_ITEM_ID),
|
||||
awaitItem(),
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Nested
|
||||
|
||||
Reference in New Issue
Block a user