From 15b0da6351d77edce8f186634cd3d4788228318e Mon Sep 17 00:00:00 2001 From: shengzhang <2393584716@qq.com> Date: Mon, 12 Apr 2021 03:22:01 +0800 Subject: [PATCH] =?UTF-8?q?=E6=96=B0=E5=A2=9E=E5=85=A8=E5=B1=80=E8=BF=87?= =?UTF-8?q?=E6=BB=A4=E5=99=A8=E8=AE=A4=E8=AF=81=E9=89=B4=E6=9D=83=EF=BC=8C?= =?UTF-8?q?=E5=A2=9E=E5=BC=BA=E9=98=B2=E6=B8=97=E9=80=8F=E6=89=AB=E6=8F=8F?= =?UTF-8?q?=E5=A4=84=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- sa-token-demo-springboot/pom.xml | 2 +- ...nfiguration.java => SaTokenConfigure.java} | 6 +- sa-token-demo-webflux/pom.xml | 2 +- ...nfiguration.java => SaTokenConfigure.java} | 6 +- sa-token-doc/doc/_sidebar.md | 6 +- sa-token-doc/doc/lib/index.css | 3 + sa-token-doc/doc/more/tj-gzh.md | 30 ++++- sa-token-doc/doc/senior/dcs.md | 13 ++- sa-token-doc/doc/start/download.md | 36 ++++-- sa-token-doc/doc/start/example.md | 30 +++-- sa-token-doc/doc/start/webflux-example.md | 76 +++++++++++++ sa-token-doc/doc/use/at-check.md | 4 +- sa-token-doc/doc/use/config.md | 4 +- sa-token-doc/doc/use/global-filter.md | 103 ++++++++++++++++++ sa-token-doc/doc/use/route-check.md | 8 +- .../{context => filter}/SaReactorFilter.java | 4 +- .../dev33/satoken/filter/SaServletFilter.java | 56 ++++++++++ 17 files changed, 342 insertions(+), 47 deletions(-) rename sa-token-demo-springboot/src/main/java/com/pj/satoken/{SaTokenConfiguration.java => SaTokenConfigure.java} (81%) rename sa-token-demo-webflux/src/main/java/com/pj/satoken/{SaTokenConfiguration.java => SaTokenConfigure.java} (90%) create mode 100644 sa-token-doc/doc/start/webflux-example.md create mode 100644 sa-token-doc/doc/use/global-filter.md rename sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/{context => filter}/SaReactorFilter.java (91%) create mode 100644 sa-token-spring-boot-starter/src/main/java/cn/dev33/satoken/filter/SaServletFilter.java diff --git a/sa-token-demo-springboot/pom.xml b/sa-token-demo-springboot/pom.xml index a89facbc..e7603a9c 100644 --- a/sa-token-demo-springboot/pom.xml +++ b/sa-token-demo-springboot/pom.xml @@ -31,7 +31,7 @@ spring-boot-starter-aop - + cn.dev33 sa-token-spring-boot-starter diff --git a/sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfiguration.java b/sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfigure.java similarity index 81% rename from sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfiguration.java rename to sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfigure.java index 14a9a62a..6889533f 100644 --- a/sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfiguration.java +++ b/sa-token-demo-springboot/src/main/java/com/pj/satoken/SaTokenConfigure.java @@ -13,9 +13,11 @@ import cn.dev33.satoken.interceptor.SaAnnotationInterceptor; * */ @Configuration -public class SaTokenConfiguration implements WebMvcConfigurer { +public class SaTokenConfigure implements WebMvcConfigurer { - // 注册sa-token的拦截器,打开注解式鉴权功能 + /** + * 注册sa-token的拦截器,打开注解式鉴权功能 + */ @Override public void addInterceptors(InterceptorRegistry registry) { // 注册注解拦截器 diff --git a/sa-token-demo-webflux/pom.xml b/sa-token-demo-webflux/pom.xml index d2265cf8..e6fe1d48 100644 --- a/sa-token-demo-webflux/pom.xml +++ b/sa-token-demo-webflux/pom.xml @@ -31,7 +31,7 @@ spring-boot-starter-aop - + cn.dev33 sa-token-reactor-spring-boot-starter diff --git a/sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfiguration.java b/sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfigure.java similarity index 90% rename from sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfiguration.java rename to sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfigure.java index 48ee86f6..b54ab49a 100644 --- a/sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfiguration.java +++ b/sa-token-demo-webflux/src/main/java/com/pj/satoken/SaTokenConfigure.java @@ -7,7 +7,7 @@ import com.pj.util.AjaxJson; import cn.dev33.satoken.filter.SaFilterErrorStrategy; import cn.dev33.satoken.filter.SaFilterStrategy; -import cn.dev33.satoken.reactor.context.SaReactorFilter; +import cn.dev33.satoken.reactor.filter.SaReactorFilter; import cn.dev33.satoken.router.SaRouterUtil; import cn.dev33.satoken.stp.StpUtil; @@ -17,7 +17,7 @@ import cn.dev33.satoken.stp.StpUtil; * */ @Configuration -public class SaTokenConfiguration { +public class SaTokenConfigure { /** * 注册 [sa-token全局过滤器] @@ -34,7 +34,7 @@ public class SaTokenConfiguration { public SaFilterStrategy getSaFilterStrategy() { return r -> { System.out.println("---------- 进入sa-token全局过滤器 -----------"); - SaRouterUtil.match("/test/test", () -> StpUtil.checkLogin()); + SaRouterUtil.match("/test/test333", () -> StpUtil.checkLogin()); // SaRouterUtil.match("/user/**", () -> StpUtil.checkPermission("user")); // SaRouterUtil.match("/admin/**", () -> StpUtil.checkPermission("admin")); // SaRouterUtil.match("/goods/**", () -> StpUtil.checkPermission("goods")); diff --git a/sa-token-doc/doc/_sidebar.md b/sa-token-doc/doc/_sidebar.md index d76c22e5..44a1d18b 100644 --- a/sa-token-doc/doc/_sidebar.md +++ b/sa-token-doc/doc/_sidebar.md @@ -1,9 +1,10 @@ - **开始** - - [介绍](/README) + - [框架](/README) - [集成](/start/download) - - [示例](/start/example) + - [在SpringBoot环境集成](/start/example) + - [在WebFlux环境集成](/start/webflux-example) - **使用** - [登录验证](/use/login-auth) @@ -16,6 +17,7 @@ - [同端互斥登录](/use/mutex-login) - [注解式鉴权](/use/at-check) - [路由拦截式鉴权](/use/route-check) + - [全局过滤器](/use/global-filter) - [花式token](/use/token-style) - [Token前缀](/use/token-prefix) - [框架配置](/use/config) diff --git a/sa-token-doc/doc/lib/index.css b/sa-token-doc/doc/lib/index.css index b7812f14..1addab81 100644 --- a/sa-token-doc/doc/lib/index.css +++ b/sa-token-doc/doc/lib/index.css @@ -31,6 +31,9 @@ body{font-family: -apple-system,BlinkMacSystemFont,Segoe UI,Roboto,Oxygen,Ubuntu /* .gzh-table td img{width: 100%;} */ /* .gzh-table tr, .gzh-table td{ border: 0px !important;} */ +/* tab选项卡优化 */ +.docsify-tabs__tab{outline: 0; cursor: pointer;} +.docsify-tabs--classic .docsify-tabs__tab--active{box-shadow: 0 0 0;} /* ============== 代码样式优化 ================ */ diff --git a/sa-token-doc/doc/more/tj-gzh.md b/sa-token-doc/doc/more/tj-gzh.md index df6798e8..eee29218 100644 --- a/sa-token-doc/doc/more/tj-gzh.md +++ b/sa-token-doc/doc/more/tj-gzh.md @@ -6,11 +6,37 @@ + + + + + + +
+ + 程序猿 + 传播编程经验,挖掘程序员优秀的学习资源。 + + + 架构师必备 + 分享干货文章,做一个有逼格的架构师社区! + + + GitHuboy + 专注于分享 Python、Java、Web、AI、数据分析等多个领域的优质学习资源 + + + 开源最前线 + 推荐热门开源软件,介绍新开源项目,报导开源资讯! +
- dromara开源组织 - dromara开源组织官方公众号 [https://github.com/dromara][https://gitee.com/dromara] + Dromara开源组织 + Dromara开源组织官方公众号
+ Gitee + GitHub + 官网
diff --git a/sa-token-doc/doc/senior/dcs.md b/sa-token-doc/doc/senior/dcs.md index 9a0aadf7..46b8b2bc 100644 --- a/sa-token-doc/doc/senior/dcs.md +++ b/sa-token-doc/doc/senior/dcs.md @@ -1,12 +1,11 @@ # 集群、分布式 -Sa-token 在集群、分布式下的解决方案 +Sa-Token 在集群、分布式下的解决方案 --- - -### 分布式下的数据同步问题 -单机版的`Session`在分布式环境下一般不能正常工作,为此我们需要对框架做一些特定的处理。 +### 分布式会话 +分布式架构下的第一个难题便是数据同步,单机版的`Session`在分布式环境下一般不能正常工作,为此我们需要对框架做一些特定的处理。 首先我们要明白,分布式环境下为什么`Session`会失效?因为用户在一个节点对会话做出的更改无法实时同步到其它的节点, 这就导致一个很严重的问题:如果用户在节点一上已经登录成功,那么当下一次的请求落在节点二上时,对节点二来讲,此用户仍然是未登录状态。 @@ -26,6 +25,12 @@ Sa-token 在集群、分布式下的解决方案 由于`jwt`模式不在服务端存储数据,对于比较复杂的业务可能会功能受限,因此更加推荐使用方案三 +### 微服务网关鉴权 +由于大多数常见网关组件基于`webflux`编写,从底层上脱离了"ServletAPI"模型(如`Gateway`、`Soul`等),这就导致很多底层依赖ServletAPI的权限认证框架无法在网关处使用。 + +为此`Sa-Token`自`v1.16.0`版本开始提供了`Reactor响应式模型`web框架的starter依赖包,你可以据此轻松完成网关鉴权需求, +详细请参考:[全局过滤器](/use/global-filter) + diff --git a/sa-token-doc/doc/start/download.md b/sa-token-doc/doc/start/download.md index 753b86cf..8d45dbc5 100644 --- a/sa-token-doc/doc/start/download.md +++ b/sa-token-doc/doc/start/download.md @@ -3,7 +3,10 @@ ------ ## Maven依赖 -在项目中直接通过 `pom.xml` 导入 `sa-token` 的依赖即可 +在项目中直接通过 `pom.xml` 导入 `sa-token` 的依赖即可: + + + ``` xml @@ -13,27 +16,46 @@ ``` -## Gradle依赖 -Gradle用户引入依赖: + +注:此依赖适合在 Reactor模式 的web框架中导入(例如`Netty`、`WebFlux`等),如果您的项目基于 ServletAPI (`SpringMVC`、`SpringBoot`等),请以前者为准 +``` xml + + + cn.dev33 + sa-token-reactor-spring-boot-starter + 1.15.2 + ``` + + + + +## Gradle依赖 + + +``` xml implementation 'cn.dev33:sa-token-spring-boot-starter:1.15.2' ``` - + +``` xml +implementation 'cn.dev33:sa-token-reactor-spring-boot-starter:1.15.2' +``` + ## 获取源码 -如果你想深入了解`sa-token`,你可以通过`github`或者`gitee`来获取源码 +如果你想深入了解`sa-token`,你可以通过`github`或者`gitee`来获取源码 (**学习测试请拉取master分支**,dev为正在开发的分支,有很多特性并不稳定) - github地址:[https://github.com/dromara/sa-token](https://github.com/dromara/sa-token) - gitee地址:[https://gitee.com/dromara/sa-token](https://gitee.com/dromara/sa-token) - 开源不易,求鼓励,给个`star`吧 - 源码目录介绍: -``` +``` js ── sa-token ├── sa-token-core // sa-token 核心模块 ├── sa-token-servlet // sa-token 整合 Servlet容器实现类包 ├── sa-token-spring-boot-starter // sa-token 整合 SpringBoot 快速集成 - ├── sa-token-webflux-spring-boot-starter // sa-token 整合 WebFlux 快速集成 + ├── sa-token-reactor-spring-boot-starter // sa-token 整合 Reactor响应式编程 快速集成 ├── sa-token-dao-redis // sa-token 整合 Redis (使用jdk默认序列化方式) ├── sa-token-dao-redis-jackson // sa-token 整合 Redis (使用jackson序列化方式) ├── sa-token-spring-aop // sa-token 整合 SpringAOP 注解鉴权 diff --git a/sa-token-doc/doc/start/example.md b/sa-token-doc/doc/start/example.md index 2795eecd..f77eaf6a 100644 --- a/sa-token-doc/doc/start/example.md +++ b/sa-token-doc/doc/start/example.md @@ -1,21 +1,19 @@ -# 示例 +# SpringBoot 集成 Sa-Token 示例 本篇将带你从零开始集成sa-token,从而让你快速熟悉sa-token的使用姿势
-以Maven + SpringBoot为例 +整合示例在官方仓库的`/sa-token-demo-springboot`文件夹下,如遇到难点可结合源码进行测试学习 --- +### 1、创建项目 +在IDE中新建一个SpringBoot项目,例如:`sa-token-demo-springboot`(不会的同学请自行百度或者参考github示例) -## SpringBoot环境 -#### 1、创建项目 -在IDE中新建一个Springboot项目,例如:`sa-token-demo-springboot`(不会的同学请自行百度或者参考github示例) - -#### 2、设置jar包依赖 +### 2、设置pom包依赖 在 `pom.xml` 中添加依赖: ``` xml - + cn.dev33 sa-token-spring-boot-starter @@ -23,9 +21,9 @@ ``` -#### 3、配置文件 -你可以**零配置启动项目**
-但同时你也可以在`application.yml`中增加如下配置,定制性使用框架: + +### 3、设置配置文件 +你可以**零配置启动项目** ,但同时你也可以在`application.yml`中增加如下配置,定制性使用框架: ``` java spring: @@ -49,7 +47,7 @@ spring: 百度: [springboot properties与yml 配置文件的区别](https://www.baidu.com/s?ie=UTF-8&wd=springboot%20properties%E4%B8%8Eyml%20%E9%85%8D%E7%BD%AE%E6%96%87%E4%BB%B6%E7%9A%84%E5%8C%BA%E5%88%AB) -#### 4、创建启动类 +### 4、创建启动类 在项目中新建包 `com.pj` ,在此包内新建主类 `SaTokenDemoApplication.java`,输入以下代码: ``` java @@ -62,18 +60,18 @@ public class SaTokenDemoApplication { } ``` -#### 5、运行 +### 5、运行 运行代码,当你从控制台看到类似下面的内容时,就代表框架已经成功集成了 ![运行结果](https://color-test.oss-cn-qingdao.aliyuncs.com/sa-token/app-run.jpg) -## 普通Spring环境 +### 普通Spring环境 普通spring环境与springboot环境大体无异,只不过需要在项目根目录手动创建配置文件`sa-token.properties`来完成配置 -## 详细了解 -通过这个示例,你已经对sa-token有了初步的了解,那么现在开始详细了解一下它都有哪些[能力](/use/login-auth)吧 +### 详细了解 +通过这个示例,你已经对sa-token有了初步的了解,那么现在开始详细了解一下它都有哪些 [能力](/use/login-auth) 吧 diff --git a/sa-token-doc/doc/start/webflux-example.md b/sa-token-doc/doc/start/webflux-example.md new file mode 100644 index 00000000..002968d5 --- /dev/null +++ b/sa-token-doc/doc/start/webflux-example.md @@ -0,0 +1,76 @@ +# Spring WebFlux 集成 Sa-Token 示例 + +WebFlux基于Reactor响应式模型开发,有着与标准ServletAPI完全不同的底层架构,因此要适配WebFlux, 必须提供与Reactor相关的整合实现, +本篇将以WebFlux为例,展示sa-token与Reactor响应式模型web框架相整合的示例, **你可以用同样方式去对接其它Reactor模型Web框架** + +整合示例在官方仓库的`/sa-token-demo-webflux`文件夹下,如遇到难点可结合源码进行测试学习 + + +--- + +### 1、创建项目 +在IDE中新建一个SpringBoot项目,例如:`sa-token-demo-webflux`(不会的同学请自行百度或者参考github示例) + + +### 2、设置pom包依赖 +在 `pom.xml` 中添加依赖: + +``` xml + + + cn.dev33 + sa-token-reactor-spring-boot-starter + 1.15.2 + +``` + + +### 3、设置配置文件 +你可以**零配置启动项目** ,但同时你也可以在`application.yml`中增加如下配置,定制性使用框架: + +``` java +spring: + # sa-token配置 + sa-token: + # token名称 (同时也是cookie名称) + token-name: satoken + # token有效期,单位s 默认30天, -1代表永不过期 + timeout: 2592000 + # token临时有效期 (指定时间内无操作就视为token过期) 单位: 秒 + activity-timeout: -1 + # 是否允许同一账号并发登录 (为true时允许一起登录, 为false时新登录挤掉旧登录) + allow-concurrent-login: false + # 在多人登录同一账号时,是否共用一个token (为true时所有登录共用一个token, 为false时每次登录新建一个token) + is-share: false + # token风格 + token-style: uuid +``` + +如果你习惯于 `application.properties` 类型的配置文件,那也很好办:
+百度: [springboot properties与yml 配置文件的区别](https://www.baidu.com/s?ie=UTF-8&wd=springboot%20properties%E4%B8%8Eyml%20%E9%85%8D%E7%BD%AE%E6%96%87%E4%BB%B6%E7%9A%84%E5%8C%BA%E5%88%AB) + + +### 4、创建启动类 +在项目中新建包 `com.pj` ,在此包内新建主类 `SaTokenDemoApplication.java`,输入以下代码: + +``` java +@SpringBootApplication +public class SaTokenDemoApplication { + public static void main(String[] args) throws JsonProcessingException { + SpringApplication.run(SaTokenDemoApplication.class, args); + System.out.println("启动成功:sa-token配置如下:" + SaTokenManager.getConfig()); + } +} +``` + +### 5、运行 +运行代码,当你从控制台看到类似下面的内容时,就代表框架已经成功集成了 + +![运行结果](https://color-test.oss-cn-qingdao.aliyuncs.com/sa-token/app-run.jpg) + + + + + + + diff --git a/sa-token-doc/doc/use/at-check.md b/sa-token-doc/doc/use/at-check.md index 25b81c8f..161b0d69 100644 --- a/sa-token-doc/doc/use/at-check.md +++ b/sa-token-doc/doc/use/at-check.md @@ -84,11 +84,11 @@ mode有两种取值: ## 2、使用拦截器模式 使用AOP方式需要引入新的pom依赖,与此相比,拦截器模式显的更加轻量级
你只需要将sa-token的注解校验拦截器注册到你的项目中即可打开注解鉴权功能
-以`SpringBoot2.0`为例, 新建配置类`MySaTokenConfig.java` +以`SpringBoot2.0`为例, 新建配置类`SaTokenConfigure.java` ``` java @Configuration -public class MySaTokenConfig implements WebMvcConfigurer { +public class SaTokenConfigure implements WebMvcConfigurer { // 注册sa-token的注解拦截器,打开注解式鉴权功能 @Override public void addInterceptors(InterceptorRegistry registry) { diff --git a/sa-token-doc/doc/use/config.md b/sa-token-doc/doc/use/config.md index 6e539475..79d9b887 100644 --- a/sa-token-doc/doc/use/config.md +++ b/sa-token-doc/doc/use/config.md @@ -35,11 +35,11 @@ spring: * sa-token代码方式进行配置 */ @Configuration -public class MySaTokenConfig { +public class SaTokenConfigure { // 获取配置Bean (以代码的方式配置sa-token, 此配置会覆盖yml中的配置) @Primary - @Bean(name="MySaTokenConfig") + @Bean(name="SaTokenConfigure") public SaTokenConfig getSaTokenConfig() { SaTokenConfig config = new SaTokenConfig(); config.setTokenName("satoken"); // token名称 (同时也是cookie名称) diff --git a/sa-token-doc/doc/use/global-filter.md b/sa-token-doc/doc/use/global-filter.md new file mode 100644 index 00000000..9a9bb825 --- /dev/null +++ b/sa-token-doc/doc/use/global-filter.md @@ -0,0 +1,103 @@ +# 全局过滤器 +--- + +### 组件简述 + +上一节,我们学习了“根据拦截器实现路由拦截鉴权”,其实在大多数web框架中,使用过滤器可以实现同样的功能,本章我们就利用sa-token全局过滤器来实现路由拦截器鉴权。 + +首先我们先梳理清楚一个问题,既然拦截器已经可以实现路由鉴权,为什么还要用过滤器再实现一遍呢?简而言之: +1. 相比于拦截器,过滤器更加底层,执行时机更靠前,有利于防渗透扫描 +2. 过滤器可以拦截静态资源,方便我们做一些权限控制 +3. 部分Web框架根本就没有提供拦截器功能,但几乎所有的Web框架都会提供过滤器机制 + +但是过滤器也有一些缺点,比如: +1. 由于太过底层,导致无法率先拿到`HandlerMethod`对象,无法据此添加一些额外功能 +2. 由于拦截的太全面了,导致我们需要对很多特殊路由(如`/favicon.ico`)做一些额外处理 +3. 在Spring中,过滤器中抛出的异常无法进入全局`@ExceptionHandler`,我们必须额外编写代码进行异常处理 + +Sa-Token同时提供过滤器和拦截器机制,不是为了让谁替代谁,而是为了让大家根据自己的实际业务合理选择,拥有更多的发挥空间。 + + +### 注册过滤器 +同拦截器一样,为了避免不必要的性能浪费,sa-token全局过滤器默认处于关闭状态,若要使用过滤器组件,首先你需要注册它到项目中: +``` java +/** + * [Sa-Token 权限认证] 配置类 + * @author kong + */ +@Configuration +public class SaTokenConfigure { + + /** + * 注册 [sa-token全局过滤器] + */ + @Bean + public SaServletFilter getSaReactorFilter() { + return new SaServletFilter(); + } + + /** + * 注册 [sa-token全局过滤器-认证策略] + */ + @Bean + public SaFilterStrategy getSaFilterStrategy() { + return r -> { + System.out.println("---------- 进入sa-token全局过滤器 -----------"); + + // 登录验证 -- 拦截所有路由,并排除/user/doLogin 用于开放登录 + SaRouterUtil.match("/**", "/user/doLogin", () -> StpUtil.checkLogin()); + + // 权限认证 -- 不同模块, 校验不同权限 + SaRouterUtil.match("/user/**", () -> StpUtil.checkPermission("user")); + SaRouterUtil.match("/admin/**", () -> StpUtil.checkPermission("admin")); + SaRouterUtil.match("/goods/**", () -> StpUtil.checkPermission("goods")); + SaRouterUtil.match("/orders/**", () -> StpUtil.checkPermission("orders")); + SaRouterUtil.match("/notice/**", () -> StpUtil.checkPermission("notice")); + SaRouterUtil.match("/comment/**", () -> StpUtil.checkPermission("comment")); + + // 匹配 restful 风格路由 + SaRouterUtil.match("/article/get/{id}", () -> StpUtil.checkPermission("article")); + }; + } + + /** + * 注册 [sa-token全局过滤器-异常处理策略] + */ + @Bean + public SaFilterErrorStrategy getSaFilterErrorStrategy() { + return e -> AjaxJson.getError(e.getMessage()); + } + +} +``` + +### 注意事项 +- 在`[认证策略]`里,你可以和拦截器里一致的代码,进行路由匹配鉴权 +- 由于过滤器中抛出的异常不进入全局异常处理,所以你必须提供`[异常处理策略]`来处理`[认证策略]`里抛出的异常 +- 在`[异常处理策略]`里的返回值,将作为字符串输出到前端,如果需要定制化返回数据,请注意其中的格式转换 + + +### 在WebFlux中使用过滤器 +`Spring WebFlux`中不提供拦截器机制,因此若你的项目需要路由鉴权功能,过滤器是你唯一的选择,在`Spring WebFlux`注册过滤器的流程与上述流程几乎完全一致, +除了您需要将过滤器名称由`SaServletFilter`更换为`SaReactorFilter`以外,其它所有步骤均可参考以上示例 +``` java +/** + * [Sa-Token 权限认证] 配置类 + * @author kong + */ +@Configuration +public class SaTokenConfigure { + + /** + * 注册 [sa-token全局过滤器] + */ + @Bean + public SaReactorFilter getSaReactorFilter() { + return new SaReactorFilter(); + } + + // 其它代码 ... + +} +``` + \ No newline at end of file diff --git a/sa-token-doc/doc/use/route-check.md b/sa-token-doc/doc/use/route-check.md index e9d87b0d..f4627456 100644 --- a/sa-token-doc/doc/use/route-check.md +++ b/sa-token-doc/doc/use/route-check.md @@ -10,10 +10,10 @@ ## 1、注册路由拦截器 -以`SpringBoot2.0`为例, 新建配置类`MySaTokenConfig.java` +以`SpringBoot2.0`为例, 新建配置类`SaTokenConfigure.java` ``` java @Configuration -public class MySaTokenConfig implements WebMvcConfigurer { +public class SaTokenConfigure implements WebMvcConfigurer { // 注册sa-token的登录拦截器 @Override public void addInterceptors(InterceptorRegistry registry) { @@ -31,7 +31,7 @@ public class MySaTokenConfig implements WebMvcConfigurer { ``` java @Configuration -public class MySaTokenConfig implements WebMvcConfigurer { +public class SaTokenConfigure implements WebMvcConfigurer { @Override public void addInterceptors(InterceptorRegistry registry) { // 注册路由拦截器,自定义验证规则 @@ -53,7 +53,7 @@ public class MySaTokenConfig implements WebMvcConfigurer { ``` java @Configuration -public class MySaTokenConfig implements WebMvcConfigurer { +public class SaTokenConfigure implements WebMvcConfigurer { // 注册sa-token的拦截器 @Override public void addInterceptors(InterceptorRegistry registry) { diff --git a/sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/context/SaReactorFilter.java b/sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/filter/SaReactorFilter.java similarity index 91% rename from sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/context/SaReactorFilter.java rename to sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/filter/SaReactorFilter.java index 57c48f21..8e5eae3e 100644 --- a/sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/context/SaReactorFilter.java +++ b/sa-token-reactor-spring-boot-starter/src/main/java/cn/dev33/satoken/reactor/filter/SaReactorFilter.java @@ -1,4 +1,4 @@ -package cn.dev33.satoken.reactor.context; +package cn.dev33.satoken.reactor.filter; import org.springframework.core.annotation.Order; import org.springframework.web.server.ServerWebExchange; @@ -6,6 +6,8 @@ import org.springframework.web.server.WebFilter; import org.springframework.web.server.WebFilterChain; import cn.dev33.satoken.SaTokenManager; +import cn.dev33.satoken.reactor.context.SaReactorHolder; +import cn.dev33.satoken.reactor.context.SaReactorSyncHolder; import cn.dev33.satoken.util.SaTokenConsts; import reactor.core.publisher.Mono; diff --git a/sa-token-spring-boot-starter/src/main/java/cn/dev33/satoken/filter/SaServletFilter.java b/sa-token-spring-boot-starter/src/main/java/cn/dev33/satoken/filter/SaServletFilter.java new file mode 100644 index 00000000..579bdcd0 --- /dev/null +++ b/sa-token-spring-boot-starter/src/main/java/cn/dev33/satoken/filter/SaServletFilter.java @@ -0,0 +1,56 @@ +package cn.dev33.satoken.filter; + +import java.io.IOException; + +import javax.servlet.Filter; +import javax.servlet.FilterChain; +import javax.servlet.FilterConfig; +import javax.servlet.ServletException; +import javax.servlet.ServletRequest; +import javax.servlet.ServletResponse; + +import org.springframework.core.annotation.Order; + +import cn.dev33.satoken.SaTokenManager; +import cn.dev33.satoken.util.SaTokenConsts; + +/** + * Servlet全局过滤器 + * @author kong + * + */ +@Order(SaTokenConsts.ASSEMBLY_ORDER) +public class SaServletFilter implements Filter { + + @Override + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) + throws IOException, ServletException { + + try { + // 执行全局过滤器 + SaTokenManager.getSaFilterStrategy().run(null); + + } catch (Throwable e) { + // 1. 获取异常处理策略结果 + Object result = SaTokenManager.getSaFilterErrorStrategy().run(e); + String resultString = String.valueOf(result); + + // 2. 写入输出流 + response.setContentType("text/plain; charset=utf-8"); + response.getWriter().print(resultString); + return; + } + + // 执行 + chain.doFilter(request, response); + } + + @Override + public void init(FilterConfig filterConfig) throws ServletException { + } + + @Override + public void destroy() { + } + +}