本文详细介绍了 sa-token 在 java 项目中的使用方法,包括 sa-token 的基本概念、与其他权限框架的比较、基本语法和高级用法,并通过实例讲解了如何在项目中集成和使用 sa-token 。
作为一款轻量级 Java 权限认证框架,Sa-Token 在简化权限管理、提高开发效率方面发挥了重要作用。本文还将深入探讨 Sa-Token 的核心原理,通过内部代码展示其工作机制。最后,总结了 Sa-Token 的优缺点及其在实际开发中的应用场景,为开发者提供全面的指导。
Sa-Token 是一款轻量级 Java 权限认证框架,旨在解决 Java Web 系统中常见的登录认证、权限验证、Session 会话、单点登录等问题。其核心目标是以最简洁的方式,实现强大的权限控制功能,帮助开发者快速完成权限系统的搭建。
Sa-Token 具有如下优势:
| 优势 | 描述 |
|---|---|
| 简单易用 | API设计简洁明了,易于集成和使用,上手快,学习成本低。 |
| 功能丰富 | 支持多种权限控制需求,满足复杂业务场景。支持登录认证、权限验证、角色验证、Session会话、多账号体系等功能。 |
| 高性能 | 轻量级设计,对系统性能影响小。 |
| 高度可扩展 | 提供丰富的扩展接口,与 Spring、SpringBoot、Solon 等常用框架高度兼容,支持自定义持久化、注解方式验证、单点登录等高级特性。 |
| 社区活跃 | 有良好的社区支持和文档资源。 |
Sa-Token 的核心原理是通过 Token 机制实现用户的身份认证和权限校验。
其主要工作流程如下:
流程图例如下:

