diff --git a/config/src/main/java/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurer.java b/config/src/main/java/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurer.java index bd104bd94c..344cd5ab9c 100644 --- a/config/src/main/java/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurer.java +++ b/config/src/main/java/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurer.java @@ -32,12 +32,13 @@ import org.springframework.security.config.annotation.web.builders.HttpSecurity; import org.springframework.security.core.AuthenticationException; import org.springframework.security.web.AuthenticationEntryPoint; import org.springframework.security.web.authentication.DelegatingAuthenticationEntryPoint; +import org.springframework.security.web.authentication.RememberMeServices; import org.springframework.security.web.authentication.WebAuthenticationDetailsSource; import org.springframework.security.web.authentication.www.BasicAuthenticationEntryPoint; import org.springframework.security.web.authentication.www.BasicAuthenticationFilter; -import org.springframework.security.web.util.matcher.RequestMatcher; import org.springframework.security.web.util.matcher.MediaTypeRequestMatcher; import org.springframework.security.web.util.matcher.RequestHeaderRequestMatcher; +import org.springframework.security.web.util.matcher.RequestMatcher; import org.springframework.web.accept.ContentNegotiationStrategy; import org.springframework.web.accept.HeaderContentNegotiationStrategy; @@ -167,6 +168,10 @@ public final class HttpBasicConfigurer> extends if(authenticationDetailsSource != null) { basicAuthenticationFilter.setAuthenticationDetailsSource(authenticationDetailsSource); } + RememberMeServices rememberMeServices = http.getSharedObject(RememberMeServices.class); + if(rememberMeServices != null) { + basicAuthenticationFilter.setRememberMeServices(rememberMeServices); + } basicAuthenticationFilter = postProcess(basicAuthenticationFilter); http.addFilter(basicAuthenticationFilter); } diff --git a/config/src/test/groovy/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurerTests.groovy b/config/src/test/groovy/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurerTests.groovy index 8d6cb934b7..107df8bffa 100644 --- a/config/src/test/groovy/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurerTests.groovy +++ b/config/src/test/groovy/org/springframework/security/config/annotation/web/configurers/HttpBasicConfigurerTests.groovy @@ -24,6 +24,7 @@ import org.springframework.security.config.annotation.web.configuration.EnableWe import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter import org.springframework.security.web.AuthenticationEntryPoint import org.springframework.security.web.access.ExceptionTranslationFilter +import org.springframework.security.web.authentication.rememberme.RememberMeAuthenticationFilter; import org.springframework.security.web.authentication.www.BasicAuthenticationEntryPoint import org.springframework.security.web.authentication.www.BasicAuthenticationFilter @@ -133,4 +134,29 @@ class HttpBasicConfigurerTests extends BaseSpringSpec { .inMemoryAuthentication() } } + + def "SEC-3019: Basic Authentication uses RememberMe Config"() { + when: + loadConfig(BasicUsesRememberMeConfig) + then: + findFilter(BasicAuthenticationFilter).rememberMeServices == findFilter(RememberMeAuthenticationFilter).rememberMeServices + } + + @EnableWebSecurity + @Configuration + static class BasicUsesRememberMeConfig extends WebSecurityConfigurerAdapter { + + @Override + protected void configure(HttpSecurity http) throws Exception { + http + .httpBasic().and() + .rememberMe() + } + + @Override + protected void configure(AuthenticationManagerBuilder auth) throws Exception { + auth + .inMemoryAuthentication() + } + } } \ No newline at end of file diff --git a/docs/manual/src/asciidoc/index.adoc b/docs/manual/src/asciidoc/index.adoc index 35421e736a..51b617a32a 100644 --- a/docs/manual/src/asciidoc/index.adoc +++ b/docs/manual/src/asciidoc/index.adoc @@ -2902,7 +2902,10 @@ create table persistent_logins (username varchar(64) not null, [[remember-me-impls]] === Remember-Me Interfaces and Implementations -Remember-me authentication is not used with basic authentication, given it is often not used with `HttpSession` s. Remember-me is used with `UsernamePasswordAuthenticationFilter`, and is implemented via hooks in the `AbstractAuthenticationProcessingFilter` superclass. The hooks will invoke a concrete `RememberMeServices` at the appropriate times. The interface looks like this: +Remember-me is used with `UsernamePasswordAuthenticationFilter`, and is implemented via hooks in the `AbstractAuthenticationProcessingFilter` superclass. +It is also used within `BasicAuthenticationFilter`. +The hooks will invoke a concrete `RememberMeServices` at the appropriate times. +The interface looks like this: [source,java] ----