axum-security 0.0.2

A security toolbox for the Axum library
Documentation
use std::{cmp, time::Duration};

use crate::{cookie::store::ErasedStore, utils::utc_now_secs};

pub(crate) enum SessionExpiry {
    CookieMaxAge,
    Duration(Duration),
}

pub(crate) async fn maintenance_task<S: 'static>(this: ErasedStore<S>, expires_after: Duration) {
    let check_interval = cmp::max(expires_after / 2, Duration::from_secs(60));
    let mut interval = tokio::time::interval(check_interval);
    loop {
        interval.tick().await;
        if let Err(_e) = this.remove_before(utc_now_secs()).await {
            crate::error!("session maintenance task failed to remove expired sessions");
        }
    }
}

#[cfg(test)]
mod expiry {
    use std::time::Duration;

    use crate::cookie::{CookieContext, MemStore};

    #[tokio::test]
    async fn duration() {
        let cookie_context = CookieContext::builder()
            .expires_after(Duration::from_secs(1))
            .store(MemStore::new())
            .build::<()>();

        let cookie = cookie_context.create_session(()).await.unwrap();

        let session = cookie_context.load_from_cookie(&cookie).await.unwrap();
        assert!(session.is_some());

        tokio::time::sleep(Duration::from_secs(2)).await;

        let session = cookie_context.load_from_cookie(&cookie).await.unwrap();
        assert!(session.is_none());
    }

    #[tokio::test]
    async fn max_age() {
        let cookie_context = CookieContext::builder()
            .cookie(|c| c.max_age(Duration::from_secs(1)))
            .expires_max_age()
            .store(MemStore::new())
            .build::<()>();

        let cookie = cookie_context.create_session(()).await.unwrap();

        let session = cookie_context.load_from_cookie(&cookie).await.unwrap();
        assert!(session.is_some());

        tokio::time::sleep(Duration::from_secs(2)).await;

        let session = cookie_context.load_from_cookie(&cookie).await.unwrap();
        assert!(session.is_none());
    }

    #[test]
    #[should_panic]
    fn no_max_age() {
        CookieContext::builder()
            .expires_max_age()
            .store(MemStore::new())
            .build::<()>();
    }
}