mirror of
https://github.com/spring-projects/spring-security.git
synced 2025-06-26 22:02:41 +00:00
Polish AuthorizationCodeAuthenticationFilter
Fixes gh-4599
This commit is contained in:
parent
efa4bf409c
commit
da0a7afa38
@ -45,7 +45,6 @@ import org.springframework.security.oauth2.core.user.OAuth2User;
|
|||||||
import org.springframework.security.oauth2.oidc.client.authentication.OidcAuthorizationCodeAuthenticator;
|
import org.springframework.security.oauth2.oidc.client.authentication.OidcAuthorizationCodeAuthenticator;
|
||||||
import org.springframework.security.oauth2.oidc.client.user.OidcUserService;
|
import org.springframework.security.oauth2.oidc.client.user.OidcUserService;
|
||||||
import org.springframework.security.web.authentication.session.SessionAuthenticationStrategy;
|
import org.springframework.security.web.authentication.session.SessionAuthenticationStrategy;
|
||||||
import org.springframework.security.web.util.matcher.RequestMatcher;
|
|
||||||
import org.springframework.util.Assert;
|
import org.springframework.util.Assert;
|
||||||
|
|
||||||
import java.net.URI;
|
import java.net.URI;
|
||||||
@ -65,13 +64,13 @@ public class AuthorizationCodeGrantConfigurer<B extends HttpSecurityBuilder<B>>
|
|||||||
|
|
||||||
// ***** Authorization Request members
|
// ***** Authorization Request members
|
||||||
private AuthorizationCodeRequestRedirectFilter authorizationRequestFilter;
|
private AuthorizationCodeRequestRedirectFilter authorizationRequestFilter;
|
||||||
private String authorizationRequestBaseUri = AuthorizationCodeRequestRedirectFilter.DEFAULT_AUTHORIZATION_REQUEST_BASE_URI;
|
private String authorizationRequestBaseUri;
|
||||||
private AuthorizationRequestUriBuilder authorizationRequestBuilder;
|
private AuthorizationRequestUriBuilder authorizationRequestBuilder;
|
||||||
private AuthorizationRequestRepository authorizationRequestRepository;
|
private AuthorizationRequestRepository authorizationRequestRepository;
|
||||||
|
|
||||||
// ***** Authorization Response members
|
// ***** Authorization Response members
|
||||||
private AuthorizationCodeAuthenticationFilter authorizationResponseFilter;
|
private AuthorizationCodeAuthenticationFilter authorizationResponseFilter;
|
||||||
private RequestMatcher authorizationResponseMatcher;
|
private String authorizationResponseBaseUri;
|
||||||
private AuthorizationGrantAuthenticator<AuthorizationCodeAuthenticationToken> authorizationCodeAuthenticator;
|
private AuthorizationGrantAuthenticator<AuthorizationCodeAuthenticationToken> authorizationCodeAuthenticator;
|
||||||
private AuthorizationGrantTokenExchanger<AuthorizationCodeAuthenticationToken> authorizationCodeTokenExchanger;
|
private AuthorizationGrantTokenExchanger<AuthorizationCodeAuthenticationToken> authorizationCodeTokenExchanger;
|
||||||
private SecurityTokenRepository<AccessToken> accessTokenRepository;
|
private SecurityTokenRepository<AccessToken> accessTokenRepository;
|
||||||
@ -98,9 +97,9 @@ public class AuthorizationCodeGrantConfigurer<B extends HttpSecurityBuilder<B>>
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public AuthorizationCodeGrantConfigurer<B> authorizationResponseMatcher(RequestMatcher authorizationResponseMatcher) {
|
public AuthorizationCodeGrantConfigurer<B> authorizationResponseBaseUri(String authorizationResponseBaseUri) {
|
||||||
Assert.notNull(authorizationResponseMatcher, "authorizationResponseMatcher cannot be null");
|
Assert.hasText(authorizationResponseBaseUri, "authorizationResponseBaseUri cannot be empty");
|
||||||
this.authorizationResponseMatcher = authorizationResponseMatcher;
|
this.authorizationResponseBaseUri = authorizationResponseBaseUri;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -183,7 +182,7 @@ public class AuthorizationCodeGrantConfigurer<B extends HttpSecurityBuilder<B>>
|
|||||||
//
|
//
|
||||||
// -> AuthorizationCodeRequestRedirectFilter
|
// -> AuthorizationCodeRequestRedirectFilter
|
||||||
this.authorizationRequestFilter = new AuthorizationCodeRequestRedirectFilter(
|
this.authorizationRequestFilter = new AuthorizationCodeRequestRedirectFilter(
|
||||||
this.authorizationRequestBaseUri, this.getClientRegistrationRepository());
|
this.getAuthorizationRequestBaseUri(), this.getClientRegistrationRepository());
|
||||||
if (this.authorizationRequestBuilder != null) {
|
if (this.authorizationRequestBuilder != null) {
|
||||||
this.authorizationRequestFilter.setAuthorizationUriBuilder(this.authorizationRequestBuilder);
|
this.authorizationRequestFilter.setAuthorizationUriBuilder(this.authorizationRequestBuilder);
|
||||||
}
|
}
|
||||||
@ -192,11 +191,8 @@ public class AuthorizationCodeGrantConfigurer<B extends HttpSecurityBuilder<B>>
|
|||||||
}
|
}
|
||||||
|
|
||||||
// -> AuthorizationCodeAuthenticationFilter
|
// -> AuthorizationCodeAuthenticationFilter
|
||||||
this.authorizationResponseFilter = new AuthorizationCodeAuthenticationFilter();
|
this.authorizationResponseFilter = new AuthorizationCodeAuthenticationFilter(this.getAuthorizationResponseBaseUri());
|
||||||
this.authorizationResponseFilter.setClientRegistrationRepository(this.getClientRegistrationRepository());
|
this.authorizationResponseFilter.setClientRegistrationRepository(this.getClientRegistrationRepository());
|
||||||
if (this.authorizationResponseMatcher != null) {
|
|
||||||
this.authorizationResponseFilter.setAuthorizationResponseMatcher(this.authorizationResponseMatcher);
|
|
||||||
}
|
|
||||||
if (this.authorizationRequestRepository != null) {
|
if (this.authorizationRequestRepository != null) {
|
||||||
this.authorizationResponseFilter.setAuthorizationRequestRepository(this.authorizationRequestRepository);
|
this.authorizationResponseFilter.setAuthorizationRequestRepository(this.authorizationRequestRepository);
|
||||||
}
|
}
|
||||||
@ -219,15 +215,15 @@ public class AuthorizationCodeGrantConfigurer<B extends HttpSecurityBuilder<B>>
|
|||||||
}
|
}
|
||||||
|
|
||||||
String getAuthorizationRequestBaseUri() {
|
String getAuthorizationRequestBaseUri() {
|
||||||
return this.authorizationRequestBaseUri;
|
return this.authorizationRequestBaseUri != null ?
|
||||||
|
this.authorizationRequestBaseUri :
|
||||||
|
AuthorizationCodeRequestRedirectFilter.DEFAULT_AUTHORIZATION_REQUEST_BASE_URI;
|
||||||
}
|
}
|
||||||
|
|
||||||
AuthorizationCodeAuthenticationFilter getAuthorizationResponseFilter() {
|
String getAuthorizationResponseBaseUri() {
|
||||||
return this.authorizationResponseFilter;
|
return this.authorizationResponseBaseUri != null ?
|
||||||
}
|
this.authorizationResponseBaseUri :
|
||||||
|
AuthorizationCodeAuthenticationFilter.DEFAULT_AUTHORIZATION_RESPONSE_BASE_URI;
|
||||||
RequestMatcher getAuthorizationResponseMatcher() {
|
|
||||||
return this.authorizationResponseMatcher;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
AuthorizationRequestRepository getAuthorizationRequestRepository() {
|
AuthorizationRequestRepository getAuthorizationRequestRepository() {
|
||||||
|
@ -149,9 +149,9 @@ public final class OAuth2LoginConfigurer<B extends HttpSecurityBuilder<B>> exten
|
|||||||
private RedirectionEndpointConfig() {
|
private RedirectionEndpointConfig() {
|
||||||
}
|
}
|
||||||
|
|
||||||
public RedirectionEndpointConfig requestMatcher(RequestMatcher authorizationResponseMatcher) {
|
public RedirectionEndpointConfig baseUri(String authorizationResponseBaseUri) {
|
||||||
Assert.notNull(authorizationResponseMatcher, "authorizationResponseMatcher cannot be null");
|
Assert.hasText(authorizationResponseBaseUri, "authorizationResponseBaseUri cannot be empty");
|
||||||
authorizationCodeGrantConfigurer.authorizationResponseMatcher(authorizationResponseMatcher);
|
authorizationCodeGrantConfigurer.authorizationResponseBaseUri(authorizationResponseBaseUri);
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -209,9 +209,7 @@ public final class OAuth2LoginConfigurer<B extends HttpSecurityBuilder<B>> exten
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected RequestMatcher createLoginProcessingUrlMatcher(String loginProcessingUrl) {
|
protected RequestMatcher createLoginProcessingUrlMatcher(String loginProcessingUrl) {
|
||||||
return (this.authorizationCodeGrantConfigurer.getAuthorizationResponseMatcher() != null ?
|
return this.getAuthenticationFilter().getAuthorizationResponseMatcher();
|
||||||
this.authorizationCodeGrantConfigurer.getAuthorizationResponseMatcher() :
|
|
||||||
this.getAuthenticationFilter().getAuthorizationResponseMatcher());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private ClientRegistrationRepository getClientRegistrationRepository() {
|
private ClientRegistrationRepository getClientRegistrationRepository() {
|
||||||
@ -244,9 +242,11 @@ public final class OAuth2LoginConfigurer<B extends HttpSecurityBuilder<B>> exten
|
|||||||
}
|
}
|
||||||
|
|
||||||
Map<String, String> authenticationUrlToClientName = new HashMap<>();
|
Map<String, String> authenticationUrlToClientName = new HashMap<>();
|
||||||
clientRegistrations.forEach(registration -> authenticationUrlToClientName.put(
|
clientRegistrations.forEach(registration -> {
|
||||||
authorizationCodeGrantConfigurer.getAuthorizationRequestBaseUri() + "/" + registration.getRegistrationId(),
|
authenticationUrlToClientName.put(
|
||||||
registration.getClientName()));
|
authorizationCodeGrantConfigurer.getAuthorizationRequestBaseUri() + "/" + registration.getRegistrationId(),
|
||||||
|
registration.getClientName());
|
||||||
|
});
|
||||||
loginPageGeneratingFilter.setOauth2LoginEnabled(true);
|
loginPageGeneratingFilter.setOauth2LoginEnabled(true);
|
||||||
loginPageGeneratingFilter.setOauth2AuthenticationUrlToClientName(authenticationUrlToClientName);
|
loginPageGeneratingFilter.setOauth2AuthenticationUrlToClientName(authenticationUrlToClientName);
|
||||||
loginPageGeneratingFilter.setLoginPageUrl(this.getLoginPage());
|
loginPageGeneratingFilter.setLoginPageUrl(this.getLoginPage());
|
||||||
@ -261,10 +261,8 @@ public final class OAuth2LoginConfigurer<B extends HttpSecurityBuilder<B>> exten
|
|||||||
|
|
||||||
AuthorizationCodeAuthenticationFilter authorizationResponseFilter = getAuthenticationFilter();
|
AuthorizationCodeAuthenticationFilter authorizationResponseFilter = getAuthenticationFilter();
|
||||||
authorizationResponseFilter.setClientRegistrationRepository(getClientRegistrationRepository());
|
authorizationResponseFilter.setClientRegistrationRepository(getClientRegistrationRepository());
|
||||||
if (authorizationCodeGrantConfigurer.getAuthorizationResponseMatcher() != null) {
|
authorizationResponseFilter.setAuthorizationResponseBaseUri(
|
||||||
authorizationResponseFilter.setAuthorizationResponseMatcher(
|
authorizationCodeGrantConfigurer.getAuthorizationResponseBaseUri());
|
||||||
authorizationCodeGrantConfigurer.getAuthorizationResponseMatcher());
|
|
||||||
}
|
|
||||||
if (authorizationCodeGrantConfigurer.getAuthorizationRequestRepository() != null) {
|
if (authorizationCodeGrantConfigurer.getAuthorizationRequestRepository() != null) {
|
||||||
authorizationResponseFilter.setAuthorizationRequestRepository(
|
authorizationResponseFilter.setAuthorizationRequestRepository(
|
||||||
authorizationCodeGrantConfigurer.getAuthorizationRequestRepository());
|
authorizationCodeGrantConfigurer.getAuthorizationRequestRepository());
|
||||||
|
@ -83,30 +83,41 @@ public class AuthorizationCodeAuthenticationFilter extends AbstractAuthenticatio
|
|||||||
public static final String DEFAULT_AUTHORIZATION_RESPONSE_BASE_URI = "/oauth2/authorize/code";
|
public static final String DEFAULT_AUTHORIZATION_RESPONSE_BASE_URI = "/oauth2/authorize/code";
|
||||||
private static final String AUTHORIZATION_REQUEST_NOT_FOUND_ERROR_CODE = "authorization_request_not_found";
|
private static final String AUTHORIZATION_REQUEST_NOT_FOUND_ERROR_CODE = "authorization_request_not_found";
|
||||||
private final AuthorizationResponseConverter authorizationResponseConverter = new AuthorizationResponseConverter();
|
private final AuthorizationResponseConverter authorizationResponseConverter = new AuthorizationResponseConverter();
|
||||||
private ClientRegistrationRepository clientRegistrationRepository;
|
|
||||||
private RequestMatcher authorizationResponseMatcher = new AuthorizationResponseMatcher();
|
|
||||||
private AuthorizationRequestRepository authorizationRequestRepository = new HttpSessionAuthorizationRequestRepository();
|
|
||||||
private final ClientRegistrationIdentifierStrategy<String> providerIdentifierStrategy = new ProviderIdentifierStrategy();
|
private final ClientRegistrationIdentifierStrategy<String> providerIdentifierStrategy = new ProviderIdentifierStrategy();
|
||||||
|
private RequestMatcher authorizationResponseMatcher;
|
||||||
|
private ClientRegistrationRepository clientRegistrationRepository;
|
||||||
|
private AuthorizationRequestRepository authorizationRequestRepository = new HttpSessionAuthorizationRequestRepository();
|
||||||
|
|
||||||
public AuthorizationCodeAuthenticationFilter() {
|
public AuthorizationCodeAuthenticationFilter() {
|
||||||
super(new AuthorizationResponseMatcher());
|
this(DEFAULT_AUTHORIZATION_RESPONSE_BASE_URI);
|
||||||
|
}
|
||||||
|
|
||||||
|
public AuthorizationCodeAuthenticationFilter(String authorizationResponseBaseUri) {
|
||||||
|
super(new AuthorizationResponseMatcher(authorizationResponseBaseUri));
|
||||||
|
this.authorizationResponseMatcher = new AuthorizationResponseMatcher(authorizationResponseBaseUri);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void afterPropertiesSet() {
|
||||||
|
super.afterPropertiesSet();
|
||||||
|
Assert.notNull(this.clientRegistrationRepository, "clientRegistrationRepository cannot be null");
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response)
|
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response)
|
||||||
throws AuthenticationException, IOException, ServletException {
|
throws AuthenticationException, IOException, ServletException {
|
||||||
|
|
||||||
AuthorizationRequest authorizationRequest = this.getAuthorizationRequestRepository().loadAuthorizationRequest(request);
|
AuthorizationRequest authorizationRequest = this.authorizationRequestRepository.loadAuthorizationRequest(request);
|
||||||
if (authorizationRequest == null) {
|
if (authorizationRequest == null) {
|
||||||
OAuth2Error oauth2Error = new OAuth2Error(AUTHORIZATION_REQUEST_NOT_FOUND_ERROR_CODE);
|
OAuth2Error oauth2Error = new OAuth2Error(AUTHORIZATION_REQUEST_NOT_FOUND_ERROR_CODE);
|
||||||
throw new OAuth2AuthenticationException(oauth2Error, oauth2Error.toString());
|
throw new OAuth2AuthenticationException(oauth2Error, oauth2Error.toString());
|
||||||
}
|
}
|
||||||
this.getAuthorizationRequestRepository().removeAuthorizationRequest(request);
|
this.authorizationRequestRepository.removeAuthorizationRequest(request);
|
||||||
|
|
||||||
AuthorizationResponse authorizationResponse = this.authorizationResponseConverter.apply(request);
|
AuthorizationResponse authorizationResponse = this.authorizationResponseConverter.apply(request);
|
||||||
|
|
||||||
String registrationId = (String)authorizationRequest.getAdditionalParameters().get(OAuth2Parameter.REGISTRATION_ID);
|
String registrationId = (String)authorizationRequest.getAdditionalParameters().get(OAuth2Parameter.REGISTRATION_ID);
|
||||||
ClientRegistration clientRegistration = this.getClientRegistrationRepository().findByRegistrationId(registrationId);
|
ClientRegistration clientRegistration = this.clientRegistrationRepository.findByRegistrationId(registrationId);
|
||||||
|
|
||||||
// The clientRegistration.redirectUri may contain Uri template variables, whether it's configured by
|
// The clientRegistration.redirectUri may contain Uri template variables, whether it's configured by
|
||||||
// the user or configured by default. In these cases, the redirectUri will be expanded and ultimately changed
|
// the user or configured by default. In these cases, the redirectUri will be expanded and ultimately changed
|
||||||
@ -142,18 +153,14 @@ public class AuthorizationCodeAuthenticationFilter extends AbstractAuthenticatio
|
|||||||
return oauth2UserAuthentication;
|
return oauth2UserAuthentication;
|
||||||
}
|
}
|
||||||
|
|
||||||
public RequestMatcher getAuthorizationResponseMatcher() {
|
public final RequestMatcher getAuthorizationResponseMatcher() {
|
||||||
return this.authorizationResponseMatcher;
|
return this.authorizationResponseMatcher;
|
||||||
}
|
}
|
||||||
|
|
||||||
public final <T extends RequestMatcher> void setAuthorizationResponseMatcher(T authorizationResponseMatcher) {
|
public final void setAuthorizationResponseBaseUri(String authorizationResponseBaseUri) {
|
||||||
Assert.notNull(authorizationResponseMatcher, "authorizationResponseMatcher cannot be null");
|
Assert.hasText(authorizationResponseBaseUri, "authorizationResponseBaseUri cannot be empty");
|
||||||
this.authorizationResponseMatcher = authorizationResponseMatcher;
|
this.authorizationResponseMatcher = new AuthorizationResponseMatcher(authorizationResponseBaseUri);
|
||||||
this.setRequiresAuthenticationRequestMatcher(authorizationResponseMatcher);
|
this.setRequiresAuthenticationRequestMatcher(this.authorizationResponseMatcher);
|
||||||
}
|
|
||||||
|
|
||||||
protected ClientRegistrationRepository getClientRegistrationRepository() {
|
|
||||||
return this.clientRegistrationRepository;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public final void setClientRegistrationRepository(ClientRegistrationRepository clientRegistrationRepository) {
|
public final void setClientRegistrationRepository(ClientRegistrationRepository clientRegistrationRepository) {
|
||||||
@ -161,10 +168,6 @@ public class AuthorizationCodeAuthenticationFilter extends AbstractAuthenticatio
|
|||||||
this.clientRegistrationRepository = clientRegistrationRepository;
|
this.clientRegistrationRepository = clientRegistrationRepository;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected AuthorizationRequestRepository getAuthorizationRequestRepository() {
|
|
||||||
return this.authorizationRequestRepository;
|
|
||||||
}
|
|
||||||
|
|
||||||
public final void setAuthorizationRequestRepository(AuthorizationRequestRepository authorizationRequestRepository) {
|
public final void setAuthorizationRequestRepository(AuthorizationRequestRepository authorizationRequestRepository) {
|
||||||
Assert.notNull(authorizationRequestRepository, "authorizationRequestRepository cannot be null");
|
Assert.notNull(authorizationRequestRepository, "authorizationRequestRepository cannot be null");
|
||||||
this.authorizationRequestRepository = authorizationRequestRepository;
|
this.authorizationRequestRepository = authorizationRequestRepository;
|
||||||
@ -215,10 +218,17 @@ public class AuthorizationCodeAuthenticationFilter extends AbstractAuthenticatio
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static class AuthorizationResponseMatcher implements RequestMatcher {
|
private static class AuthorizationResponseMatcher implements RequestMatcher {
|
||||||
|
private final String baseUri;
|
||||||
|
|
||||||
|
private AuthorizationResponseMatcher(String baseUri) {
|
||||||
|
Assert.hasText(baseUri, "baseUri cannot be empty");
|
||||||
|
this.baseUri = baseUri;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean matches(HttpServletRequest request) {
|
public boolean matches(HttpServletRequest request) {
|
||||||
return this.successResponse(request) || this.errorResponse(request);
|
return request.getRequestURI().startsWith(this.baseUri) &&
|
||||||
|
(this.successResponse(request) || this.errorResponse(request));
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean successResponse(HttpServletRequest request) {
|
private boolean successResponse(HttpServletRequest request) {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user