pathList) {
+ excludeList = pathList;
+ return this;
+ }
+
+
+ // ------------------------ 钩子函数
+
+ /**
+ * 认证函数:每次请求执行
+ */
+ public SaFilterAuthStrategy auth = r -> {};
+
+ /**
+ * 异常处理函数:每次[认证函数]发生异常时执行此函数
+ */
+ public SaFilterErrorStrategy error = e -> {
+ throw new SaTokenException(e);
+ };
+
+ /**
+ * 前置函数:在每次[认证函数]之前执行
+ * 注意点:前置认证函数将不受 includeList 与 excludeList 的限制,所有路由的请求都会进入 beforeAuth
+ */
+ public SaFilterAuthStrategy beforeAuth = r -> {};
+
+ @Override
+ public SaServletFilter setAuth(SaFilterAuthStrategy auth) {
+ this.auth = auth;
+ return this;
+ }
+
+ @Override
+ public SaServletFilter setError(SaFilterErrorStrategy error) {
+ this.error = error;
+ return this;
+ }
+
+ @Override
+ public SaServletFilter setBeforeAuth(SaFilterAuthStrategy beforeAuth) {
+ this.beforeAuth = beforeAuth;
+ return this;
+ }
+
+
+ // ------------------------ doFilter
+
+ @Override
+ public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
+
+ try {
+ // 执行全局过滤器
+ beforeAuth.run(null);
+ SaRouter.match(includeList).notMatch(excludeList).check(r -> {
+ auth.run(null);
+ });
+ }
+ catch (StopMatchException ignored) {}
+ catch (BackResultException e) {
+ SaJakartaServletOperateUtil.writeResult(response, e.getMessage());
+ return;
+ }
+ catch (Throwable e) {
+ SaJakartaServletOperateUtil.writeResult(response, String.valueOf(error.run(e)));
+ return;
+ }
+
+ // 执行
+ chain.doFilter(request, response);
+ }
+
+}
diff --git a/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenContextFilterForJakartaServlet.java b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenContextFilterForJakartaServlet.java
new file mode 100644
index 00000000..22dce8ce
--- /dev/null
+++ b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenContextFilterForJakartaServlet.java
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2020-2099 sa-token.cc
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package cn.dev33.satoken.filter;
+
+import cn.dev33.satoken.servlet.util.SaTokenContextJakartaServletUtil;
+import cn.dev33.satoken.util.SaTokenConsts;
+import jakarta.servlet.*;
+import jakarta.servlet.http.HttpServletRequest;
+import jakarta.servlet.http.HttpServletResponse;
+import org.springframework.core.annotation.Order;
+
+import java.io.IOException;
+
+/**
+ * SaTokenContext 上下文初始化过滤器 (基于 Jakarta-Servlet)
+ *
+ * @author click33
+ * @since 1.42.0
+ */
+@Order(SaTokenConsts.SA_TOKEN_CONTEXT_FILTER_ORDER)
+public class SaTokenContextFilterForJakartaServlet implements Filter {
+
+ @Override
+ public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
+ try {
+ SaTokenContextJakartaServletUtil.setContext((HttpServletRequest) request, (HttpServletResponse) response);
+ chain.doFilter(request, response);
+ } finally {
+ SaTokenContextJakartaServletUtil.clearContext();
+ }
+ }
+
+}
diff --git a/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenCorsFilterForJakartaServlet.java b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenCorsFilterForJakartaServlet.java
new file mode 100644
index 00000000..f0c04a99
--- /dev/null
+++ b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/filter/SaTokenCorsFilterForJakartaServlet.java
@@ -0,0 +1,55 @@
+/*
+ * Copyright 2020-2099 sa-token.cc
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package cn.dev33.satoken.filter;
+
+import cn.dev33.satoken.context.SaHolder;
+import cn.dev33.satoken.context.model.SaTokenContextModelBox;
+import cn.dev33.satoken.exception.BackResultException;
+import cn.dev33.satoken.exception.StopMatchException;
+import cn.dev33.satoken.servlet.util.SaJakartaServletOperateUtil;
+import cn.dev33.satoken.strategy.SaStrategy;
+import cn.dev33.satoken.util.SaTokenConsts;
+import jakarta.servlet.*;
+import org.springframework.core.annotation.Order;
+
+import java.io.IOException;
+
+/**
+ * CORS 跨域策略过滤器 (基于 Jakarta-Servlet)
+ *
+ * @author click33
+ * @since 1.42.0
+ */
+@Order(SaTokenConsts.CORS_FILTER_ORDER)
+public class SaTokenCorsFilterForJakartaServlet implements Filter {
+
+ @Override
+ public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
+
+ try {
+ SaTokenContextModelBox box = SaHolder.getContext().getModelBox();
+ SaStrategy.instance.corsHandle.execute(box.getRequest(), box.getResponse(), box.getStorage());
+ }
+ catch (StopMatchException ignored) {}
+ catch (BackResultException e) {
+ SaJakartaServletOperateUtil.writeResult(response, e.getMessage());
+ return;
+ }
+
+ chain.doFilter(request, response);
+ }
+
+}
diff --git a/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/interceptor/SaInterceptor.java b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/interceptor/SaInterceptor.java
new file mode 100644
index 00000000..f42e892a
--- /dev/null
+++ b/sa-token-starter/sa-token-spring-boot4-starter/src/main/java/cn/dev33/satoken/interceptor/SaInterceptor.java
@@ -0,0 +1,122 @@
+/*
+ * Copyright 2020-2099 sa-token.cc
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package cn.dev33.satoken.interceptor;
+
+import cn.dev33.satoken.exception.BackResultException;
+import cn.dev33.satoken.exception.StopMatchException;
+import cn.dev33.satoken.fun.SaParamFunction;
+import cn.dev33.satoken.strategy.SaAnnotationStrategy;
+import jakarta.servlet.http.HttpServletRequest;
+import jakarta.servlet.http.HttpServletResponse;
+import org.springframework.web.method.HandlerMethod;
+import org.springframework.web.servlet.HandlerInterceptor;
+
+import java.lang.reflect.Method;
+
+/**
+ * Sa-Token 综合拦截器,提供注解鉴权和路由拦截鉴权能力
+ *
+ * @author click33
+ * @since 1.34.0
+ */
+public class SaInterceptor implements HandlerInterceptor {
+
+ /**
+ * 是否打开注解鉴权
+ */
+ public boolean isAnnotation = true;
+
+ /**
+ * 认证函数:每次请求执行
+ * 参数:路由处理函数指针
+ */
+ public SaParamFunction