Получить доступ

Spring Security: фильтр-цепочка и авторизация

SecurityFilterChain, аутентификация (UserDetailsService/PasswordEncoder), SecurityContext, авторизация запросов и CSRF/CORS/сессии.

SecurityFilterChain

Spring Security — это цепочка сервлет-фильтров ПЕРЕД DispatcherServlet (а не MVC-interceptor!). Запрос проходит через фильтры, каждый из которых отвечает за свой аспект: извлечь credentials, построить Authentication, проверить авторизацию, обработать отказ. Поэтому security срабатывает раньше контроллеров.

Современная конфигурация — это бин SecurityFilterChain (через HttpSecurity DSL). Старый WebSecurityConfigurerAdapter удалён в Spring Security 6, поэтому актуальные примеры — на бинах.

@Bean
SecurityFilterChain api(HttpSecurity http) throws Exception {
    return http
        .csrf(c -> c.disable())                 // stateless API
        .sessionManagement(s -> s.sessionCreationPolicy(STATELESS))
        .authorizeHttpRequests(a -> a
            .requestMatchers("/actuator/health").permitAll()
            .requestMatchers("/admin/**").hasRole("ADMIN")
            .anyRequest().authenticated())
        .oauth2ResourceServer(o -> o.jwt(Customizer.withDefaults()))
        .build();
}
Цепочка фильтров Spring Security: запрос проходит фильтры аутентификации и авторизации до контроллера; любой фильтр может отклонить запрос раньше.
Запрос проходит упорядоченную цепочку фильтров; любой из них может прервать обработку до контроллера.

Аутентификация

За проверку «кто ты» отвечает AuthenticationManager, делегирующий AuthenticationProvider'ам. Для логина по логину/паролю UserDetailsService загружает пользователя (из БД), а PasswordEncoder сверяет пароль.

Пароли ВСЕГДА хранят хешированными медленным алгоритмом с солью — BCrypt (или Argon2/scrypt). Никогда не хранить в открытом виде и не использовать быстрые хеши (MD5/SHA) — их перебирают мгновенно.

SecurityContext

После успешной аутентификации результат — Authentication (с principal и authorities) — кладётся в SecurityContextHolder, который по умолчанию держит его в ThreadLocal текущего запроса. Отсюда его берут и фильтры авторизации, и прикладной код (@AuthenticationPrincipal).

В stateless API контекст не хранится между запросами в сессии — он восстанавливается на КАЖДЫЙ запрос из bearer-токена соответствующим фильтром. Из-за ThreadLocal контекст не «переезжает» в другой поток (@Async) без специальной настройки.

Авторизация запросов

authorizeHttpRequests задаёт правила доступа по матчерам: requestMatchers("/admin/**").hasRole("ADMIN"), .authenticated(), .permitAll(). Правила проверяются по порядку — от частных к общему, а anyRequest() идёт последним.

Тонкость roles vs authorities: hasRole("ADMIN") внутри проверяет authority "ROLE_ADMIN" (префикс ROLE_ добавляется автоматически), а hasAuthority("...") сверяет строку как есть. Путаница с префиксом ROLE_ — частая причина «почему доступ не работает».

CSRF, CORS, сессии

CSRF-защита включена по умолчанию и нужна для stateful-сценариев (cookie/сессия, формы), где браузер сам шлёт credentials. Для stateless bearer-API (токен в заголовке Authorization, браузер не добавляет его автоматически) CSRF обычно отключают — и одновременно ставят session policy STATELESS.

CORS — это браузерная политика кросс-доменных запросов, а не авторизация; её настраивают в Security/MVC. XSS предотвращают на уровне вывода (экранирование, CSP) и тем, что чувствительные токены не кладут в доступное JS место.

Как отвечать на собеседовании

Объясните, что Security — цепочка фильтров до DispatcherServlet (не interceptor), и конфигурируется бином SecurityFilterChain (адаптер удалён в SS6). Разберите аутентификацию (UserDetailsService + PasswordEncoder=BCrypt, пароли только хешированные), SecurityContext в ThreadLocal, авторизацию запросов с ловушкой ROLE_-префикса, и когда отключать CSRF (stateless bearer).

Вопросы по теме

Читайте также

Закрытая бета

Знать тему — половина дела

На живом собеседовании sotto слышит вопрос интервьюера и показывает короткий ответ и план. Оставьте контакт — пришлём доступ и промокод.

  • Промокод на 2 часа — сверх пробных 30 минут
  • Программа для Windows — скачать сразу, войти — через Яндекс ID или VK ID
  • Прямая связь с разработчиком: что улучшить — сделаем