我的 Jhipster 项目为数据库中的用户提供了 JWT 身份验证机制,效果很好。我想添加一个 CustomAuthenticationProvider,这是一个与以下 this.
并行工作的第三方身份验证机制我创建了实现 AuthenticationProvider 的 CustomAuthenticationProvider。
我的安全配置文件,
import com.security.*;
import com.security.jwt.*;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Import;
import org.springframework.http.HttpMethod;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.http.SessionCreationPolicy;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.web.SecurityFilterChain;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
import org.springframework.security.web.header.writers.ReferrerPolicyHeaderWriter;
import org.springframework.web.filter.CorsFilter;
import org.zalando.problem.spring.web.advice.security.SecurityProblemSupport;
import tech.jhipster.config.JHipsterProperties;
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true, securedEnabled = true)
@Import(SecurityProblemSupport.class)
public class SecurityConfiguration {
private final JHipsterProperties jHipsterProperties;
private final TokenProvider tokenProvider;
private final CustomAuthenticationProvider customAuthenticationProvider;
private final UserDetailsService userDetailsService;
private final CorsFilter corsFilter;
private final SecurityProblemSupport problemSupport;
public SecurityConfiguration(
TokenProvider tokenProvider,
CorsFilter corsFilter,
JHipsterProperties jHipsterProperties,
CustomAuthenticationProvider customAuthenticationProvider,
UserDetailsService userDetailsService,
SecurityProblemSupport problemSupport
) {
this.tokenProvider = tokenProvider;
this.corsFilter = corsFilter;
this.customAuthenticationProvider = customAuthenticationProvider;
this.problemSupport = problemSupport;
this.jHipsterProperties = jHipsterProperties;
this.userDetailsService = userDetailsService;
}
@Bean
public PasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
@Bean
public AuthenticationManager authManager(HttpSecurity http) throws Exception {
AuthenticationManagerBuilder authenticationManagerBuilder = http.getSharedObject(AuthenticationManagerBuilder.class);
authenticationManagerBuilder.authenticationProvider(customAuthenticationProvider);
authenticationManagerBuilder.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
return authenticationManagerBuilder.build();
}
@Bean
public SecurityFilterChain filterChain(HttpSecurity http) throws Exception {
// @formatter:off
http
.csrf()
.disable()
.addFilterBefore(corsFilter, UsernamePasswordAuthenticationFilter.class)
.exceptionHandling()
.authenticationEntryPoint(problemSupport)
.accessDeniedHandler(problemSupport)
.and()
.headers()
.contentSecurityPolicy(jHipsterProperties.getSecurity().getContentSecurityPolicy())
.and()
.referrerPolicy(ReferrerPolicyHeaderWriter.ReferrerPolicy.STRICT_ORIGIN_WHEN_CROSS_ORIGIN)
.and()
.permissionsPolicy().policy("camera=(), fullscreen=(self), geolocation=(), gyroscope=(), magnetometer=(), microphone=(), midi=(), payment=(), sync-xhr=()")
.and()
.frameOptions().sameOrigin()
.and()
.sessionManagement()
.sessionCreationPolicy(SessionCreationPolicy.STATELESS)
.and()
.authorizeRequests()
.antMatchers(HttpMethod.OPTIONS, "/**").permitAll()
.antMatchers("/app/**/*.{js,html}").permitAll()
.antMatchers("/i18n/**").permitAll()
.antMatchers("/content/**").permitAll()
.antMatchers("/swagger-ui/**").permitAll()
.antMatchers("/test/**").permitAll()
.antMatchers("/api/authenticate").permitAll()
.antMatchers("/api/register").permitAll()
.antMatchers("/api/activate").permitAll()
.antMatchers("/api/account/reset-password/init").permitAll()
.antMatchers("/api/account/reset-password/finish").permitAll()
.antMatchers("/api/admin/**").hasAuthority(AuthoritiesConstants.ADMIN)
.antMatchers("/api/**").authenticated()
.antMatchers("/management/health").permitAll()
.antMatchers("/management/health/**").permitAll()
.antMatchers("/management/info").permitAll()
.antMatchers("/management/prometheus").permitAll()
.antMatchers("/management/**").hasAuthority(AuthoritiesConstants.ADMIN)
.and()
.httpBasic()
.and()
.apply(securityConfigurerAdapter());
return http.build();
// @formatter:on
}
private JWTConfigurer securityConfigurerAdapter() {
return new JWTConfigurer(tokenProvider);
}
}
}
然而,当开始调试时,我看到只有新的自定义提供程序被识别,默认的提供程序丢失了。所以在正常的用户场景中,我会得到这样的错误
{
"type": "https://www.jhipster.tech/problem/problem-with-message",
"title": "Unauthorized",
"status": 401,
"detail": "No AuthenticationProvider found for org.springframework.security.authentication.UsernamePasswordAuthenticationToken",
"path": "/api/authenticate",
"message": "error.http.401"
}
谁能帮我看看我错过了什么?