core_crypto/mls/session/
identifier.rs

1use std::collections::HashMap;
2
3use openmls::prelude::CredentialType;
4use openmls_traits::types::SignatureScheme;
5
6use super::error::{Error, Result};
7use crate::{CertificateBundle, ClientId, RecursiveError, mls::session::id::ClientIdRef};
8
9/// Used by consumers to initializes a MLS client. Encompasses all the client types available.
10/// Could be enriched later with Verifiable Presentations.
11#[derive(Debug, Clone, derive_more::From)]
12pub enum ClientIdentifier {
13    /// Basic keypair
14    Basic(ClientId),
15    /// X509 certificate
16    X509(HashMap<SignatureScheme, CertificateBundle>),
17}
18
19impl ClientIdentifier {
20    /// Extract the unique [ClientId] from an identifier. Use with parsimony as, in case of a x509
21    /// certificate this leads to parsing the certificate
22    pub fn get_id(&self) -> Result<std::borrow::Cow<'_, ClientIdRef>> {
23        match self {
24            ClientIdentifier::Basic(id) => Ok(std::borrow::Cow::Borrowed(id)),
25            ClientIdentifier::X509(certs) => {
26                // since ClientId has uniqueness constraints, it is the same for all certificates.
27                // hence no need to compute it for every certificate then verify its uniqueness
28                // that's not a getter's job
29                let cert = certs.values().next().ok_or(Error::NoX509CertificateBundle)?;
30                let id = cert
31                    .get_client_id()
32                    .map_err(RecursiveError::mls_credential("getting client id"))?;
33                Ok(std::borrow::Cow::Owned(id))
34            }
35        }
36    }
37
38    /// The credential type for this identifier
39    pub fn credential_type(&self) -> CredentialType {
40        match self {
41            ClientIdentifier::Basic(_) => CredentialType::Basic,
42            ClientIdentifier::X509(_) => CredentialType::X509,
43        }
44    }
45}