Okay thanks all. This is what I have now:
lazy_static! {
static ref SESSIONS : RwLock<DashMap<String, Option<u8>>> = RwLock::new(DashMap::new());
}
// Module for handling sessions
pub mod session_handler {
use actix_web::{HttpRequest, HttpResponse};
use rand::{thread_rng, Rng};
use rand::distributions::Alphanumeric;
use sha2::{Sha256, Digest};
use uuid::Uuid;
use crate::*;
// Generate session_token. Concatenation of sha256(ip_address) and a random string,
// ip_address is included to avoid collission
fn generate_session_token() -> String {
Uuid::new_v4().to_string()
}
// Check if a session exists by reading the cookie 'session' in the request-header
pub fn session_exists(req: HttpRequest) -> bool {
get_session_token(req).map_or(false, |s| s != "")
}
// Retrieves the session_token from the request.
// if none cookie is found this Option<String> will be None, otherwise
// it will contain the session_token after unwrapping
pub fn get_session_token(req: HttpRequest) -> Option<String> {
Some(req.headers().get("session").and_then(|r| r.to_str().ok()).unwrap().to_string())
}
// Make a HttpResponse with the NEW session_token in the header.
pub fn set_session_token(req: HttpRequest) -> HttpResponse {
let ip_address = req
.connection_info()
.remote_addr()
.unwrap()
.to_string();
let session_token = generate_session_token();
let header_string = format!("session={}; Secure; HttpOnly", session_token);
add_session(session_token);
HttpResponse::Ok()
.content_type("plain/text")
.header("Set-Cookie", header_string)
.body("")
}
// Save this session in the session_database
pub fn add_session(token: String) {
SESSIONS.read().unwrap().insert(token, None);
}
// Delete a session from the session_database
pub fn delete_session_by_token(token: String) {
SESSIONS.read().unwrap().remove(&token);
}
// Unimplemented...
pub fn delete_session_by_userid(id: u8) {
unimplemented!()
}
// A user is linked to a session after authenticating himself. This Function
// can retrieve which user is connected to which session.
pub fn get_user_by_session(token: String) -> Option<u8> {
*SESSIONS.read().unwrap().get(&token).unwrap()
}
pub fn set_user_by_session(token: String, user_id: u8) {
if let Some(mut value) = SESSIONS.read().unwrap().get_mut(&token) {
*value = Some(user_id);
}
}
}
If this is okay I'll try to actually implement it.