32个版本 (11个破坏性版本)
0.12.3 | 2024年8月15日 |
---|---|
0.12.2 | 2024年4月14日 |
0.12.1 | 2024年3月31日 |
0.8.2 | 2023年12月24日 |
0.7.0 | 2023年11月27日 |
#36 in 异步
51,366 每月下载次数
用于 23 个crate (22直接)
120KB
1.5K SLoC
tower-sessions
🥠 将会话作为 `tower` 和 `axum` 中间件。
🎨 概述
此crate提供会话,与站点访问者关联的键值对,作为 tower
中间件。
它提供
- 可插拔存储后端: 通过实现
SessionStore
特性,简单地使用自己的后端,完全解耦会话与其存储。 - 最小开销: 只有在实际使用时,会话才会从其支持存储加载,例如在使用的处理程序中。这意味着此中间件可以以最小的开销安装到您的路由图中任何位置。
axum
提取器用于Session
: 使用axum
构建的应用程序可以直接在其处理程序中使用Session
作为提取器。这使得使用会话与在处理程序中包含Session
一样简单。- 简单的键值接口: 会话提供支持本地Rust类型的键值接口。只要这些类型是
Serialize
并且可以转换为JSON,插入、获取和删除任何值都很容易。 - 强类型会话: 强类型保证可以轻松地建立在基础键值接口之上。
此crate的会话实现灵感来源于Django会话中间件,并提供这些语义的转义。
会话存储
会话数据持久性由用户提供的实现 SessionStore
的类型管理。这意味着应用程序可以也应该实现会话存储以满足其特定需求。
尽管如此,已经存在许多会话存储实现,可能是有用的起点。
Crate | Persistent | 描述 |
---|---|---|
tower-sessions-dynamodb-store |
是 | Amazon DynamoDB 会话存储 |
tower-sessions-firestore-store |
是 | Firestore 会话存储 |
tower-sessions-libsql-store |
是 | libSQL 会话存储 |
tower-sessions-mongodb-store |
是 | MongoDB 会话存储 |
tower-sessions-moka-store |
否 | Moka 会话存储 |
tower-sessions-redis-store |
是 | 通过 fred 的 Redis 会话存储 |
tower-sessions-rorm-store |
是 | 由 rorm 提供的 SQLite、Postgres 和 MySQL 会话存储 |
tower-sessions-rusqlite-store |
是 | Rusqlite 会话存储 |
tower-sessions-sled-store |
是 | Sled 会话存储 |
tower-sessions-sqlx-store |
是 | SQLite、Postgres 和 MySQL 会话存储 |
tower-sessions-surrealdb-store |
是 | SurrealDB 会话存储 |
要添加存储?请提交一个包含它的 PR。
用户会话管理
为了便于身份验证和授权,我们在该crate的基础上构建了 axum-login
。如果您正在寻找一个通用的身份验证解决方案,请查看它。
📦 安装
要在项目中使用此crate,请将以下内容添加到您的 Cargo.toml
文件中
[dependencies]
tower-sessions = "0.12.3"
🤸 使用
axum
示例
use std::net::SocketAddr;
use axum::{response::IntoResponse, routing::get, Router};
use serde::{Deserialize, Serialize};
use time::Duration;
use tower_sessions::{Expiry, MemoryStore, Session, SessionManagerLayer};
const COUNTER_KEY: &str = "counter";
#[derive(Default, Deserialize, Serialize)]
struct Counter(usize);
async fn handler(session: Session) -> impl IntoResponse {
let counter: Counter = session.get(COUNTER_KEY).await.unwrap().unwrap_or_default();
session.insert(COUNTER_KEY, counter.0 + 1).await.unwrap();
format!("Current count: {}", counter.0)
}
#[tokio::main]
async fn main() {
let session_store = MemoryStore::default();
let session_layer = SessionManagerLayer::new(session_store)
.with_secure(false)
.with_expiry(Expiry::OnInactivity(Duration::seconds(10)));
let app = Router::new().route("/", get(handler)).layer(session_layer);
let addr = SocketAddr::from(([127, 0, 0, 1], 3000));
let listener = tokio::net::TcpListener::bind(&addr).await.unwrap();
axum::serve(listener, app.into_make_service())
.await
.unwrap();
}
您可以在 此处 找到这个示例,以及其他示例项目在 示例目录 中。
[!NOTE] 更多使用信息,请参阅 crate 文档。
🦺 安全性
此crate使用 #![forbid(unsafe_code)]
来确保所有内容都在100%安全的Rust中实现。
🛟 获取帮助
我们提供了一些 示例 来帮助您入门。您也可以 发起一个讨论 并提出您可能有的其他问题。
👯 贡献
我们感谢所有类型的贡献,谢谢!
依赖项
~6–14MB
~156K SLoC