From 8bc9b1ebdabaacc0ba8837829f7b4b7f9380d715 Mon Sep 17 00:00:00 2001 From: XuqmGroup Date: Mon, 18 May 2026 15:40:11 +0800 Subject: [PATCH] fix(file-service): use AntPathRequestMatcher to bypass Spring MVC matching Spring Security 6 with MVC on classpath resolves requestMatchers(HttpMethod, String) to MvcRequestMatcher, which fails to match the actual servlet paths for this service. Switching to explicit AntPathRequestMatcher instances bypasses MVC introspection and forces pure Ant pattern evaluation, fixing persistent 401 on public upload/serve endpoints. Co-Authored-By: Claude Sonnet 4.6 --- .../java/com/xuqm/file/config/SecurityConfig.java | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/file-service/src/main/java/com/xuqm/file/config/SecurityConfig.java b/file-service/src/main/java/com/xuqm/file/config/SecurityConfig.java index a402a09..af90a50 100644 --- a/file-service/src/main/java/com/xuqm/file/config/SecurityConfig.java +++ b/file-service/src/main/java/com/xuqm/file/config/SecurityConfig.java @@ -5,13 +5,13 @@ import com.xuqm.common.security.JwtUtil; import jakarta.servlet.http.HttpServletResponse; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; -import org.springframework.http.HttpMethod; import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer; import org.springframework.security.config.http.SessionCreationPolicy; import org.springframework.security.web.SecurityFilterChain; import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter; +import org.springframework.security.web.util.matcher.AntPathRequestMatcher; import org.springframework.web.cors.CorsConfiguration; import org.springframework.web.cors.CorsConfigurationSource; import org.springframework.web.cors.UrlBasedCorsConfigurationSource; @@ -35,13 +35,11 @@ public class SecurityConfig { .cors(cors -> {}) .sessionManagement(sm -> sm.sessionCreationPolicy(SessionCreationPolicy.STATELESS)) .authorizeHttpRequests(auth -> auth - .requestMatchers(HttpMethod.OPTIONS, "/**").permitAll() - // Public: file upload and serving (AntRequestMatcher via explicit method) - .requestMatchers(HttpMethod.POST, "/api/file/upload").permitAll() - .requestMatchers(HttpMethod.GET, "/api/file/*/thumbnail").permitAll() - .requestMatchers(HttpMethod.GET, "/api/file/*").permitAll() - // Actuator health & info - .requestMatchers(HttpMethod.GET, "/actuator/**").permitAll() + .requestMatchers(new AntPathRequestMatcher("/**", "OPTIONS")).permitAll() + .requestMatchers(new AntPathRequestMatcher("/api/file/upload", "POST")).permitAll() + .requestMatchers(new AntPathRequestMatcher("/api/file/*/thumbnail", "GET")).permitAll() + .requestMatchers(new AntPathRequestMatcher("/api/file/*", "GET")).permitAll() + .requestMatchers(new AntPathRequestMatcher("/actuator/**", "GET")).permitAll() .anyRequest().authenticated() ) .exceptionHandling(ex -> ex