Skip to content

Commit

Permalink
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add SSH key cipher type
Browse files Browse the repository at this point in the history
SaintPatrck committed Oct 28, 2024

Verified

This commit was signed with the committer’s verified signature.
snyk-bot Snyk bot
1 parent 064db9f commit 0e0e0b8
Showing 73 changed files with 2,451 additions and 33 deletions.
Original file line number Diff line number Diff line change
@@ -21,7 +21,6 @@ private const val CARD_DIGITS_DISPLAYED: Int = 4
val CipherView.subtitle: String?
get() = when (type) {
CipherType.LOGIN -> this.login?.username.orEmpty()
CipherType.SECURE_NOTE -> null
CipherType.CARD -> {
this
.card
@@ -45,6 +44,10 @@ val CipherView.subtitle: String?
}
}
}

CipherType.SECURE_NOTE,
CipherType.SSH_KEY,
-> null
}

/**
Original file line number Diff line number Diff line change
@@ -51,6 +51,9 @@ data class CipherJsonRequest(
@SerialName("secureNote")
val secureNote: SyncResponseJson.Cipher.SecureNote?,

@SerialName("sshKey")
val sshKey: SyncResponseJson.Cipher.SshKey?,

@SerialName("folderId")
val folderId: String?,

Original file line number Diff line number Diff line change
@@ -33,6 +33,12 @@ enum class CipherTypeJson {
*/
@SerialName("4")
IDENTITY,

/**
* A SSH key.
*/
@SerialName("5")
SSH_KEY,
}

@Keep
Original file line number Diff line number Diff line change
@@ -472,6 +472,9 @@ data class SyncResponseJson(
@SerialName("identity")
val identity: Identity?,

@SerialName("sshKey")
val sshKey: SshKey?,

@SerialName("collectionIds")
val collectionIds: List<String>?,

@@ -718,6 +721,25 @@ data class SyncResponseJson(
)
}

/**
* Represents a SSH key in the vault response.
*
* @property publicKey The public key of the SSH key.
* @property privateKey The private key of the SSH key.
* @property keyFingerprint The key fingerprint of the SSH key.
*/
@Serializable
data class SshKey(
@SerialName("publicKey")
val publicKey: String?,

@SerialName("privateKey")
val privateKey: String?,

@SerialName("keyFingerprint")
val keyFingerprint: String?,
)

/**
* Represents password history in the vault response.
*
Original file line number Diff line number Diff line change
@@ -17,6 +17,7 @@ import com.bitwarden.vault.LoginUri
import com.bitwarden.vault.PasswordHistory
import com.bitwarden.vault.SecureNote
import com.bitwarden.vault.SecureNoteType
import com.bitwarden.vault.SshKey
import com.bitwarden.vault.UriMatchType
import com.x8bit.bitwarden.data.platform.util.SpecialCharWithPrecedenceComparator
import com.x8bit.bitwarden.data.vault.datasource.network.model.AttachmentJsonRequest
@@ -55,6 +56,7 @@ fun Cipher.toEncryptedNetworkCipher(): CipherJsonRequest =
isFavorite = favorite,
card = card?.toEncryptedNetworkCard(),
key = key,
sshKey = sshKey?.toEncryptedNetworkSshKey(),
)

/**
@@ -77,6 +79,7 @@ fun Cipher.toEncryptedNetworkCipherResponse(): SyncResponseJson.Cipher =
isFavorite = favorite,
card = card?.toEncryptedNetworkCard(),
attachments = attachments?.toNetworkAttachmentList(),
sshKey = sshKey?.toEncryptedNetworkSshKey(),
shouldOrganizationUseTotp = organizationUseTotp,
shouldEdit = edit,
revisionDate = ZonedDateTime.ofInstant(revisionDate, ZoneOffset.UTC),
@@ -102,6 +105,13 @@ private fun Card.toEncryptedNetworkCard(): SyncResponseJson.Cipher.Card =
brand = brand,
)

private fun SshKey.toEncryptedNetworkSshKey(): SyncResponseJson.Cipher.SshKey =
SyncResponseJson.Cipher.SshKey(
publicKey = publicKey,
privateKey = privateKey,
keyFingerprint = fingerprint,
)

/**
* Converts a list of Bitwarden SDK [Field] objects to a corresponding
* list of [SyncResponseJson.Cipher.Field] objects.
@@ -309,6 +319,7 @@ private fun CipherType.toNetworkCipherType(): CipherTypeJson =
CipherType.SECURE_NOTE -> CipherTypeJson.SECURE_NOTE
CipherType.CARD -> CipherTypeJson.CARD
CipherType.IDENTITY -> CipherTypeJson.IDENTITY
CipherType.SSH_KEY -> CipherTypeJson.SSH_KEY

Check warning on line 322 in app/src/main/java/com/x8bit/bitwarden/data/vault/repository/util/VaultSdkCipherExtensions.kt

Codecov / codecov/patch

app/src/main/java/com/x8bit/bitwarden/data/vault/repository/util/VaultSdkCipherExtensions.kt#L322

Added line #L322 was not covered by tests
}

/**
@@ -334,6 +345,7 @@ fun SyncResponseJson.Cipher.toEncryptedSdkCipher(): Cipher =
type = type.toSdkCipherType(),
login = login?.toSdkLogin(),
identity = identity?.toSdkIdentity(),
sshKey = sshKey?.toSdkSshKey(),
card = card?.toSdkCard(),
secureNote = secureNote?.toSdkSecureNote(),
favorite = isFavorite,
@@ -432,6 +444,17 @@ fun SyncResponseJson.Cipher.SecureNote.toSdkSecureNote(): SecureNote =
},
)

/**
* Transforms a [SyncResponseJson.Cipher.SshKey] into
* the corresponding Bitwarden SDK [SshKey].
*/
fun SyncResponseJson.Cipher.SshKey.toSdkSshKey(): SshKey =
SshKey(
publicKey = publicKey,
privateKey = privateKey,
fingerprint = keyFingerprint,
)