Sa-Token 与其他常见权限框架在学习成本、集成难度上有显著优势:
| 特性 | Sa-Token | Solon Auth |
|---|---|---|
| 学习成本 | 低 | 低 |
| 功能丰富度 | 高 | 低 |
| 集成难度 | 低 | 低 |
| 性能表现 | 高 | 高 |
| 社区支持 | 活跃 | 一般 |
| 扩展性 | 高 | 中 |
在实际项目中,Sa-Token 通过简单的配置和API调用,即可实现完整的权限管理功能。以下将通过一个完整的 Solon 示例,演示如何集成和使用Sa-Token。
首先,创建一个新的 Solon 项目,可以使用IDEA的项目向导或 Solon Initializr。
引入必要的依赖:
<span><<span style="color:#e45649">dependencies</span>></span>
<em><!-- Solon Web --></em>
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>org.noear<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>solon-web<span></<span style="color:#e45649">artifactId</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
<em><!-- Sa-Token核心依赖 --></em>
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>cn.dev33<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>sa-token-solon-plugin<span></<span style="color:#e45649">artifactId</span>></span>
<span><<span style="color:#e45649">version</span>></span>1.44.0<span></<span style="color:#e45649">version</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
<span></<span style="color:#e45649">dependencies</span>></span>
<em># Sa-Token配置,可根据需要进行调整</em> <span style="color:#986801">sa-token:</span> <em># token有效期,单位秒,默认30天</em> <span style="color:#986801">timeout:</span> <span style="color:#986801">2592000</span> <em># 是否打开二级登录校验</em> <span style="color:#986801">open-safe:</span> <span style="color:#0184bb">false</span>
创建配置类,添加Sa-Token的拦截器,以拦截请求并进行权限验证。SaTokenConfig.java
<span style="color:#a626a4">import</span> cn.dev33.satoken.solon.integration.SaTokenInterceptor;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Configuration;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Managed;
<span style="color:#4078f2">@Configuration</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">SaTokenConfig</span> {
<span style="color:#4078f2">@Managed(index = -100)</span> <em>//-100,是顺序位(低值优先)</em>
<span style="color:#a626a4">public</span> SaTokenInterceptor <span style="color:#4078f2">saTokenInterceptor</span><span>()</span> {
<span style="color:#a626a4">return</span> <span style="color:#a626a4">new</span> <span style="color:#c18401">SaTokenInterceptor</span>(); <em>//用于支持规划处理及注解处理</em>
}
}
创建登录接口,实现用户登录功能。LoginController.java
<span style="color:#a626a4">import</span> cn.dev33.satoken.stp.StpUtil;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Controller;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Mapping;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Param;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Post;
<span style="color:#4078f2">@Controller</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">LoginController</span> {
<span style="color:#4078f2">@Post</span>
<span style="color:#4078f2">@Mapping("/login")</span>
<span style="color:#a626a4">public</span> String <span style="color:#4078f2">login</span><span>(<span style="color:#4078f2">@Param</span> String username, <span style="color:#4078f2">@Param</span> String password)</span> {
<em>// 1. 校验用户名和密码(这里模拟一个简单的校验)</em>
<span style="color:#a626a4">if</span> (<span style="color:#50a14f">"admin"</span>.equals(username) && <span style="color:#50a14f">"123456"</span>.equals(password)) {
<em>// 2. 登录,保存用户ID为10001</em>
StpUtil.login(<span style="color:#986801">10001</span>);
<span style="color:#a626a4">return</span> <span style="color:#50a14f">"登录成功,Token:"</span> + StpUtil.getTokenValue();
}
<span style="color:#a626a4">return</span> <span style="color:#50a14f">"用户名或密码错误"</span>;
}
}
说明:
StpUtil.login(10001)
StpUtil.getTokenValue()
创建需要权限验证的接口,例如获取用户信息的接口。UserController.java
<span style="color:#a626a4">import</span> cn.dev33.satoken.annotation.SaCheckPermission;
<span style="color:#a626a4">import</span> cn.dev33.satoken.stp.StpUtil;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Controller;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Get;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Mapping;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Post;
<span style="color:#4078f2">@Controller</span>
<span style="color:#4078f2">@Mapping("/user")</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">UserController</span> {
<em>// 查询用户信息,需登录</em>
<span style="color:#4078f2">@Get</span>
<span style="color:#4078f2">@Mapping("/info")</span>
<span style="color:#a626a4">public</span> String <span style="color:#4078f2">getUserInfo</span><span>()</span> {
<em>// 校验是否登录</em>
StpUtil.checkLogin();
<em>// 获取用户ID</em>
<span style="color:#986801">int</span> <span style="color:#986801">userId</span> <span>=</span> StpUtil.getLoginIdAsInt();
<span style="color:#a626a4">return</span> <span style="color:#50a14f">"当前用户信息,ID:"</span> + userId;
}
<em>// 修改用户信息,需有权限"user:update"</em>
<span style="color:#4078f2">@SaCheckPermission("user:update")</span>
<span style="color:#4078f2">@Post</span>
<span style="color:#4078f2">@Mapping("/update")</span>
<span style="color:#a626a4">public</span> String <span style="color:#4078f2">updateUser</span><span>()</span> {
<span style="color:#a626a4">return</span> <span style="color:#50a14f">"用户信息更新成功"</span>;
}
}
说明:
StpUtil.checkLogin()
@SaCheckPermission("user:update")如果需要基于角色进行权限控制,可以使用
@SaCheckRole
<span style="color:#a626a4">import</span> cn.dev33.satoken.annotation.SaCheckRole;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Controller;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Get;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Mapping;
<span style="color:#4078f2">@Controller</span>
<span style="color:#4078f2">@Mapping("/admin")</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">AdminController</span> {
<em>// 仅管理员角色可访问</em>
<span style="color:#4078f2">@SaCheckRole("admin")</span>
<span style="color:#4078f2">@Get</span>
<span style="color:#4078f2">@Mapping("/dashboard")</span>
<span style="color:#a626a4">public</span> String <span style="color:#4078f2">adminDashboard</span><span>()</span> {
<span style="color:#a626a4">return</span> <span style="color:#50a14f">"欢迎进入管理员控制台"</span>;
}
}
需要自定义获取用户权限和角色的逻辑,可以实现
StpInterface
<span style="color:#a626a4">import</span> cn.dev33.satoken.stp.StpInterface;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Managed;
<span style="color:#a626a4">import</span> java.util.ArrayList;
<span style="color:#a626a4">import</span> java.util.List;
<span style="color:#4078f2">@Managed</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">StpInterfaceImpl</span> <span style="color:#a626a4">implements</span> <span style="color:#c18401">StpInterface</span> {
<em>// 返回一个用户所拥有的权限码集合</em>
<span style="color:#4078f2">@Override</span>
<span style="color:#a626a4">public</span> List<String> <span style="color:#4078f2">getPermissionList</span><span>(Object loginId, String loginKey)</span> {
<em>// 模拟从数据库获取权限</em>
List<String> permissionList = <span style="color:#a626a4">new</span> <span style="color:#c18401">ArrayList</span><>();
<span style="color:#a626a4">if</span>(<span style="color:#50a14f">"10001"</span>.equals(loginId.toString())) {
permissionList.add(<span style="color:#50a14f">"user:update"</span>);
permissionList.add(<span style="color:#50a14f">"user:delete"</span>);
}
<span style="color:#a626a4">return</span> permissionList;
}
<em>// 返回一个用户所拥有的角色标识集合 (权限与角色可分开校验)</em>
<span style="color:#4078f2">@Override</span>
<span style="color:#a626a4">public</span> List<String> <span style="color:#4078f2">getRoleList</span><span>(Object loginId, String loginKey)</span> {
<em>// 模拟从数据库获取角色</em>
List<String> roleList = <span style="color:#a626a4">new</span> <span style="color:#c18401">ArrayList</span><>();
<span style="color:#a626a4">if</span>(<span style="color:#50a14f">"10001"</span>.equals(loginId.toString())) {
roleList.add(<span style="color:#50a14f">"admin"</span>);
}
<span style="color:#a626a4">return</span> roleList;
}
}
说明:
getPermissionList
getRoleList
Sa-Token 提供了会话管理功能,可以在 Session 中存储和获取数据。
<span style="color:#a626a4">import</span> cn.dev33.satoken.session.SaSession;
<span style="color:#a626a4">import</span> cn.dev33.satoken.stp.StpUtil;
<span style="color:#a626a4">public</span> <span style="color:#a626a4">void</span> <span style="color:#4078f2">sessionDemo</span><span>()</span> {
<em>// 获取当前会话的Session</em>
<span style="color:#986801">SaSession</span> <span style="color:#986801">session</span> <span>=</span> StpUtil.getSession();
<em>// 存储数据</em>
session.set(<span style="color:#50a14f">"name"</span>, <span style="color:#50a14f">"张三"</span>);
session.set(<span style="color:#50a14f">"email"</span>, <span style="color:#50a14f">"zhangsan@example.com"</span>);
<em>// 获取数据</em>
<span style="color:#986801">String</span> <span style="color:#986801">name</span> <span>=</span> session.getString(<span style="color:#50a14f">"name"</span>);
<span style="color:#986801">String</span> <span style="color:#986801">email</span> <span>=</span> session.getString(<span style="color:#50a14f">"email"</span>);
<em>// 输出</em>
System.out.println(<span style="color:#50a14f">"姓名:"</span> + name);
System.out.println(<span style="color:#50a14f">"邮箱:"</span> + email);
}
可以通过用户ID强制用户下线。
<em>// 将用户ID为10001的用户踢下线</em> StpUtil.logoutByLoginId(<span style="color:#986801">10001</span>); <em>// 检查用户是否已被踢下线</em> <span style="color:#986801">boolean</span> <span style="color:#986801">isLogout</span> <span>=</span> StpUtil.isLogin(); System.out.println(<span style="color:#50a14f">"用户是否登录:"</span> + isLogout);
用户主动注销登录,可以调用
StpUtil.logout()
<em>// 注销登录</em> StpUtil.logout(); <em>// 检查登录状态</em> <span style="color:#986801">boolean</span> <span style="color:#986801">isLogin</span> <span>=</span> StpUtil.isLogin(); System.out.println(<span style="color:#50a14f">"用户是否登录:"</span> + isLogin);
Sa-Token 默认使用内存来存储 Token 信息,在分布式环境中,可以使用 Redis 作为持久化介质。
引入Redis依赖:
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>cn.dev33<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>sa-token-redisx<span></<span style="color:#e45649">artifactId</span>></span>
<span><<span style="color:#e45649">version</span>></span>1.44.0<span></<span style="color:#e45649">version</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>cn.dev33<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>sa-token-snack3<span></<span style="color:#e45649">artifactId</span>></span>
<span><<span style="color:#e45649">version</span>></span>1.44.0<span></<span style="color:#e45649">version</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
配置 Redis Dao 连接信息:app.yml
<span style="color:#986801">sa-token:</span> <em># 不同的扩展插件,配置可能会不同</em>
<span style="color:#986801">dao:</span>
<span style="color:#986801">server:</span> <span style="color:#50a14f">"localhost:6379"</span>
<span style="color:#986801">password:</span> <span style="color:#986801">123456</span>
<span style="color:#986801">db:</span> <span style="color:#986801">1</span>
<span style="color:#986801">maxTotal:</span> <span style="color:#986801">200</span>
配置 Redis 持久化:
<span style="color:#a626a4">import</span> cn.dev33.satoken.dao.SaTokenDao;
<span style="color:#a626a4">import</span> cn.dev33.satoken.dao.SaTokenDaoForRedisx;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Configuration;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Inject;
<span style="color:#a626a4">import</span> org.noear.solon.annotation.Managed;
<span style="color:#4078f2">@Configuration</span>
<span style="color:#a626a4">public</span> <span style="color:#a626a4">class</span> <span style="color:#c18401">SaTokenDaoConfig</span> {
<span style="color:#4078f2">@Managed</span>
<span style="color:#a626a4">public</span> SaTokenDao <span style="color:#4078f2">saTokenDaoInit</span><span>(<span style="color:#4078f2">@Inject("${sa-token.dao}")</span> SaTokenDaoForRedisx saTokenDao)</span> {
<span style="color:#a626a4">return</span> saTokenDao;
}
}
Sa-Token提供了SSO模块,可以快速实现单点登录功能。
引入SSO依赖:
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>cn.dev33<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>sa-token-sso<span></<span style="color:#e45649">artifactId</span>></span>
<span><<span style="color:#e45649">version</span>></span>1.44.0<span></<span style="color:#e45649">version</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
配置 SSO 相关参数:app.yml
<span style="color:#986801">sa-token:</span>
<span style="color:#986801">sso-client:</span>
<span style="color:#986801">client:</span> <span style="color:#50a14f">demo-app</span>
<span style="color:#986801">server-url:</span> <span style="color:#50a14f">http://sso-server.com</span>
<span style="color:#986801">is-http:</span> <span style="color:#0184bb">true</span>
<span style="color:#986801">secret-key:</span> <span style="color:#50a14f">SSO-C3-kQwIOrYvnXmSDkwEiFngrKidMcdrgKor</span>
Sa-Token
OAuth2.0
引入
OAuth2.0
<span><<span style="color:#e45649">dependency</span>></span>
<span><<span style="color:#e45649">groupId</span>></span>cn.dev33<span></<span style="color:#e45649">groupId</span>></span>
<span><<span style="color:#e45649">artifactId</span>></span>sa-token-oauth2<span></<span style="color:#e45649">artifactId</span>></span>
<span><<span style="color:#e45649">version</span>></span>1.44.0<span></<span style="color:#e45649">version</span>></span>
<span></<span style="color:#e45649">dependency</span>></span>
配置
OAuth2.0
如果系统中存在多种身份的用户,例如普通用户、管理员、商家等,可以使用多账号体系进行区分。
登录指定账号体系:
<em>// 管理员登录,loginKey为"admin"</em> StpUtil.login(<span style="color:#986801">10001</span>, <span style="color:#50a14f">"admin"</span>);
检查登录状态:
<em>// 检查当前账号体系下是否登录</em> <span style="color:#986801">boolean</span> <span style="color:#986801">isLogin</span> <span>=</span> StpUtil.isLogin(<span style="color:#50a14f">"admin"</span>);
权限验证:
<em>// 在指定账号体系下进行权限验证</em> StpUtil.checkPermission(<span style="color:#50a14f">"user:update"</span>, <span style="color:#50a14f">"admin"</span>);
Sa-Token 是一款轻量级的 Java 权限认证框架,因其简单易用和功能丰富而备受开发者青睐。它以简洁明了的API设计,使得集成和使用变得非常方便,开发者可以快速上手,降低了学习成本。Sa-Token 支持多种权限控制需求,满足复杂业务场景,包括登录认证、权限验证、角色验证、Session 会话、多账号体系等功能,全面覆盖了权限管理的各个方面。其轻量级的设计对系统性能影响小,适用于高并发的应用环境。此外,Sa-Token 提供了丰富的扩展接口,与 Spring、SpringBoot、Solon 等常用框架高度兼容,支持自定义持久化、注解方式验证、单点登录等高级特性,方便开发者根据项目需求进行定制开发。活跃的社区支持和丰富的文档资源也使得开发者能够轻松获取帮助和指导。
由于这些优势,Sa-Token 非常适 Web 项目的快速开发和微服务架构下的权限管理。当项目需要快速搭建权限系统时,选择 Sa-Token 是一个理想的方案。然而,在使用过程中需要注意 Token 的安全性,防止泄露带来风险;对于高并发场景,建议使用Redis等持久化介质来提高系统性能和扩展性;同时,关注 Sa-Token 的版本更新,及时获取新功能和安全补丁,以确保系统的安全性和稳定性。
此文参考自:https://www.cnblogs.com/liuguangzhi/articles/18415627
源码地址:点击下载
以上就是Solon 权限认证之 Sa-Token 的使用与详解的详细内容,更多请关注php中文网其它相关文章!
每个人都需要一台速度更快、更稳定的 PC。随着时间的推移,垃圾文件、旧注册表数据和不必要的后台进程会占用资源并降低性能。幸运的是,许多工具可以让 Windows 保持平稳运行。
Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号