Files
AstralRinth/src/database/models/flow_item.rs
Geometrically 4bdf9bff3a 2FA + Add/Remove Auth Providers (#652)
* 2FA + Add/Remove Auth Providers

* fix fmt issue
2023-07-11 19:13:07 -07:00

89 lines
2.2 KiB
Rust

use super::ids::*;
use crate::auth::flows::AuthProvider;
use crate::database::models::DatabaseError;
use chrono::{DateTime, Timelike, Utc};
use rand::distributions::Alphanumeric;
use rand::Rng;
use rand_chacha::rand_core::SeedableRng;
use rand_chacha::ChaCha20Rng;
use redis::cmd;
use serde::{Deserialize, Serialize};
const FLOWS_NAMESPACE: &str = "flows";
#[derive(Deserialize, Serialize)]
#[serde(tag = "type", rename_all = "snake_case")]
pub enum Flow {
OAuth {
user_id: Option<UserId>,
url: String,
provider: AuthProvider,
},
Login2FA {
user_id: UserId,
},
Initialize2FA {
user_id: UserId,
secret: String,
},
ForgotPassword {
user_id: UserId,
},
ConfirmEmail {
user_id: UserId,
confirm_email: String,
},
}
impl Flow {
pub async fn insert(
&self,
expires: DateTime<Utc>,
redis: &deadpool_redis::Pool,
) -> Result<String, DatabaseError> {
let mut redis = redis.get().await?;
let flow = ChaCha20Rng::from_entropy()
.sample_iter(&Alphanumeric)
.take(32)
.map(char::from)
.collect::<String>();
cmd("SET")
.arg(format!("{}:{}", FLOWS_NAMESPACE, flow))
.arg(serde_json::to_string(&self)?)
.arg("EX")
.arg(expires.second())
.query_async::<_, ()>(&mut redis)
.await?;
Ok(flow)
}
pub async fn get(
id: &str,
redis: &deadpool_redis::Pool,
) -> Result<Option<Flow>, DatabaseError> {
let mut redis = redis.get().await?;
let res = cmd("GET")
.arg(format!("{}:{}", FLOWS_NAMESPACE, id))
.query_async::<_, Option<String>>(&mut redis)
.await?;
Ok(res.and_then(|x| serde_json::from_str(&x).ok()))
}
pub async fn remove(
id: &str,
redis: &deadpool_redis::Pool,
) -> Result<Option<()>, DatabaseError> {
let mut redis = redis.get().await?;
let mut cmd = cmd("DEL");
cmd.arg(format!("{}:{}", FLOWS_NAMESPACE, id));
cmd.query_async::<_, ()>(&mut redis).await?;
Ok(Some(()))
}
}