引入spring-cloud-starter-gateway后Spring Security认证授权失效如何解决
问题根因
- 依赖栈冲突:Spring Cloud Gateway 底层基于 Reactive 响应式技术栈(WebFlux + Netty)运行,而你引入的
spring-boot-starter-web属于 Servlet 阻塞式技术栈(Tomcat),二者底层容器完全不兼容,同时存在会导致应用运行时资源加载混乱,安全配置优先级被覆盖。 - 安全配置不兼容:你当前使用的
@EnableWebSecurity、WebSecurityConfigurerAdapter都是 Servlet 体系下的 Spring Security 配置类,完全不适用于 WebFlux 环境,引入 Gateway 依赖后该配置根本不会被加载,认证授权自然失效。 - 过滤器不兼容:你自定义的 JWT 过滤器是基于 Servlet 的
Filter接口实现的,在 WebFlux 环境下不会进入该过滤器链,无法完成账号校验、Token 解析等认证逻辑。
可行解决方案
步骤1:清理POM依赖
直接删除 spring-boot-starter-web 依赖即可,spring-cloud-starter-gateway 已经内置了 spring-boot-starter-webflux,不需要额外引入响应式web依赖。
步骤2:重构安全配置类
废弃原有基于 WebSecurityConfigurerAdapter 的Servlet体系配置,改用WebFlux专属的安全配置,参考代码如下:
@Configuration @EnableWebFluxSecurity class ReactiveSecurityConfig { @Autowired private lateinit var passwordEncoder: PasswordEncoder @Autowired private lateinit var reactiveAppUserService: ReactiveUserDetailsService @Autowired private lateinit var configs: Configs @Bean fun securityWebFilterChain(http: ServerHttpSecurity): SecurityWebFilterChain { return http .csrf { it.disable() } .httpBasic { it.disable() } .formLogin { it.disable() } .sessionManagement { it.sessionCreationPolicy(SessionCreationPolicy.STATELESS) } .authenticationManager(reactiveAuthenticationManager()) .addFilterAt(JWTAuthenticationWebFilter(reactiveAuthenticationManager(), configs), SecurityWebFiltersOrder.AUTHENTICATION) .addFilterAfter(JWTVerifierWebFilter(configs), SecurityWebFiltersOrder.AUTHENTICATION) .authorizeExchange { exchanges -> exchanges.pathMatchers(HttpMethod.POST, "/database").hasAuthority(AppUserPermission.ADMIN_WRITE.permission) .pathMatchers(HttpMethod.PUT, "/database").hasAuthority(AppUserPermission.ADMIN_WRITE.permission) .pathMatchers(HttpMethod.DELETE, "/database").hasAuthority(AppUserPermission.ADMIN_WRITE.permission) .pathMatchers(HttpMethod.GET, "/database").hasAnyRole(AppUserRole.ADMIN.name, AppUserRole.ADMIN_TRAINEE.name) .pathMatchers( "/v2/api-docs", "/swagger-ui/index.html", "/swagger-ui/**", "/swagger-ui.html", "/swagger-resources/**", "/webjars/**", "/hello/sendEmail" ).permitAll() .anyExchange().authenticated() } .build() } @Bean fun reactiveAuthenticationManager(): ReactiveAuthenticationManager { val provider = UserDetailsRepositoryReactiveAuthenticationManager(reactiveAppUserService) provider.setPasswordEncoder(passwordEncoder) return provider } }
步骤3:重构自定义过滤器
将原有基于Servlet Filter 实现的 JWTUsernameAndPasswordAuthenticationFilter、JWTVerifier 过滤器,改为实现WebFlux的 WebFilter 接口,适配响应式的 ServerHttpRequest、ServerHttpResponse 处理逻辑。
步骤4:调整用户查询逻辑
将原有实现 UserDetailsService 接口的 AppUserService,改为实现 ReactiveUserDetailsService 接口,返回 Mono<UserDetails> 类型的结果适配响应式调用。
内容的提问来源于stack exchange,提问作者Sagar Nayak
相关产品推荐
相关产品推荐

