BasicOIDC/src/data/session_identity.rs

111 lines
3.0 KiB
Rust
Raw Normal View History

2022-04-01 16:59:17 +00:00
use actix_identity::Identity;
2022-04-01 20:51:33 +00:00
use serde::{Deserialize, Serialize};
2022-04-01 16:59:17 +00:00
2022-04-02 13:30:08 +00:00
use crate::constants::{MAX_INACTIVITY_DURATION, MAX_SESSION_DURATION, MIN_ACTIVITY_RECORD_TIME};
use crate::data::user::{User, UserID};
2022-04-01 20:51:33 +00:00
use crate::utils::time::time;
#[derive(Debug, Serialize, Deserialize, Eq, PartialEq)]
2022-04-02 06:30:01 +00:00
pub enum SessionStatus {
Invalid,
2022-04-01 20:51:33 +00:00
SignedIn,
NeedNewPassword,
NeedMFA,
}
2022-04-01 16:59:17 +00:00
2022-04-02 06:30:01 +00:00
impl Default for SessionStatus {
fn default() -> Self {
Self::Invalid
}
}
#[derive(Debug, Serialize, Deserialize, Default)]
2022-04-01 20:51:33 +00:00
struct SessionIdentityData {
2022-04-02 13:30:08 +00:00
pub id: UserID,
2022-04-01 16:59:17 +00:00
pub is_admin: bool,
2022-04-02 13:30:08 +00:00
login_time: u64,
2022-04-01 20:51:33 +00:00
last_access: u64,
pub status: SessionStatus,
2022-04-01 16:59:17 +00:00
}
2022-04-01 20:51:33 +00:00
pub struct SessionIdentity<'a>(pub &'a Identity);
impl<'a> SessionIdentity<'a> {
pub fn set_user(&self, user: &User) {
self.set_session_data(&SessionIdentityData {
2022-04-01 16:59:17 +00:00
id: user.uid.clone(),
is_admin: user.admin,
2022-04-02 13:30:08 +00:00
login_time: time(),
2022-04-01 20:51:33 +00:00
last_access: time(),
status: SessionStatus::SignedIn,
});
2022-04-01 16:59:17 +00:00
}
2022-04-01 20:51:33 +00:00
fn get_session_data(&self) -> Option<SessionIdentityData> {
let mut res: Option<SessionIdentityData> = self.0.identity()
2022-04-02 06:31:48 +00:00
.as_deref()
2022-04-01 20:51:33 +00:00
.map(serde_json::from_str)
.map(|f| f.expect("Failed to deserialize session data!"));
2022-04-02 06:30:01 +00:00
// Check if session is valid
if let Some(sess) = &res {
if sess.id.is_empty() {
return None;
}
}
2022-04-01 20:51:33 +00:00
if let Some(session) = res.as_mut() {
2022-04-02 13:30:08 +00:00
if session.login_time + MAX_SESSION_DURATION < time() {
log::info!("Session for {} reached max duration timeout", session.id);
self.0.forget();
return None;
}
if session.last_access + MAX_INACTIVITY_DURATION < time() {
2022-04-01 20:51:33 +00:00
log::info!("Session is expired for {}", session.id);
self.0.forget();
return None;
}
if session.last_access + MIN_ACTIVITY_RECORD_TIME < time() {
log::debug!("Refresh last access for session");
session.last_access = time();
self.set_session_data(session);
}
2022-04-01 16:59:17 +00:00
}
2022-04-01 20:51:33 +00:00
res
2022-04-01 16:59:17 +00:00
}
2022-04-01 20:51:33 +00:00
fn set_session_data(&self, data: &SessionIdentityData) {
let s = serde_json::to_string(data)
.expect("Failed to serialize session data!");
self.0.remember(s);
2022-04-01 16:59:17 +00:00
}
2022-04-02 06:30:01 +00:00
pub fn set_status(&self, status: SessionStatus) {
let mut sess = self.get_session_data().unwrap_or_default();
sess.status = status;
self.set_session_data(&sess);
}
2022-04-01 20:51:33 +00:00
pub fn is_authenticated(&self) -> bool {
self.get_session_data()
.map(|s| s.status == SessionStatus::SignedIn)
2022-04-01 16:59:17 +00:00
.unwrap_or(false)
}
2022-04-02 06:30:01 +00:00
pub fn need_new_password(&self) -> bool {
self.get_session_data()
.map(|s| s.status == SessionStatus::NeedNewPassword)
.unwrap_or(false)
}
2022-04-02 13:30:08 +00:00
pub fn user_id(&self) -> UserID {
2022-04-02 06:30:01 +00:00
self.get_session_data()
.unwrap_or_default()
.id
}
2022-04-01 16:59:17 +00:00
}