![](/img/trans.png)
[英]How to replace UsernamePasswordAuthenticationFilter in Spring Security
[英]Spring Security 6 CustomAuthenticationFilter(intend to replace the UsernamePasswordAuthenticationFilter) does not work
通過引用https://www.baeldung.com/spring-security-extra-login-fields
我打算自定義 Spring 安全身份驗證 UsernamePasswordAuthenticationFilter 的功能以獲取額外的自定義“loginForm”字段。
我創建了一個自定義過濾器
CustomAuthenticationFilter extends UsernamePasswordAuthenticationFilter
和一個定制的身份驗證令牌
public class CustomAuthenticationToken extends UsernamePasswordAuthenticationToken
通過使用以下配置:
@EnableWebSecurity
@Configuration(proxyBeanMethods = false)
public class AuthenticationSecurityConfig extends AbstractHttpConfigurer<AuthenticationSecurityConfig, HttpSecurity> {
@Override
public void configure(HttpSecurity http) throws Exception {
AuthenticationManager authenticationManager = http.getSharedObject(AuthenticationManager.class);
http.addFilterBefore(authenticationFilter(authenticationManager), UsernamePasswordAuthenticationFilter.class);
}
@Bean
SecurityFilterChain defaultSecurityFilterChain(HttpSecurity http) throws Exception {
http.authorizeHttpRequests()
.requestMatchers("/css/**", "/login")
.permitAll()
.requestMatchers("/resources/**")
.permitAll()
.and()
.formLogin(form -> form
.loginPage("/login")
.permitAll()
)
.logout()
.logoutUrl("/logout")
.and()
.authorizeHttpRequests(
auth -> auth.anyRequest().authenticated()
)
.apply(securityConfig());
return http.build();
}
}
我可以成功地使我的 AuthenticationProvider 的
authenticate
要執行的方法,並且它可以成功返回一個“已驗證”
Authentication object.
但是它不會重定向到 OAuth2 客戶端的重定向頁面(我將我的項目設置為一個 OIDC 授權服務器),它會停留在登錄頁面,日志如下所示:
.HttpSessionRequestCache: 保存的請求http://192.168.0.107:9000/oauth2/authorize?client_id=messaging-client&redirect_uri=http%3A%2F%2F192.168.0.107%3A8080%2Fauth%2Fsigninwin%2_fmain&response=opentype&response %20message.read&state=802af0dcd82a483eb726c1dffff0867d&code_challenge=t_tfBjZPRd228uEZuQJ56clfXokGYqiwkudQqKhWQqo&code_challenge_method=S256&prompt=login&response_mode=query&continue&continue to session 2022-11-30T19:48:05.063+08:00 DEBUG 63801 --- [nio-9000-exec-5] ossweb.DefaultRedirectStrategy: Redirecting to http ://192.168.0.107:9000/login 2022-11-30T19:48:05.078+08:00 DEBUG 63801 --- [nio-9000-exec-6] osssecurity.web.FilterChainProxy:保護 GET /login 2022-11 -30T19:48:05.078+08:00 DEBUG 63801 --- [nio-9000-exec-6] osssecurity.web.FilterChainProxy: 安全 GET /login 2022-11-30T19:48:05.084+08:00 DEBUG 63801 - -- [nio-9000-exec-6] osswaAnonymousAuthenticationFilter:將 SecurityContextHolder 設置為匿名 S 安全上下文
如果我不使用自定義過濾器 CustomAuthenticationFilter,一切都會好起來的(但我當然無法獲得額外的 LoginForm 文件)。
我的 build.gradle
plugins {
id "org.springframework.boot" version "3.0.0-RC2"
id "io.spring.dependency-management" version "1.0.11.RELEASE"
id "java"
}
implementation "org.springframework.security:spring-security-oauth2-authorization-server:1.0.0"
有任何想法嗎?
我懷疑CustomAuthenticationFilter(使用new創建對象)的屬性與spring安全框架將初始化的UsernamePasswordAuthenticationFilter的屬性不一樣,需要進一步檢查差異。
有兩種解決方案,與之前版本的不同是因為這個改動:https://github.com/spring-projects/spring-security/issues/11110
***第一個解決方案***
您可以使用舊策略(已棄用)自動保存 SecurityContextHolder 設置:
http.securityContext((securityContext) -> securityContext.requireExplicitSave(false))
*** 第二種解決方案 ***
定義一個 HttpSessionSecurityContextRepository:
@Bean
public HttpSessionSecurityContextRepository securityContextRepository() {
return new HttpSessionSecurityContextRepository();
}
設置為http配置:
http.securityContext().securityContextRepository(securityContextRepository())
最后將上下文存儲庫設置為您的自定義過濾器:
filter.setSecurityContextRepository(securityContextRepository());
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.