diff --git a/src/lib.rs b/src/lib.rs index 6ba0da60..29b5af1c 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -259,15 +259,15 @@ pub fn app_setup( } let stripe_client = stripe::Client::new(dotenvy::var("STRIPE_API_KEY").unwrap()); - { - let pool_ref = pool.clone(); - let redis_ref = redis_pool.clone(); - let stripe_client_ref = stripe_client.clone(); - - actix_rt::spawn(async move { - routes::internal::billing::task(stripe_client_ref, pool_ref, redis_ref).await; - }); - } + // { + // let pool_ref = pool.clone(); + // let redis_ref = redis_pool.clone(); + // let stripe_client_ref = stripe_client.clone(); + // + // actix_rt::spawn(async move { + // routes::internal::billing::task(stripe_client_ref, pool_ref, redis_ref).await; + // }); + // } let ip_salt = Pepper { pepper: models::ids::Base62Id(models::ids::random_base62(11)).to_string(), diff --git a/src/routes/internal/flows.rs b/src/routes/internal/flows.rs index accbfbc6..c45fc96a 100644 --- a/src/routes/internal/flows.rs +++ b/src/routes/internal/flows.rs @@ -1628,7 +1628,28 @@ async fn validate_2fa_code( .generate_current() .map_err(|_| AuthenticationError::InvalidCredentials)?; + const TOTP_NAMESPACE: &str = "used_totp"; + let mut conn = redis.connect().await?; + + // Check if TOTP has already been used + if conn + .get(TOTP_NAMESPACE, &format!("{}-{}", token, user_id.0)) + .await? + .is_some() + { + return Err(AuthenticationError::InvalidCredentials); + } + if input == token { + conn + .set( + TOTP_NAMESPACE, + &format!("{}-{}", token, user_id.0), + "", + Some(60), + ) + .await?; + Ok(true) } else if allow_backup { let backup_codes = crate::database::models::User::get_backup_codes(user_id, pool).await?;