Merge factors type for authentication
This commit is contained in:
@@ -32,14 +32,32 @@ impl TwoFactor {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn description_str(&self) -> &'static str {
|
||||
match self.kind {
|
||||
TwoFactorType::TOTP(_) => "Login by entering an OTP code",
|
||||
TwoFactorType::WEBAUTHN(_) => "Login using a security key",
|
||||
}
|
||||
}
|
||||
|
||||
pub fn type_image(&self) -> &'static str {
|
||||
match self.kind {
|
||||
TwoFactorType::TOTP(_) => "/assets/img/pin.svg",
|
||||
TwoFactorType::WEBAUTHN(_) => "/assets/img/key.svg",
|
||||
}
|
||||
}
|
||||
|
||||
pub fn login_url(&self, redirect_uri: &LoginRedirect) -> String {
|
||||
match self.kind {
|
||||
TwoFactorType::TOTP(_) => format!("/2fa_otp?id={}&redirect={}",
|
||||
self.id.0, redirect_uri.get_encoded()),
|
||||
TwoFactorType::WEBAUTHN(_) => format!("/2fa_webauthn?id={}&redirect={}",
|
||||
self.id.0, redirect_uri.get_encoded()),
|
||||
TwoFactorType::TOTP(_) => format!("/2fa_otp?redirect={}", redirect_uri.get_encoded()),
|
||||
TwoFactorType::WEBAUTHN(_) => {
|
||||
format!("/2fa_webauthn?redirect={}", redirect_uri.get_encoded())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn is_webauthn(&self) -> bool {
|
||||
matches!(self.kind, TwoFactorType::WEBAUTHN(_))
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug, serde::Serialize, serde::Deserialize)]
|
||||
@@ -71,7 +89,7 @@ impl User {
|
||||
pub fn can_access_app(&self, id: &ClientID) -> bool {
|
||||
match &self.authorized_clients {
|
||||
None => true,
|
||||
Some(c) => c.contains(id)
|
||||
Some(c) => c.contains(id),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -94,6 +112,49 @@ impl User {
|
||||
pub fn find_factor(&self, factor_id: &FactorID) -> Option<&TwoFactor> {
|
||||
self.two_factor.iter().find(|f| f.id.eq(factor_id))
|
||||
}
|
||||
|
||||
pub fn has_webauthn_factor(&self) -> bool {
|
||||
self.two_factor.iter().any(TwoFactor::is_webauthn)
|
||||
}
|
||||
|
||||
/// Get all registered OTP registered passwords
|
||||
pub fn get_otp_factors(&self) -> Vec<TotpKey> {
|
||||
self.two_factor.iter().fold(vec![], |mut acc, factor| {
|
||||
if let TwoFactorType::TOTP(key) = &factor.kind {
|
||||
acc.push(key.clone())
|
||||
}
|
||||
|
||||
acc
|
||||
})
|
||||
}
|
||||
|
||||
/// Get all registered 2FA webauthn public keys
|
||||
pub fn get_webauthn_pub_keys(&self) -> Vec<WebauthnPubKey> {
|
||||
self.two_factor.iter().fold(vec![], |mut acc, factor| {
|
||||
if let TwoFactorType::WEBAUTHN(key) = &factor.kind {
|
||||
acc.push(*key.clone())
|
||||
}
|
||||
|
||||
acc
|
||||
})
|
||||
}
|
||||
|
||||
/// Get the first factor of each kind of factors
|
||||
pub fn get_distinct_factors_types(&self) -> Vec<&TwoFactor> {
|
||||
let mut urls = vec![];
|
||||
|
||||
self.two_factor
|
||||
.iter()
|
||||
.filter(|f| {
|
||||
if urls.contains(&f.type_str()) {
|
||||
false
|
||||
} else {
|
||||
urls.push(f.type_str());
|
||||
true
|
||||
}
|
||||
})
|
||||
.collect::<Vec<_>>()
|
||||
}
|
||||
}
|
||||
|
||||
impl PartialEq for User {
|
||||
@@ -157,8 +218,8 @@ impl EntityManager<User> {
|
||||
|
||||
/// Update user information
|
||||
fn update_user<F>(&mut self, id: &UserID, update: F) -> bool
|
||||
where
|
||||
F: FnOnce(User) -> User,
|
||||
where
|
||||
F: FnOnce(User) -> User,
|
||||
{
|
||||
let user = match self.find_by_user_id(id) {
|
||||
None => return false,
|
||||
|
||||
Reference in New Issue
Block a user