Sessione
Middleware che fornisce supporto per Session
.
Cos'è una Sessione
Una sessione è un insieme di dati utente memorizzati lato server, tipicamente utilizzati per tracciare lo stato dell'utente e conservare dati temporanei. Nelle applicazioni web, le sessioni risolvono il problema dell'assenza di stato nel protocollo HTTP, permettendo al server di riconoscere richieste multiple provenienti dallo stesso utente.
Utilizzo delle Sessioni in Salvo
In Salvo, il middleware Session fornisce API semplici per leggere e scrivere dati di sessione. Attraverso SessionDepot
è possibile ottenere un'istanza della sessione, mentre metodi come get
, set
, remove
permettono di gestire i dati della sessione.
Utilizzi Comuni
- Autenticazione utente e gestione dello stato di login
- Memorizzazione temporanea di dati di form
- Conservazione delle preferenze utente
Codice di Esempio
session-login/src/main.rs
use salvo::prelude::*;
use salvo::session::{CookieStore, Session, SessionDepotExt, SessionHandler};
#[tokio::main]
async fn main() {
tracing_subscriber::fmt().init();
let session_handler = SessionHandler::builder(
CookieStore::new(),
b"secretabsecretabsecretabsecretabsecretabsecretabsecretabsecretab",
)
.build()
.unwrap();
let router = Router::new()
.hoop(session_handler)
.get(home)
.push(Router::with_path("login").get(login).post(login))
.push(Router::with_path("logout").get(logout));
let acceptor = TcpListener::new("0.0.0.0:5800").bind().await;
Server::new(acceptor).serve(router).await;
}
#[handler]
pub async fn login(req: &mut Request, depot: &mut Depot, res: &mut Response) {
if req.method() == salvo::http::Method::POST {
let mut session = Session::new();
session
.insert("username", req.form::<String>("username").await.unwrap())
.unwrap();
depot.set_session(session);
res.render(Redirect::other("/"));
} else {
res.render(Text::Html(LOGIN_HTML));
}
}
#[handler]
pub async fn logout(depot: &mut Depot, res: &mut Response) {
if let Some(session) = depot.session_mut() {
session.remove("username");
}
res.render(Redirect::other("/"));
}
#[handler]
pub async fn home(depot: &mut Depot, res: &mut Response) {
let mut content = r#"<a href="login">Login</h1>"#.into();
if let Some(session) = depot.session_mut() {
if let Some(username) = session.get::<String>("username") {
content = format!(r#"Hello, {username}. <br><a href="logout">Logout</h1>"#);
}
}
res.render(Text::Html(content));
}
static LOGIN_HTML: &str = r#"<!DOCTYPE html>
<html>
<head>
<title>Login</title>
</head>
<body>
<form action="/login" method="post">
<h1>Login</h1>
<input type="text" name="username" />
<button type="submit" id="submit">Submit</button>
</form>
</body>
</html>
"#;