Несколько SecurityFilterChains в Spring SecurityJAVA

Программисты JAVA общаются здесь
Anonymous
Несколько SecurityFilterChains в Spring Security

Сообщение Anonymous »

В моей конфигурации безопасности я хочу добавить различные виды цепочек фильтров безопасности.
Одна предназначена для вызовов /api с OAuth2, а другая — для вызовов /net со специальным значение заголовка с именем X-Authorization. В этом значении находится секретный ключ, который используется для авторизации.
Вот интересные части кода.

Код: Выделить всё

@Configuration
@EnableWebSecurity
public class SecurityConfiguration {

private final XAuthorizationFilter xAuthorizationFilter;

public SecurityConfiguration(XAuthorizationFilter xAuthorizationFilter) {
this.xAuthorizationFilter= xAuthorizationFilter;
}

@Bean
@Order(1)
public SecurityFilterChain xAuthorizationSecurityFilterChain(HttpSecurity http) throws Exception {
http
.securityMatcher(
"/net/**"
)
.addFilterAt(this.xAuthorizationFilter, AuthorizationFilter.class)
.authorizeHttpRequests(auth -> auth //
.requestMatchers("/net/url1").hasRole(NET)
.requestMatchers("/net/url2").hasRole(NET)
);
return http.build();
}

@Bean
@Order(2)
public SecurityFilterChain oAuth2SecurityFilterChain(HttpSecurity http) throws Exception {
http
.securityMatcher(
"/api/**",
"/health"
)
.authorizeHttpRequests(auth -> auth //
.requestMatchers("/api/admin/**").hasRole(ADMIN)
.requestMatchers("/api/**").hasRole(EMPLOYEE)
.requestMatchers("/health").permitAll() //
.anyRequest().denyAll() //
)
.oauth2ResourceServer(oauth2 -> oauth2 //
.jwt(jwt -> jwt //
.jwtAuthenticationConverter(new KeycloakJwtConverter()) //
) //
) //
.logout(logout -> logout //
.logoutSuccessHandler(new HttpStatusReturningLogoutSuccessHandler()) //
);
return http.build();
}
}
Мой собственный фильтр для определенного токена заголовка выглядит следующим образом:

Код: Выделить всё

@Component
public class XAuthorizationFilter implements Filter {

@Value("${net.authorization}")
private String netAuthorization;

@Value("${net.endpoints}")
private String[] netEndpoints;

@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain)
throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse;

if (this.isNetEndpoint(request)) {
String header = request.getHeader("X-Authorization");

if (header == null) {
response.setStatus(HttpServletResponse.SC_UNAUTHORIZED);
response.getWriter().write("Missing X-Authorization header.");
return;
}

if (!this.netAuthorization.equals(header)) {
response.setStatus(HttpServletResponse.SC_FORBIDDEN);
response.getWriter().write("Invalid X-Authorization header.");
return;
}

SimpleGrantedAuthority authority = new SimpleGrantedAuthority("ROLE_NET");
Authentication authentication = new UsernamePasswordAuthenticationToken("xUser", null, Collections.singleton(authority));
SecurityContextHolder.getContext().setAuthentication(authentication);
}

filterChain.doFilter(request, response);
}

private boolean isNetEndpoint(HttpServletRequest request) {
return Arrays.stream(this.netEndpoints).anyMatch(endpoint -> endpoint.equals(request.getRequestURI()));
}

@Override
public void init(FilterConfig filterConfig) {
// no implementation needed
}

@Override
public void destroy() {
// no implementation needed
}

}
Теперь я вызываю конечную точку, начинающуюся с /net (например, /net/url1), но затем получаю код 401, поскольку токен носителя отсутствует. Это указывает на то, что использовалась цепочка фильтров безопасности oAuth2.
Как я могу это исправить?
Я уже пытался найти решения в stackoverflow и там где есть несколько хороших записей об отсутствии средства сопоставления безопасности.
Я сверяюсь с документами весной, но безуспешно.

Подробнее здесь: https://stackoverflow.com/questions/787 ... g-security

Вернуться в «JAVA»