Skip to main content

bitwarden_fido/
client_fido.rs

1use bitwarden_core::Client;
2use bitwarden_vault::CipherView;
3use thiserror::Error;
4
5use crate::{
6    DeviceAuthKeyAuthenticator, DeviceAuthKeyStore, Fido2Authenticator, Fido2Client,
7    Fido2CredentialAutofillView, Fido2CredentialAutofillViewError, Fido2CredentialStore,
8    Fido2UserInterface,
9};
10
11#[allow(missing_docs)]
12#[derive(Clone)]
13pub struct ClientFido2 {
14    pub(crate) client: Client,
15}
16
17#[allow(missing_docs)]
18#[derive(Debug, Error)]
19#[cfg_attr(feature = "uniffi", derive(uniffi::Error), uniffi(flat_error))]
20pub enum DecryptFido2AutofillCredentialsError {
21    #[error(transparent)]
22    Fido2CredentialAutofillView(#[from] Fido2CredentialAutofillViewError),
23}
24
25impl ClientFido2 {
26    #[allow(missing_docs)]
27    pub fn new(client: Client) -> Self {
28        Self { client }
29    }
30
31    #[allow(missing_docs)]
32    pub fn create_authenticator<'a>(
33        &'a self,
34        user_interface: &'a dyn Fido2UserInterface,
35        credential_store: &'a dyn Fido2CredentialStore,
36    ) -> Fido2Authenticator<'a> {
37        Fido2Authenticator::new(&self.client, user_interface, credential_store)
38    }
39
40    #[allow(missing_docs)]
41    pub fn create_client<'a>(
42        &'a self,
43        user_interface: &'a dyn Fido2UserInterface,
44        credential_store: &'a dyn Fido2CredentialStore,
45    ) -> Fido2Client<'a> {
46        Fido2Client {
47            authenticator: self.create_authenticator(user_interface, credential_store),
48        }
49    }
50
51    /// Create an authenticator intended to be used with a device-bound
52    /// credential to log into and unlock a Bitwarden vault.
53    pub fn create_device_key_authenticator<'a>(
54        &'a self,
55        store: &'a mut dyn DeviceAuthKeyStore,
56    ) -> DeviceAuthKeyAuthenticator<'a> {
57        DeviceAuthKeyAuthenticator {
58            client: &self.client,
59            store,
60        }
61    }
62
63    #[allow(missing_docs)]
64    pub fn decrypt_fido2_autofill_credentials(
65        &self,
66        cipher_view: CipherView,
67    ) -> Result<Vec<Fido2CredentialAutofillView>, DecryptFido2AutofillCredentialsError> {
68        let key_store = self.client.internal.get_key_store();
69
70        Ok(Fido2CredentialAutofillView::from_cipher_view(
71            &cipher_view,
72            &mut key_store.context(),
73        )?)
74    }
75}
76
77#[allow(missing_docs)]
78pub trait ClientFido2Ext {
79    fn fido2(&self) -> ClientFido2;
80}
81
82impl ClientFido2Ext for Client {
83    fn fido2(&self) -> ClientFido2 {
84        ClientFido2::new(self.clone())
85    }
86}