/**
* Transforms a list of [SyncResponseJson.Cipher.Login.Uri] into
* a corresponding list of Bitwarden SDK [LoginUri].
@@ -517,6 +540,7 @@ fun CipherTypeJson.toSdkCipherType(): CipherType =
CipherTypeJson.SECURE_NOTE -> CipherType.SECURE_NOTE
CipherTypeJson.CARD -> CipherType.CARD
CipherTypeJson.IDENTITY -> CipherType.IDENTITY
CipherTypeJson.SSH_KEY -> CipherType.SSH_KEY

Check warning on line 543 in app/src/main/java/com/x8bit/bitwarden/data/vault/repository/util/VaultSdkCipherExtensions.kt

Codecov / codecov/patch

app/src/main/java/com/x8bit/bitwarden/data/vault/repository/util/VaultSdkCipherExtensions.kt#L543

Added line #L543 was not covered by tests
}

/**
Original file line number Diff line number Diff line change
@@ -26,6 +26,7 @@ private const val SEARCH_TYPE_VAULT_TRASH: String = "search_type_vault_trash"
private const val SEARCH_TYPE_VAULT_VERIFICATION_CODES: String =
"search_type_vault_verification_codes"
private const val SEARCH_TYPE_ID: String = "search_type_id"
private const val SEARCH_TYPE_VAULT_SSH_KEYS: String = "search_type_vault_ssh_keys"

private const val SEARCH_ROUTE_PREFIX: String = "search"
private const val SEARCH_ROUTE: String = "$SEARCH_ROUTE_PREFIX/{$SEARCH_TYPE}/{$SEARCH_TYPE_ID}"
@@ -122,6 +123,7 @@ private fun SearchType.toTypeString(): String =
SearchType.Vault.SecureNotes -> SEARCH_TYPE_VAULT_SECURE_NOTES
SearchType.Vault.Trash -> SEARCH_TYPE_VAULT_TRASH
SearchType.Vault.VerificationCodes -> SEARCH_TYPE_VAULT_VERIFICATION_CODES
SearchType.Vault.SshKeys -> SEARCH_TYPE_VAULT_SSH_KEYS
}

private fun SearchType.toIdOrNull(): String? =
@@ -139,4 +141,5 @@ private fun SearchType.toIdOrNull(): String? =
SearchType.Vault.SecureNotes -> null
SearchType.Vault.Trash -> null
SearchType.Vault.VerificationCodes -> null
SearchType.Vault.SshKeys -> null
}
Original file line number Diff line number Diff line change
@@ -11,6 +11,7 @@ import com.x8bit.bitwarden.data.auth.repository.model.ValidatePasswordResult
import com.x8bit.bitwarden.data.autofill.accessibility.manager.AccessibilitySelectionManager
import com.x8bit.bitwarden.data.autofill.manager.AutofillSelectionManager
import com.x8bit.bitwarden.data.autofill.model.AutofillSelectionData
import com.x8bit.bitwarden.data.platform.annotation.OmitFromCoverage
import com.x8bit.bitwarden.data.platform.manager.PolicyManager
import com.x8bit.bitwarden.data.platform.manager.SpecialCircumstanceManager
import com.x8bit.bitwarden.data.platform.manager.clipboard.BitwardenClipboardManager
@@ -876,6 +877,7 @@ sealed class SearchTypeData : Parcelable {
* Indicates that we should be searching vault items.
*/
@Parcelize
@OmitFromCoverage
sealed class Vault : SearchTypeData() {
/**
* Indicates that we should be searching all vault items.
@@ -924,6 +926,16 @@ sealed class SearchTypeData : Parcelable {
.concat(R.string.secure_notes.asText())
}

/**
* Indicates that we should be searching only ssh key ciphers.
*/
data object SshKeys : Vault() {
override val title: Text
get() = R.string.search.asText()
.concat(" ".asText())
.concat(R.string.ssh_keys.asText())
}

Check warning on line 937 in app/src/main/java/com/x8bit/bitwarden/ui/platform/feature/search/SearchViewModel.kt

Codecov / codecov/patch

app/src/main/java/com/x8bit/bitwarden/ui/platform/feature/search/SearchViewModel.kt#L937

Added line #L937 was not covered by tests

/**
* Indicates that we should be searching only ciphers in the given collection.
*/
Original file line number Diff line number Diff line change
@@ -58,6 +58,11 @@ sealed class SearchType : Parcelable {
*/
data object SecureNotes : Vault()

/**
* Indicates that we should be searching only SSH key ciphers.
*/
data object SshKeys : Vault()

/**
* Indicates that we should be searching only ciphers in the given collection.
*/
Original file line number Diff line number Diff line change
@@ -62,6 +62,7 @@ fun SearchTypeData.updateWithAdditionalDataIfNecessary(
SearchTypeData.Vault.SecureNotes -> this
SearchTypeData.Vault.Trash -> this
SearchTypeData.Vault.VerificationCodes -> this
SearchTypeData.Vault.SshKeys -> this
}

/**
@@ -114,6 +115,7 @@ private fun CipherView.filterBySearchType(
is SearchTypeData.Vault.Identities -> type == CipherType.IDENTITY && deletedDate == null
is SearchTypeData.Vault.Logins -> type == CipherType.LOGIN && deletedDate == null
is SearchTypeData.Vault.SecureNotes -> type == CipherType.SECURE_NOTE && deletedDate == null
is SearchTypeData.Vault.SshKeys -> type == CipherType.SSH_KEY && deletedDate == null
is SearchTypeData.Vault.VerificationCodes -> login?.totp != null && deletedDate == null
is SearchTypeData.Vault.Trash -> deletedDate != null
}
@@ -255,6 +257,7 @@ private val CipherType.iconRes: Int
CipherType.SECURE_NOTE -> R.drawable.ic_note
CipherType.CARD -> R.drawable.ic_payment_card
CipherType.IDENTITY -> R.drawable.ic_id_card
CipherType.SSH_KEY -> R.drawable.ic_ssh_key

Check warning on line 260 in app/src/main/java/com/x8bit/bitwarden/ui/platform/feature/search/util/SearchTypeDataExtensions.kt

Codecov / codecov/patch

app/src/main/java/com/x8bit/bitwarden/ui/platform/feature/search/util/SearchTypeDataExtensions.kt#L260

Added line #L260 was not covered by tests
}

/**
Original file line number Diff line number Diff line change
@@ -21,4 +21,5 @@ fun SearchType.toSearchTypeData(): SearchTypeData =
SearchType.Vault.SecureNotes -> SearchTypeData.Vault.SecureNotes
SearchType.Vault.Trash -> SearchTypeData.Vault.Trash
SearchType.Vault.VerificationCodes -> SearchTypeData.Vault.VerificationCodes
SearchType.Vault.SshKeys -> SearchTypeData.Vault.SshKeys
}
Original file line number Diff line number Diff line change
@@ -21,21 +21,24 @@ import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditCardTyp
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditCommonHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditIdentityTypeHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditLoginTypeHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditSshKeyTypeHandlers
import kotlinx.collections.immutable.toImmutableList

/**
* The top level content UI state for the [VaultAddEditScreen].
*/
@Composable
@Suppress("LongMethod")
@Suppress("LongMethod", "CyclomaticComplexMethod")
fun VaultAddEditContent(
state: VaultAddEditState.ViewState.Content,
isAddItemMode: Boolean,
typeOptions: List<VaultAddEditState.ItemTypeOption>,
onTypeOptionClicked: (VaultAddEditState.ItemTypeOption) -> Unit,
commonTypeHandlers: VaultAddEditCommonHandlers,
loginItemTypeHandlers: VaultAddEditLoginTypeHandlers,
identityItemTypeHandlers: VaultAddEditIdentityTypeHandlers,
cardItemTypeHandlers: VaultAddEditCardTypeHandlers,
sshKeyItemTypeHandlers: VaultAddEditSshKeyTypeHandlers,
modifier: Modifier = Modifier,
permissionsManager: PermissionsManager,
) {
@@ -45,6 +48,7 @@ fun VaultAddEditContent(
is VaultAddEditState.ViewState.Content.ItemType.SecureNotes -> Unit
is VaultAddEditState.ViewState.Content.ItemType.Card -> Unit
is VaultAddEditState.ViewState.Content.ItemType.Identity -> Unit
is VaultAddEditState.ViewState.Content.ItemType.SshKey -> Unit
is VaultAddEditState.ViewState.Content.ItemType.Login -> {
loginItemTypeHandlers.onSetupTotpClick(isGranted)
}
@@ -77,6 +81,7 @@ fun VaultAddEditContent(
item {
Spacer(modifier = Modifier.height(8.dp))
TypeOptionsItem(
entries = typeOptions,
itemType = state.type,
onTypeOptionClicked = onTypeOptionClicked,
modifier = Modifier
@@ -131,6 +136,15 @@ fun VaultAddEditContent(
commonTypeHandlers = commonTypeHandlers,
)
}

is VaultAddEditState.ViewState.Content.ItemType.SshKey -> {
vaultAddEditSshKeyItems(
commonState = state.common,
sshKeyState = state.type,
commonTypeHandlers = commonTypeHandlers,
sshKeyTypeHandlers = sshKeyItemTypeHandlers,
)
}
}

item {
@@ -141,12 +155,12 @@ fun VaultAddEditContent(

@Composable
private fun TypeOptionsItem(
entries: List<VaultAddEditState.ItemTypeOption>,
itemType: VaultAddEditState.ViewState.Content.ItemType,
onTypeOptionClicked: (VaultAddEditState.ItemTypeOption) -> Unit,
modifier: Modifier = Modifier,
) {
val possibleMainStates = VaultAddEditState.ItemTypeOption.entries.toList()
val optionsWithStrings = possibleMainStates.associateWith { stringResource(id = it.labelRes) }
val optionsWithStrings = entries.associateWith { stringResource(id = it.labelRes) }

BitwardenMultiSelectButton(
label = stringResource(id = R.string.type),
Original file line number Diff line number Diff line change
@@ -21,6 +21,7 @@ private const val LOGIN: String = "login"
private const val CARD: String = "card"
private const val IDENTITY: String = "identity"
private const val SECURE_NOTE: String = "secure_note"
private const val SSH_KEY: String = "ssh_key"
private const val ADD_ITEM_TYPE: String = "vault_add_item_type"

private const val ADD_EDIT_ITEM_PREFIX: String = "vault_add_edit_item"
@@ -127,6 +128,7 @@ private fun VaultItemCipherType.toTypeString(): String =
VaultItemCipherType.CARD -> CARD
VaultItemCipherType.IDENTITY -> IDENTITY
VaultItemCipherType.SECURE_NOTE -> SECURE_NOTE
VaultItemCipherType.SSH_KEY -> SSH_KEY
}

private fun String.toVaultItemCipherType(): VaultItemCipherType =
@@ -135,6 +137,7 @@ private fun String.toVaultItemCipherType(): VaultItemCipherType =
CARD -> VaultItemCipherType.CARD
IDENTITY -> VaultItemCipherType.IDENTITY
SECURE_NOTE -> VaultItemCipherType.SECURE_NOTE
SSH_KEY -> VaultItemCipherType.SSH_KEY
else -> throw IllegalStateException(
"Edit Item string arguments for VaultAddEditNavigation must match!",
)
Original file line number Diff line number Diff line change
@@ -58,6 +58,7 @@ import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditCardTyp
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditCommonHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditIdentityTypeHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditLoginTypeHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditSshKeyTypeHandlers
import com.x8bit.bitwarden.ui.vault.feature.addedit.handlers.VaultAddEditUserVerificationHandlers

/**
@@ -155,6 +156,10 @@ fun VaultAddEditScreen(
VaultAddEditCardTypeHandlers.create(viewModel = viewModel)
}

val sshKeyItemTypeHandlers = remember(viewModel) {
VaultAddEditSshKeyTypeHandlers.create(viewModel = viewModel)
}

val confirmDeleteClickAction = remember(viewModel) {
{ viewModel.trySendAction(VaultAddEditAction.Common.ConfirmDeleteClick) }
}
@@ -321,6 +326,7 @@ fun VaultAddEditScreen(
VaultAddEditContent(
state = viewState,
isAddItemMode = state.isAddItemMode,
typeOptions = state.supportedItemTypes,
onTypeOptionClicked = remember(viewModel) {
{ viewModel.trySendAction(VaultAddEditAction.Common.TypeOptionSelect(it)) }
},
@@ -329,6 +335,7 @@ fun VaultAddEditScreen(
permissionsManager = permissionsManager,
identityItemTypeHandlers = identityItemTypeHandlers,
cardItemTypeHandlers = cardItemTypeHandlers,
sshKeyItemTypeHandlers = sshKeyItemTypeHandlers,
modifier = Modifier
.imePadding()
.padding(innerPadding)
Loading

0 comments on commit 0e0e0b8

Please sign in to comment.