sa_token_core/
config.rs

1// Author: 金书记
2//
3//! 配置模块
4
5use std::time::Duration;
6use std::sync::Arc;
7use serde::{Deserialize, Serialize};
8use sa_token_adapter::storage::SaStorage;
9
10/// sa-token 配置
11#[derive(Debug, Clone, Serialize, Deserialize)]
12pub struct SaTokenConfig {
13    /// Token 名称(例如在 header 或 cookie 中的键名)
14    pub token_name: String,
15    
16    /// Token 有效期(秒),-1 表示永久有效
17    pub timeout: i64,
18    
19    /// Token 最低活跃频率(秒),-1 表示不限制
20    /// 
21    /// 配合 auto_renew 使用时,表示自动续签的时长
22    pub active_timeout: i64,
23    
24    /// 是否开启自动续签(默认 false)
25    /// 
26    /// 如果设置为 true,在以下场景会自动续签 token:
27    /// - 调用 get_token_info() 时
28    /// - 中间件验证 token 时
29    /// - 调用无参数的 StpUtil 方法时
30    /// 
31    /// 续签时长由 active_timeout 决定:
32    /// - 如果 active_timeout > 0,则续签 active_timeout 秒
33    /// - 如果 active_timeout <= 0,则续签 timeout 秒
34    pub auto_renew: bool,
35    
36    /// 是否允许同一账号并发登录
37    pub is_concurrent: bool,
38    
39    /// 在多人登录同一账号时,是否共享一个 token
40    pub is_share: bool,
41    
42    /// Token 风格(uuid、simple-uuid、random-32、random-64、random-128)
43    pub token_style: TokenStyle,
44    
45    /// 是否输出操作日志
46    pub is_log: bool,
47    
48    /// 是否从 cookie 中读取 token
49    pub is_read_cookie: bool,
50    
51    /// 是否从 header 中读取 token
52    pub is_read_header: bool,
53    
54    /// 是否从请求体中读取 token
55    pub is_read_body: bool,
56    
57    /// token 前缀(例如 "Bearer ")
58    pub token_prefix: Option<String>,
59    
60    /// JWT 密钥(如果使用 JWT)
61    pub jwt_secret_key: Option<String>,
62    
63    /// JWT 算法(默认 HS256)
64    pub jwt_algorithm: Option<String>,
65    
66    /// JWT 签发者
67    pub jwt_issuer: Option<String>,
68    
69    /// JWT 受众
70    pub jwt_audience: Option<String>,
71    
72    /// 是否启用防重放攻击(nonce 机制)
73    pub enable_nonce: bool,
74    
75    /// Nonce 有效期(秒),-1 表示使用 token timeout
76    pub nonce_timeout: i64,
77    
78    /// 是否启用 Refresh Token
79    pub enable_refresh_token: bool,
80    
81    /// Refresh Token 有效期(秒),默认 7 天
82    pub refresh_token_timeout: i64,
83}
84
85impl Default for SaTokenConfig {
86    fn default() -> Self {
87        Self {
88            token_name: "sa-token".to_string(),
89            timeout: 2592000, // 30天
90            active_timeout: -1,
91            auto_renew: false, // 默认不开启自动续签
92            is_concurrent: true,
93            is_share: true,
94            token_style: TokenStyle::Uuid,
95            is_log: false,
96            is_read_cookie: true,
97            is_read_header: true,
98            is_read_body: false,
99            token_prefix: None,
100            jwt_secret_key: None,
101            jwt_algorithm: Some("HS256".to_string()),
102            jwt_issuer: None,
103            jwt_audience: None,
104            enable_nonce: false,
105            nonce_timeout: -1,
106            enable_refresh_token: false,
107            refresh_token_timeout: 604800, // 7 天
108        }
109    }
110}
111
112impl SaTokenConfig {
113    pub fn builder() -> SaTokenConfigBuilder {
114        SaTokenConfigBuilder::default()
115    }
116    
117    pub fn timeout_duration(&self) -> Option<Duration> {
118        if self.timeout < 0 {
119            None
120        } else {
121            Some(Duration::from_secs(self.timeout as u64))
122        }
123    }
124}
125
126/// Token 风格 | Token Style
127#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
128pub enum TokenStyle {
129    /// UUID 风格 | UUID style
130    Uuid,
131    /// 简化的 UUID(去掉横杠)| Simple UUID (without hyphens)
132    SimpleUuid,
133    /// 32位随机字符串 | 32-character random string
134    Random32,
135    /// 64位随机字符串 | 64-character random string
136    Random64,
137    /// 128位随机字符串 | 128-character random string
138    Random128,
139    /// JWT 风格(JSON Web Token)| JWT style (JSON Web Token)
140    Jwt,
141    /// Hash 风格(SHA256哈希)| Hash style (SHA256 hash)
142    Hash,
143    /// 时间戳风格(毫秒级时间戳+随机数)| Timestamp style (millisecond timestamp + random)
144    Timestamp,
145    /// Tik 风格(短小精悍的8位字符)| Tik style (short 8-character token)
146    Tik,
147}
148
149/// 配置构建器
150pub struct SaTokenConfigBuilder {
151    config: SaTokenConfig,
152    storage: Option<Arc<dyn SaStorage>>,
153}
154
155impl Default for SaTokenConfigBuilder {
156    fn default() -> Self {
157        Self {
158            config: SaTokenConfig::default(),
159            storage: None,
160        }
161    }
162}
163
164impl SaTokenConfigBuilder {
165    pub fn token_name(mut self, name: impl Into<String>) -> Self {
166        self.config.token_name = name.into();
167        self
168    }
169    
170    pub fn timeout(mut self, timeout: i64) -> Self {
171        self.config.timeout = timeout;
172        self
173    }
174    
175    pub fn active_timeout(mut self, timeout: i64) -> Self {
176        self.config.active_timeout = timeout;
177        self
178    }
179    
180    /// 设置是否开启自动续签
181    pub fn auto_renew(mut self, enabled: bool) -> Self {
182        self.config.auto_renew = enabled;
183        self
184    }
185    
186    pub fn is_concurrent(mut self, concurrent: bool) -> Self {
187        self.config.is_concurrent = concurrent;
188        self
189    }
190    
191    pub fn is_share(mut self, share: bool) -> Self {
192        self.config.is_share = share;
193        self
194    }
195    
196    pub fn token_style(mut self, style: TokenStyle) -> Self {
197        self.config.token_style = style;
198        self
199    }
200    
201    pub fn token_prefix(mut self, prefix: impl Into<String>) -> Self {
202        self.config.token_prefix = Some(prefix.into());
203        self
204    }
205    
206    pub fn jwt_secret_key(mut self, key: impl Into<String>) -> Self {
207        self.config.jwt_secret_key = Some(key.into());
208        self
209    }
210    
211    /// 设置 JWT 算法
212    pub fn jwt_algorithm(mut self, algorithm: impl Into<String>) -> Self {
213        self.config.jwt_algorithm = Some(algorithm.into());
214        self
215    }
216    
217    /// 设置 JWT 签发者
218    pub fn jwt_issuer(mut self, issuer: impl Into<String>) -> Self {
219        self.config.jwt_issuer = Some(issuer.into());
220        self
221    }
222    
223    /// 设置 JWT 受众
224    pub fn jwt_audience(mut self, audience: impl Into<String>) -> Self {
225        self.config.jwt_audience = Some(audience.into());
226        self
227    }
228    
229    /// 启用防重放攻击(nonce 机制)
230    pub fn enable_nonce(mut self, enable: bool) -> Self {
231        self.config.enable_nonce = enable;
232        self
233    }
234    
235    /// 设置 Nonce 有效期(秒)
236    pub fn nonce_timeout(mut self, timeout: i64) -> Self {
237        self.config.nonce_timeout = timeout;
238        self
239    }
240    
241    /// 启用 Refresh Token
242    pub fn enable_refresh_token(mut self, enable: bool) -> Self {
243        self.config.enable_refresh_token = enable;
244        self
245    }
246    
247    /// 设置 Refresh Token 有效期(秒)
248    pub fn refresh_token_timeout(mut self, timeout: i64) -> Self {
249        self.config.refresh_token_timeout = timeout;
250        self
251    }
252    
253    /// 设置存储方式
254    pub fn storage(mut self, storage: Arc<dyn SaStorage>) -> Self {
255        self.storage = Some(storage);
256        self
257    }
258    
259    /// 构建 SaTokenManager(需要先设置 storage)
260    /// 
261    /// # Panics
262    /// 如果未设置 storage,会 panic
263    /// 
264    /// # 示例
265    /// ```rust,ignore
266    /// use std::sync::Arc;
267    /// use sa_token_core::SaTokenConfig;
268    /// use sa_token_storage_memory::MemoryStorage;
269    /// 
270    /// let manager = SaTokenConfig::builder()
271    ///     .storage(Arc::new(MemoryStorage::new()))
272    ///     .timeout(7200)
273    ///     .build();
274    /// ```
275    pub fn build(self) -> crate::SaTokenManager {
276        let storage = self.storage.expect("Storage must be set before building SaTokenManager. Use .storage() method.");
277        crate::SaTokenManager::new(storage, self.config)
278    }
279    
280    /// 仅构建配置(不创建 Manager)
281    pub fn build_config(self) -> SaTokenConfig {
282        self.config
283    }
284}