我正在尝试编写一个允许通过 JDBC 或 Google/Facebook 进行身份验证的网络应用程序;使用 Spring Security 5.0.x。我有有效的 Google 客户端 ID 和密码。 OAuth2 网络流程正确地将我带到 Google 以进行帐户选择和同意,但对 redirect_uri 的回调失败并显示 404。我看不出我做错了什么。
@Configuration
@EnableScheduling
@EnableWebSecurity
public class WebSecurityConfig
extends WebSecurityConfigurerAdapter
{
private static final Logger _logger = LogManager.getLogger (WebSecurityConfig.class);
private static String
SuccessUrl = "/api/auth/login-success",
FailureUrl = "/api/auth/login-failure",
LogoutUrl = "/api/auth/logout-done";
private static String
PGoogleId = "oauth2.google.id",
PGoogleSecret = "oauth2.google.secret",
PFacebookId = "oauth2.facebook.id",
PFacebookSecret = "oauth2.google.secret";
private final List<ClientRegistration> _regns;
@Autowired
private AuthSuccessHandler _success;
@Autowired
private AuthFailureHandler _failure;
@Autowired
private DataSource _source;
@Autowired
private MezoUserManager _userManager;
/**
* Sole Constructor
*/
public WebSecurityConfig ()
{
_regns = new ArrayList<> ();
}
@Autowired
public void setPropertiesFactory (
PropertiesFactoryBean factory)
throws IOException, AddressException
{
Properties p = factory.getObject ();
extractIdSecret (CommonOAuth2Provider.GOOGLE.getBuilder ("google"), PGoogleId, PGoogleSecret, p);
extractIdSecret (CommonOAuth2Provider.FACEBOOK.getBuilder ("facebook"), PFacebookId, PFacebookSecret, p);
}
private void extractIdSecret (
ClientRegistration.Builder builder,
String idKey,
String secretKey,
Properties properties)
{
String id = properties.getProperty (idKey);
String secret = properties.getProperty (secretKey);
if (StringUtils.isBlank (id) || StringUtils.isBlank (secret))
return;
_regns.add (builder.clientId (id).clientSecret (secret).build ());
}
@Override
protected void configure (
HttpSecurity http)
throws Exception
{
_success.setUrl (SuccessUrl);
_failure.setUrl (FailureUrl);
JdbcTokenRepositoryImpl repo = new JdbcTokenRepositoryImpl ();
repo.setDataSource (_source);
http
.authorizeRequests ()
.antMatchers ("/api/profile/**").authenticated ()
.antMatchers ("/api/users/**").hasAuthority (Authority.ROLE_ADMIN.name ())
.antMatchers ("/api/**").permitAll ()
.and ()
.exceptionHandling ()
.authenticationEntryPoint (new Http403ForbiddenEntryPoint())
.and ()
.formLogin ()
.loginProcessingUrl ("/login")
.loginPage ("/")
.successHandler (_success)
.failureHandler (_failure)
.and ()
.logout ()
.logoutUrl ("/logout")
.logoutSuccessUrl (LogoutUrl)
.and ()
.rememberMe ()
.tokenRepository (repo)
.tokenValiditySeconds (1209600)
.rememberMeParameter ("remember-me")
.and ()
.csrf ().disable ();
if (!_regns.isEmpty ())
{
http.oauth2Login ()
.clientRegistrationRepository (new InMemoryClientRegistrationRepository (_regns));
_logger.debug ("OAuth2 entabled");
}
}
@Override
protected void configure (
AuthenticationManagerBuilder builder)
throws Exception
{
DaoAuthenticationProvider provider = new DaoAuthenticationProvider ();
provider.setUserDetailsService (_userManager);
provider.setPasswordEncoder (encoder ());
builder.authenticationProvider (provider);
builder.userDetailsService (_userManager);
}
@Bean
public BCryptPasswordEncoder encoder ()
{
return new BCryptPasswordEncoder ();
}
}
来自 Google 的回调将转到正确的位置:
http://localhost:8080/mezo/login/oauth2/code/google?state=.....
但是我的 webapp 提示:
HTTP Status 404 - /mezo/login
谁能看到我在配置中遗漏了什么?为什么 Spring Security 没有自动为回调 uri 设置过滤器?
请注意,使用 JDBC 的登录当前适用于此配置。
最佳答案
解决方法是对 antMatchers()
放宽一点。特别是,扩展:
.antMatchers ("/api/**").permitAll ()
与:
.antMatchers ("/api/**", "/login/**").permitAll ()
关于spring-security - Spring Security OAuth2 redirect_uri 回调结果为 404,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51346388/