summaryrefslogtreecommitdiffstats
path: root/crates/auth/src/server/csrf_token_validation.rs
diff options
context:
space:
mode:
Diffstat (limited to 'crates/auth/src/server/csrf_token_validation.rs')
-rw-r--r--crates/auth/src/server/csrf_token_validation.rs49
1 files changed, 49 insertions, 0 deletions
diff --git a/crates/auth/src/server/csrf_token_validation.rs b/crates/auth/src/server/csrf_token_validation.rs
new file mode 100644
index 0000000..c9a627c
--- /dev/null
+++ b/crates/auth/src/server/csrf_token_validation.rs
@@ -0,0 +1,49 @@
+use anyhow::{Context, anyhow};
+use axum_extra::headers;
+use oauth2::CsrfToken;
+use time::OffsetDateTime;
+use tower_sessions::{CachingSessionStore, SessionStore, session::Id};
+use tower_sessions_moka_store::MokaStore;
+use tower_sessions_sqlx_store::PostgresStore;
+
+use crate::{
+ error::AppError,
+ server::{COOKIE_NAME, CSRF_TOKEN, routes::authorised::AuthRequest},
+ state::AppHandle,
+};
+
+pub struct Session {
+ id: String,
+ expires_at: OffsetDateTime,
+ user_id: String,
+}
+
+pub async fn csrf_token_validation_workflow(
+ auth_request: &AuthRequest,
+ store: &CachingSessionStore<MokaStore, PostgresStore>,
+ oauth_session_id: Id,
+) -> Result<(), AppError> {
+ let oauth_session = store.load(&oauth_session_id).await.unwrap().unwrap();
+
+ // Extract the CSRF token from the session
+ let csrf_token_serialized = oauth_session
+ .data
+ .get(CSRF_TOKEN)
+ .context("failed to get value from session")?;
+ let csrf_token = serde_json::from_value::<CsrfToken>(csrf_token_serialized.clone())
+ .context("CSRF token not found in session")?
+ .to_owned();
+
+ // Cleanup the CSRF token session
+ store
+ .delete(&oauth_session_id)
+ .await
+ .context("Failed to destroy old session")?;
+
+ // Validate CSRF token is the same as the one in the auth request
+ if *csrf_token.secret() != auth_request.state {
+ return Err(anyhow!("CSRF token mismatch").into());
+ }
+
+ Ok(())
+}