Compare commits
48 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 59b7b55cf8 | |||
| b896a74669 | |||
| 91832bfc8e | |||
| 30c9860fc3 | |||
| 4787efb40b | |||
| b712c24a88 | |||
| 70a950119c | |||
| b8e9f47dd4 | |||
| 04baead7c0 | |||
| a0a9b48224 | |||
| 9363959566 | |||
| f38129b5a0 | |||
| 47432505fc | |||
| 6542509207 | |||
| 7d55c079c9 | |||
| e44fc3817a | |||
| 5c7237be79 | |||
| 1414b88ef3 | |||
| ba520db7f7 | |||
| 85248083c0 | |||
| 992b9d5fb1 | |||
| a91433d52b | |||
| 620136ff18 | |||
| d34bd346c0 | |||
| be09ed7e2b | |||
| d224dbe334 | |||
| c62168ca5b | |||
| d0b2b33dce | |||
| 7881660ca0 | |||
| 96c47b30d3 | |||
| 506e5b7f11 | |||
| a5cd7ce122 | |||
| a7bf8f7cc6 | |||
| 451fbf0227 | |||
| 0eaffb37e7 | |||
| d985d044bc | |||
| c24b5ebe98 | |||
| fd900c288e | |||
| e86d88d0cf | |||
| f28c26fd54 | |||
| 421430330a | |||
| 5c2106b22e | |||
| 48241deba3 | |||
| 9cc11be9f3 | |||
| e48d6b039b | |||
| dd3c6892e9 | |||
| c552366a78 | |||
| 7215c72373 |
@@ -21,6 +21,8 @@ See https://docs.spring.io/spring-security/reference/getting-spring-security.htm
|
||||
Be sure to read the https://docs.spring.io/spring-security/reference/[Spring Security Reference].
|
||||
Extensive JavaDoc for the Spring Security code is also available in the https://docs.spring.io/spring-security/site/docs/current/api/[Spring Security API Documentation].
|
||||
|
||||
You may also want to check out https://docs.spring.io/spring-security/reference/whats-new.html[what's new in the latest release].
|
||||
|
||||
== Quick Start
|
||||
See https://docs.spring.io/spring-security/reference/servlet/getting-started.html[Hello Spring Security] to get started with a "Hello, World" application.
|
||||
|
||||
|
||||
+3
-3
@@ -45,7 +45,7 @@ class ReactiveObservationConfiguration {
|
||||
|
||||
@Bean
|
||||
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
|
||||
static ObjectPostProcessor<ReactiveAuthorizationManager<ServerWebExchange>> webAuthorizationManagerPostProcessor(
|
||||
static ObjectPostProcessor<ReactiveAuthorizationManager<ServerWebExchange>> rSocketAuthorizationManagerPostProcessor(
|
||||
ObjectProvider<ObservationRegistry> registry, ObjectProvider<SecurityObservationSettings> predicate) {
|
||||
return new ObjectPostProcessor<>() {
|
||||
@Override
|
||||
@@ -59,7 +59,7 @@ class ReactiveObservationConfiguration {
|
||||
|
||||
@Bean
|
||||
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
|
||||
static ObjectPostProcessor<ReactiveAuthenticationManager> authenticationManagerPostProcessor(
|
||||
static ObjectPostProcessor<ReactiveAuthenticationManager> rSocketAuthenticationManagerPostProcessor(
|
||||
ObjectProvider<ObservationRegistry> registry, ObjectProvider<SecurityObservationSettings> predicate) {
|
||||
return new ObjectPostProcessor<>() {
|
||||
@Override
|
||||
@@ -73,7 +73,7 @@ class ReactiveObservationConfiguration {
|
||||
|
||||
@Bean
|
||||
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
|
||||
static ObjectPostProcessor<WebFilterChainDecorator> filterChainDecoratorPostProcessor(
|
||||
static ObjectPostProcessor<WebFilterChainDecorator> rSocketFilterChainDecoratorPostProcessor(
|
||||
ObjectProvider<ObservationRegistry> registry, ObjectProvider<SecurityObservationSettings> predicate) {
|
||||
return new ObjectPostProcessor<>() {
|
||||
@Override
|
||||
|
||||
+1
-1
@@ -41,7 +41,7 @@ class WebSocketObservationConfiguration {
|
||||
|
||||
@Bean
|
||||
@Role(BeanDefinition.ROLE_INFRASTRUCTURE)
|
||||
static ObjectPostProcessor<AuthorizationManager<Message<?>>> webAuthorizationManagerPostProcessor(
|
||||
static ObjectPostProcessor<AuthorizationManager<Message<?>>> webSocketAuthorizationManagerPostProcessor(
|
||||
ObjectProvider<ObservationRegistry> registry, ObjectProvider<SecurityObservationSettings> predicate) {
|
||||
return new ObjectPostProcessor<>() {
|
||||
@Override
|
||||
|
||||
+15
@@ -68,6 +68,7 @@ import org.springframework.security.authentication.TestingAuthenticationToken;
|
||||
import org.springframework.security.authorization.AuthorizationDecision;
|
||||
import org.springframework.security.authorization.AuthorizationManager;
|
||||
import org.springframework.security.config.annotation.SecurityContextChangedListenerConfig;
|
||||
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
|
||||
import org.springframework.security.config.annotation.web.messaging.MessageSecurityMetadataSourceRegistry;
|
||||
import org.springframework.security.config.observation.SecurityObservationSettings;
|
||||
import org.springframework.security.core.Authentication;
|
||||
@@ -438,6 +439,12 @@ public class WebSocketMessageBrokerSecurityConfigurationTests {
|
||||
verifyNoInteractions(observationHandler);
|
||||
}
|
||||
|
||||
// gh-16011
|
||||
@Test
|
||||
public void enableWebSocketSecurityWhenWebSocketSecurityUsedThenAutowires() {
|
||||
loadConfig(WithWebSecurity.class);
|
||||
}
|
||||
|
||||
private void assertHandshake(HttpServletRequest request) {
|
||||
TestHandshakeHandler handshakeHandler = this.context.getBean(TestHandshakeHandler.class);
|
||||
assertThatCsrfToken(handshakeHandler.attributes.get(CsrfToken.class.getName())).isEqualTo(this.token);
|
||||
@@ -489,6 +496,7 @@ public class WebSocketMessageBrokerSecurityConfigurationTests {
|
||||
|
||||
private void loadConfig(Class<?>... configs) {
|
||||
this.context = new AnnotationConfigWebApplicationContext();
|
||||
this.context.setAllowBeanDefinitionOverriding(false);
|
||||
this.context.register(configs);
|
||||
this.context.setServletConfig(new MockServletConfig());
|
||||
this.context.refresh();
|
||||
@@ -939,6 +947,13 @@ public class WebSocketMessageBrokerSecurityConfigurationTests {
|
||||
|
||||
}
|
||||
|
||||
@Configuration(proxyBeanMethods = false)
|
||||
@EnableWebSecurity
|
||||
@Import(WebSocketSecurityConfig.class)
|
||||
static class WithWebSecurity {
|
||||
|
||||
}
|
||||
|
||||
@Configuration
|
||||
static class SyncExecutorConfig {
|
||||
|
||||
|
||||
@@ -31,7 +31,7 @@ urls:
|
||||
redirect_facility: httpd
|
||||
ui:
|
||||
bundle:
|
||||
url: https://github.com/spring-io/antora-ui-spring/releases/download/v0.4.17/ui-bundle.zip
|
||||
url: https://github.com/spring-io/antora-ui-spring/releases/download/v0.4.18/ui-bundle.zip
|
||||
snapshot: true
|
||||
runtime:
|
||||
log:
|
||||
|
||||
@@ -12,4 +12,6 @@ If you are ready to start securing an application see the Getting Started sectio
|
||||
If you want to understand how Spring Security works, you can refer to the xref:servlet/architecture.adoc[Architecture] section.
|
||||
// FIXME add link to reactive architecture
|
||||
|
||||
If you are already familiar with Spring Security or are upgrading, check out https://docs.spring.io/spring-security/reference/whats-new.html[what's new in the latest release].
|
||||
|
||||
If you have any questions, there is a wonderful xref:community.adoc[community] that would love to help you!
|
||||
|
||||
@@ -14,6 +14,7 @@ The following image shows the typical layering of the handlers for a single HTTP
|
||||
|
||||
.FilterChain
|
||||
[[servlet-filterchain-figure]]
|
||||
[.invert-dark]
|
||||
image::{figures}/filterchain.png[]
|
||||
|
||||
The client sends a request to the application, and the container creates a `FilterChain`, which contains the `Filter` instances and `Servlet` that should process the `HttpServletRequest`, based on the path of the request URI.
|
||||
@@ -66,6 +67,7 @@ Here is a picture of how `DelegatingFilterProxy` fits into the <<servlet-filters
|
||||
|
||||
.DelegatingFilterProxy
|
||||
[[servlet-delegatingfilterproxy-figure]]
|
||||
[.invert-dark]
|
||||
image::{figures}/delegatingfilterproxy.png[]
|
||||
|
||||
`DelegatingFilterProxy` looks up __Bean Filter~0~__ from the `ApplicationContext` and then invokes __Bean Filter~0~__.
|
||||
@@ -113,6 +115,7 @@ The following image shows the role of `FilterChainProxy`.
|
||||
|
||||
.FilterChainProxy
|
||||
[[servlet-filterchainproxy-figure]]
|
||||
[.invert-dark]
|
||||
image::{figures}/filterchainproxy.png[]
|
||||
|
||||
[[servlet-securityfilterchain]]
|
||||
@@ -124,6 +127,7 @@ The following image shows the role of `SecurityFilterChain`.
|
||||
|
||||
.SecurityFilterChain
|
||||
[[servlet-securityfilterchain-figure]]
|
||||
[.invert-dark]
|
||||
image::{figures}/securityfilterchain.png[]
|
||||
|
||||
The <<servlet-security-filters,Security Filters>> in `SecurityFilterChain` are typically Beans, but they are registered with `FilterChainProxy` instead of <<servlet-delegatingfilterproxy>>.
|
||||
@@ -145,6 +149,7 @@ The following image shows multiple `SecurityFilterChain` instances:
|
||||
|
||||
.Multiple SecurityFilterChain
|
||||
[[servlet-multi-securityfilterchain-figure]]
|
||||
[.invert-dark]
|
||||
image::{figures}/multi-securityfilterchain.png[]
|
||||
|
||||
In the <<servlet-multi-securityfilterchain-figure>> figure, `FilterChainProxy` decides which `SecurityFilterChain` should be used.
|
||||
@@ -567,6 +572,7 @@ The javadoc:org.springframework.security.web.access.ExceptionTranslationFilter[]
|
||||
|
||||
The following image shows the relationship of `ExceptionTranslationFilter` to other components:
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/exceptiontranslationfilter.png[]
|
||||
|
||||
|
||||
|
||||
@@ -22,6 +22,7 @@ This also gives a good idea of the high level flow of authentication and how pie
|
||||
At the heart of Spring Security's authentication model is the `SecurityContextHolder`.
|
||||
It contains the <<servlet-authentication-securitycontext>>.
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/securitycontextholder.png[]
|
||||
|
||||
The `SecurityContextHolder` is where Spring Security stores the details of who is xref:features/authentication/index.adoc#authentication[authenticated].
|
||||
@@ -175,6 +176,7 @@ javadoc:org.springframework.security.authentication.ProviderManager[] is the mos
|
||||
Each `AuthenticationProvider` has an opportunity to indicate that authentication should be successful, fail, or indicate it cannot make a decision and allow a downstream `AuthenticationProvider` to decide.
|
||||
If none of the configured `AuthenticationProvider` instances can authenticate, authentication fails with a `ProviderNotFoundException`, which is a special `AuthenticationException` that indicates that the `ProviderManager` was not configured to support the type of `Authentication` that was passed into it.
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/providermanager.png[]
|
||||
|
||||
In practice each `AuthenticationProvider` knows how to perform a specific type of authentication.
|
||||
@@ -184,11 +186,13 @@ This lets each `AuthenticationProvider` do a very specific type of authenticatio
|
||||
`ProviderManager` also allows configuring an optional parent `AuthenticationManager`, which is consulted in the event that no `AuthenticationProvider` can perform authentication.
|
||||
The parent can be any type of `AuthenticationManager`, but it is often an instance of `ProviderManager`.
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/providermanager-parent.png[]
|
||||
|
||||
In fact, multiple `ProviderManager` instances might share the same parent `AuthenticationManager`.
|
||||
This is somewhat common in scenarios where there are multiple xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] instances that have some authentication in common (the shared parent `AuthenticationManager`), but also different authentication mechanisms (the different `ProviderManager` instances).
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/providermanagers-parent.png[]
|
||||
|
||||
[[servlet-authentication-providermanager-erasing-credentials]]
|
||||
@@ -240,6 +244,7 @@ Before the credentials can be authenticated, Spring Security typically requests
|
||||
|
||||
Next, the `AbstractAuthenticationProcessingFilter` can authenticate any authentication requests that are submitted to it.
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/abstractauthenticationprocessingfilter.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] When the user submits their credentials, the `AbstractAuthenticationProcessingFilter` creates an <<servlet-authentication-authentication,`Authentication`>> from the `HttpServletRequest` to be authenticated.
|
||||
|
||||
@@ -9,6 +9,7 @@ This section describes how HTTP Basic Authentication works within Spring Securit
|
||||
First, we see the https://tools.ietf.org/html/rfc7235#section-4.1[WWW-Authenticate] header is sent back to an unauthenticated client:
|
||||
|
||||
.Sending WWW-Authenticate Header
|
||||
[.invert-dark]
|
||||
image::{figures}/basicauthenticationentrypoint.png[]
|
||||
|
||||
The preceding figure builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
@@ -26,6 +27,7 @@ The following image shows the flow for the username and password being processed
|
||||
|
||||
[[servlet-authentication-basicauthenticationfilter]]
|
||||
.Authenticating Username and Password
|
||||
[.invert-dark]
|
||||
image::{figures}/basicauthenticationfilter.png[]
|
||||
|
||||
The preceding figure builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
|
||||
+1
@@ -8,6 +8,7 @@ This section examines how `DaoAuthenticationProvider` works within Spring Securi
|
||||
The following figure explains the workings of the xref:servlet/authentication/architecture.adoc#servlet-authentication-authenticationmanager[`AuthenticationManager`] in figures from the xref:servlet/authentication/passwords/index.adoc#servlet-authentication-unpwd-input[Reading the Username & Password] section.
|
||||
|
||||
.`DaoAuthenticationProvider` Usage
|
||||
[.invert-dark]
|
||||
image::{figures}/daoauthenticationprovider.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] The authentication `Filter` from the xref:servlet/authentication/passwords/index.adoc#servlet-authentication-unpwd-input[Reading the Username & Password] section passes a `UsernamePasswordAuthenticationToken` to the `AuthenticationManager`, which is implemented by xref:servlet/authentication/architecture.adoc#servlet-authentication-providermanager[`ProviderManager`].
|
||||
|
||||
@@ -10,6 +10,7 @@ This section examines how form-based login works within Spring Security.
|
||||
First, we see how the user is redirected to the login form:
|
||||
|
||||
.Redirecting to the Login Page
|
||||
[.invert-dark]
|
||||
image::{figures}/loginurlauthenticationentrypoint.png[]
|
||||
|
||||
The preceding figure builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
@@ -30,6 +31,7 @@ When the username and password are submitted, the `UsernamePasswordAuthenticatio
|
||||
The `UsernamePasswordAuthenticationFilter` extends xref:servlet/authentication/architecture.adoc#servlet-authentication-abstractprocessingfilter[AbstractAuthenticationProcessingFilter], so the following diagram should look pretty similar:
|
||||
|
||||
.Authenticating Username and Password
|
||||
[.invert-dark]
|
||||
image::{figures}/usernamepasswordauthenticationfilter.png[]
|
||||
|
||||
The figure builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
|
||||
@@ -191,6 +191,7 @@ In Spring Security 6, the example shown above is the default configuration.
|
||||
|
||||
The javadoc:org.springframework.security.web.context.SecurityContextPersistenceFilter[] is responsible for persisting the `SecurityContext` between requests using the xref::servlet/authentication/persistence.adoc#securitycontextrepository[`SecurityContextRepository`].
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/securitycontextpersistencefilter.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] Before running the rest of the application, `SecurityContextPersistenceFilter` loads the `SecurityContext` from the `SecurityContextRepository` and sets it on the `SecurityContextHolder`.
|
||||
@@ -213,6 +214,7 @@ To avoid these problems, the `SecurityContextPersistenceFilter` wraps both the `
|
||||
|
||||
The javadoc:org.springframework.security.web.context.SecurityContextHolderFilter[] is responsible for loading the `SecurityContext` between requests using the xref::servlet/authentication/persistence.adoc#securitycontextrepository[`SecurityContextRepository`].
|
||||
|
||||
[.invert-dark]
|
||||
image::{figures}/securitycontextholderfilter.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] Before running the rest of the application, `SecurityContextHolderFilter` loads the `SecurityContext` from the `SecurityContextRepository` and sets it on the `SecurityContextHolder`.
|
||||
|
||||
@@ -126,6 +126,7 @@ For method security, you can use `AuthorizationManagerBeforeMethodInterceptor` a
|
||||
|
||||
[[authz-authorization-manager-implementations]]
|
||||
.Authorization Manager Implementations
|
||||
[.invert-dark]
|
||||
image::{figures}/authorizationhierarchy.png[]
|
||||
|
||||
Using this approach, a composition of `AuthorizationManager` implementations can be polled on an authorization decision.
|
||||
@@ -342,6 +343,7 @@ The following image shows the `AccessDecisionManager` interface:
|
||||
|
||||
[[authz-access-voting]]
|
||||
.Voting Decision Manager
|
||||
[.invert-dark]
|
||||
image::{figures}/access-decision-voting.png[]
|
||||
|
||||
By using this approach, a series of `AccessDecisionVoter` implementations are polled on an authorization decision.
|
||||
@@ -402,6 +404,7 @@ For example, on the Spring web site, you can find a https://spring.io/blog/2009/
|
||||
|
||||
[[authz-after-invocation]]
|
||||
.After Invocation Implementation
|
||||
[.invert-dark]
|
||||
image::{figures}/after-invocation.png[]
|
||||
|
||||
Like many other parts of Spring Security, `AfterInvocationManager` has a single concrete implementation, `AfterInvocationProviderManager`, which polls a list of ``AfterInvocationProvider``s.
|
||||
|
||||
@@ -65,6 +65,7 @@ In many cases, your authorization rules will be more sophisticated than that, so
|
||||
This section builds on xref:servlet/architecture.adoc#servlet-architecture[Servlet Architecture and Implementation] by digging deeper into how xref:servlet/authorization/index.adoc#servlet-authorization[authorization] works at the request level in Servlet-based applications.
|
||||
|
||||
.Authorize HttpServletRequest
|
||||
[.invert-dark]
|
||||
image::{figures}/authorizationfilter.png[]
|
||||
|
||||
* image:{icondir}/number_1.png[] First, the `AuthorizationFilter` constructs a `Supplier` that retrieves an xref:servlet/authentication/architecture.adoc#servlet-authentication-authentication[Authentication] from the xref:servlet/authentication/architecture.adoc#servlet-authentication-securitycontextholder[SecurityContextHolder].
|
||||
|
||||
@@ -1528,6 +1528,7 @@ We expose `MethodSecurityExpressionHandler` using a `static` method to ensure th
|
||||
|
||||
You can also <<subclass-defaultmethodsecurityexpressionhandler,subclass `DefaultMessageSecurityExpressionHandler`>> to add your own custom authorization expressions beyond the defaults.
|
||||
|
||||
[[pre-post-authorize-aot]]
|
||||
=== Working with AOT
|
||||
|
||||
Spring Security will scan all beans in the application context for methods that use `@PreAuthorize` or `@PostAuthorize`.
|
||||
@@ -2462,6 +2463,7 @@ And if they do have that authority, they'll see:
|
||||
You can also add the Spring Boot property `spring.jackson.default-property-inclusion=non_null` to exclude the null value from serialization, if you also don't want to reveal the JSON key to an unauthorized user.
|
||||
====
|
||||
|
||||
[[authorize-return-object-aot]]
|
||||
=== Working with AOT
|
||||
|
||||
Spring Security will scan all beans in the application context for methods that use `@AuthorizeReturnObject`.
|
||||
|
||||
@@ -21,6 +21,7 @@ Now we can consider how Bearer Token Authentication works within Spring Security
|
||||
First, we see that, as with xref:servlet/authentication/passwords/basic.adoc#servlet-authentication-basic[Basic Authentication], the https://tools.ietf.org/html/rfc7235#section-4.1[WWW-Authenticate] header is sent back to an unauthenticated client:
|
||||
|
||||
.Sending WWW-Authenticate Header
|
||||
[.invert-dark]
|
||||
image::{figures}/bearerauthenticationentrypoint.png[]
|
||||
|
||||
The figure above builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
@@ -38,6 +39,7 @@ The following image shows the flow for the bearer token being processed:
|
||||
|
||||
[[oauth2resourceserver-authentication-bearertokenauthenticationfilter]]
|
||||
.Authenticating Bearer Token
|
||||
[.invert-dark]
|
||||
image::{figures}/bearertokenauthenticationfilter.png[]
|
||||
|
||||
The figure builds off our xref:servlet/architecture.adoc#servlet-securityfilterchain[`SecurityFilterChain`] diagram.
|
||||
|
||||
@@ -92,6 +92,7 @@ Let's take a look at how `JwtAuthenticationProvider` works within Spring Securit
|
||||
The figure explains details of how the xref:servlet/authentication/architecture.adoc#servlet-authentication-authenticationmanager[`AuthenticationManager`] in figures from xref:servlet/oauth2/resource-server/index.adoc#oauth2resourceserver-authentication-bearertokenauthenticationfilter[Reading the Bearer Token] works.
|
||||
|
||||
.`JwtAuthenticationProvider` Usage
|
||||
[.invert-dark]
|
||||
image::{figures}/jwtauthenticationprovider.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] The authentication `Filter` from xref:servlet/oauth2/resource-server/index.adoc#oauth2resourceserver-authentication-bearertokenauthenticationfilter[Reading the Bearer Token] passes a `BearerTokenAuthenticationToken` to the `AuthenticationManager` which is implemented by xref:servlet/authentication/architecture.adoc#servlet-authentication-providermanager[`ProviderManager`].
|
||||
|
||||
@@ -88,6 +88,7 @@ Let's take a look at how `OpaqueTokenAuthenticationProvider` works within Spring
|
||||
The figure explains details of how the xref:servlet/authentication/architecture.adoc#servlet-authentication-authenticationmanager[`AuthenticationManager`] in figures from xref:servlet/oauth2/resource-server/index.adoc#oauth2resourceserver-authentication-bearertokenauthenticationfilter[Reading the Bearer Token] works.
|
||||
|
||||
.`OpaqueTokenAuthenticationProvider` Usage
|
||||
[.invert-dark]
|
||||
image::{figures}/opaquetokenauthenticationprovider.png[]
|
||||
|
||||
image:{icondir}/number_1.png[] The authentication `Filter` from xref:servlet/oauth2/resource-server/index.adoc#oauth2resourceserver-authentication-bearertokenauthenticationfilter[Reading the Bearer Token] passes a `BearerTokenAuthenticationToken` to the `AuthenticationManager` which is implemented by xref:servlet/authentication/architecture.adoc#servlet-authentication-providermanager[`ProviderManager`].
|
||||
|
||||
@@ -7,6 +7,7 @@ First, we see that, like <<oauth2login, OAuth 2.0 Login>>, Spring Security takes
|
||||
It does this through a series of redirects:
|
||||
|
||||
.Redirecting to Asserting Party Authentication
|
||||
[.invert-dark]
|
||||
image::{figures}/saml2webssoauthenticationrequestfilter.png[]
|
||||
|
||||
[NOTE]
|
||||
@@ -34,6 +35,7 @@ The following image shows how Spring Security authenticates a `<saml2:Response>`
|
||||
|
||||
[[servlet-saml2login-authentication-saml2webssoauthenticationfilter]]
|
||||
.Authenticating a `<saml2:Response>`
|
||||
[.invert-dark]
|
||||
image::{figures}/saml2webssoauthenticationfilter.png[]
|
||||
|
||||
[NOTE]
|
||||
|
||||
@@ -4,6 +4,89 @@
|
||||
Spring Security 6.4 provides a number of new features.
|
||||
Below are the highlights of the release, or you can view https://github.com/spring-projects/spring-security/releases[the release notes] for a detailed listing of each feature and bug fix.
|
||||
|
||||
== Deprecation Notices
|
||||
|
||||
As we get closer to Spring Security 7, it's important to stay up to date on deprecations.
|
||||
As such, this section points out deprecations in the 6.4 release.
|
||||
|
||||
* *Method Security* - `AuthorizationManager#check` is deprecated in favor of `AuthorizationManager#authorize`.
|
||||
This is primarily to allow the return type to be an interface instead of a concrete class.
|
||||
If you are invoking `AuthorizationManager#check`, please invoke `AuthorizationManager#authorize` instead.
|
||||
+
|
||||
Relatedly, `AuthorizationEventPublisher#publishEvent` that takes an `AuthorizationDecision` is deprecated in favor of a method of the same name that takes an `AuthorizationResult` interface instead.
|
||||
* *Method Security* - `PrePostTemplateDefaults` is deprecated in favor of the more generic `AnnotationTemplateExpressionDefaults` as there is now meta-annotation property support for `@AuthenticationPrincipal` and `@CurrentSecurityContext` as well.
|
||||
If you are constructing a `PrePostTemplateDefaults`, change this out for an `AnnotationTemplateExpressionDefaults`.
|
||||
* *OAuth 2.0* - `NimbusOpaqueTokenIntrospector` has been deprecated in favor of `SpringOpaqueTokenIntrospector` in order to remove Spring Security OAuth 2.0 Resource Server's reliance on the `oidc-oauth2-sdk` package.
|
||||
If you are constructing a `NimbusOpaqueTokenIntrospector`, replace it with ``SpringOpaqueTokenIntrospector``'s constructor
|
||||
* *OAuth 2.0* - `DefaultAuthorizationCodeTokenResponseClient`, `DefaultClientCredentialsTokenResponseClient`, `DefaultJwtBearerTokenResponseClient`, `DefaultPasswordTokenResponseClient`, `DefaultRefreshTokenTokenResponseClient`, and `DefaultTokenExchangeTokenResponseClient` are deprecated in favor of their `RestClient` equivalents.
|
||||
+
|
||||
Relatedly,`JwtBearerGrantRequestEntityConverter`, `OAuth2AuthorizationCodeGrantRequestEntityConverter`, `OAuth2ClientCredentialsGrantRequestEntityConverter`, `OAuth2PasswordGrantRequestEntityConverter`, `OAuth2RefreshTokenGrantRequestEntityConverter` are deprecated in favor of providing an instance of `DefaultOAuth2TokenRequestParametersConverter` to one of the above token response clients
|
||||
+
|
||||
For example, if you have the following arrangement:
|
||||
+
|
||||
[source,java]
|
||||
----
|
||||
private static class MyCustomConverter
|
||||
extends AbstractOAuth2AuthorizationGrantRequestEntityConverter<OAuth2AuthorizationCodeGrantRequest> {
|
||||
@Override
|
||||
protected MultiValueMap<String, String> createParameters
|
||||
(OAuth2AuthorizationCodeGrantRequest request) {
|
||||
MultiValueMap<String, String> parameters = super.createParameters(request);
|
||||
parameters.add("custom", "value");
|
||||
return parameters;
|
||||
}
|
||||
}
|
||||
|
||||
@Bean
|
||||
OAuth2AccessTokenResponseClient authorizationCode() {
|
||||
DefaultAuthorizationCodeTokenResponseClient client =
|
||||
new DefaultAuthorizationCodeTokenResponseClient();
|
||||
Converter<AuthorizationCodeGrantRequest, RequestEntity<?>> entityConverter =
|
||||
new OAuth2AuthorizationCodeGrantRequestEntityConverter();
|
||||
entityConverter.setParametersConverter(new MyCustomConverter());
|
||||
client.setRequestEntityConverter(entityConverter);
|
||||
return client;
|
||||
}
|
||||
----
|
||||
+
|
||||
This configuration is deprecated since it uses `DefaultAuthorizationCodeTokenResponseClient` and `OAuth2AuthorizationCodeGrantRequestEntityConverter`.
|
||||
The recommended configuration is now:
|
||||
+
|
||||
[source,java]
|
||||
----
|
||||
private static class MyCustomConverter implements Converter<OAuth2AuthorizationCodeGrantRequest, Map<String, String>> {
|
||||
@Override
|
||||
public MultiValueMap<String, String> convert(OAuth2AuthorizeCodeGrantRequest request) {
|
||||
MultiValueMap<String, String> parameters = OAuth2AuthorizationCodeGrantRequest.defaultParameters(request);
|
||||
parameters.add("custom", "value");
|
||||
return parameters;
|
||||
}
|
||||
}
|
||||
|
||||
@Bean
|
||||
OAuth2AccessTokenResponseClient authorizationCode() {
|
||||
RestClientAuthorizationCodeTokenResponseClient client =
|
||||
new RestClientAuthorizationCodeTokenResponseClient();
|
||||
client.setParametersConverter(new MyCustomConverter());
|
||||
return client;
|
||||
}
|
||||
----
|
||||
|
||||
|
||||
* *SAML 2.0* - Unversioned OpenSAML implementations of Spring Security SAML 2.0 Service Provider's interfaces have been deprecated in favor of versioned ones.
|
||||
For example, `OpenSamlAuthenticationTokenConverter` is now replaced by `OpenSaml4AuthenticationTokenConverter` and `OpenSaml5AuthenticationTokenConverter`.
|
||||
If you are constructing one of these deprecated versions, please replace it with the one that corresponds to the OpenSAML version you are using.
|
||||
* *SAML 2.0* - Methods surrounding `AssertingPartyDetails` are deprecated in favor of equivalent methods that use the `AssertingPartyMetadata` interface.
|
||||
* *LDAP* - Usages of `DistinguishedName` are now deprecated in order to align with Spring LDAP's deprecations
|
||||
|
||||
== One-Time Token Login
|
||||
|
||||
* Spring Security now xref:servlet/authentication/onetimetoken.adoc[supports One-Time Token Login] via the `oneTimeTokenLogin()` DSL, including xref:servlet/authentication/onetimetoken.adoc#customize-generate-consume-token[JDBC support].
|
||||
|
||||
== Passkeys
|
||||
|
||||
Spring Security now has xref:servlet/authentication/passkeys.adoc[Passkeys] support.
|
||||
|
||||
== Method Security
|
||||
|
||||
* All xref:servlet/authorization/method-security.adoc#meta-annotations[method security annotations] now support {spring-framework-api-url}org/springframework/core/annotation/AliasFor.html[Framework's `@AliasFor`]
|
||||
@@ -48,10 +131,14 @@ fun method(@CurrentUsername("username") val username: String): String {
|
||||
======
|
||||
* https://github.com/spring-projects/spring-security/issues/13490[Several] https://github.com/spring-projects/spring-security/issues/13234[improvements] https://github.com/spring-projects/spring-security/issues/15097[were made] to align Security's annotation search with ``AbstractFallbackMethodSecurityMetadataSource``'s algorithm.
|
||||
This aids in migration from earlier versions of Spring Security.
|
||||
* Native applications can now xref:servlet/authorization/method-security.adoc#authorize-return-object-aot[use `@AuthorizeReturnObject`]
|
||||
* Native applications can now xref:servlet/authorization/method-security.adoc#pre-post-authorize-aot[reference beans in `@PreAuthorize` and `@PostAuthorize`]
|
||||
* `SecurityAnnotationScanners` offers https://github.com/spring-projects/spring-security/issues/15700[a convenient API] for scanning for Security annotations and for adding Security's selection and templating features to custom annotations
|
||||
|
||||
== OAuth 2.0
|
||||
|
||||
* `oauth2Login()` now accepts https://github.com/spring-projects/spring-security/pull/15237[`OAuth2AuthorizationRequestResolver` as a `@Bean`]
|
||||
* `ClientRegistrations` now supports externally obtained configuration
|
||||
* Added `loginPage()` to DSL in reactive `oauth2Login()`
|
||||
* OIDC Back-Channel support now accepts https://github.com/spring-projects/spring-security/issues/15003[logout tokens of type `logout+jwt`]
|
||||
* `RestClient` can now be xref:servlet/oauth2/index.adoc#oauth2-client-access-protected-resources[configured] with `OAuth2ClientHttpRequestInterceptor` to xref:servlet/oauth2/index.adoc#oauth2-client-accessing-protected-resources-example[make protected resources requests]
|
||||
@@ -131,7 +218,7 @@ class SecurityConfig {
|
||||
}
|
||||
----
|
||||
======
|
||||
* Deprecated `Default*` implementations of `OAuth2AccessTokenResponseClient`
|
||||
* Token Exchange now https://github.com/spring-projects/spring-security/issues/15534[supports refresh tokens]
|
||||
|
||||
== SAML 2.0
|
||||
|
||||
@@ -197,15 +284,15 @@ This implementation also supports the validation of a metadata's signature.
|
||||
* You can now sign https://github.com/spring-projects/spring-security/pull/14916[relying party metadata]
|
||||
* `RelyingPartyRegistrationRepository` results can now be javadoc:org.springframework.security.saml2.provider.service.registration.CachingRelyingPartyRegistrationRepository[cached].
|
||||
This is helpful if you want to defer the loading of the registration values til after application startup.
|
||||
It is also helpful if you want to control when metadata gets refreshed.
|
||||
It is also helpful if you want to control when metadata gets refreshed via Spring Cache.
|
||||
* To align with the SAML 2.0 standard, the metadata endpoint now https://github.com/spring-projects/spring-security/issues/15147[uses the `application/samlmetadata+xml` MIME type]
|
||||
|
||||
== Web
|
||||
|
||||
* CSRF BREACH tokens are now https://github.com/spring-projects/spring-security/issues/15187[more consistent]
|
||||
* The Remember Me cookie now is https://github.com/spring-projects/spring-security/pull/15203[more customizable]
|
||||
* Security Filter Chain is now improved.
|
||||
Specifically, the following arrangement is invalid since an any request filter chain comes before all other filter chains:
|
||||
* Security Filter Chain finds more invalid configurations.
|
||||
For example, a filter chain declared after an any-request filter chain is invalid since it will never be invoked:
|
||||
+
|
||||
[tabs]
|
||||
======
|
||||
@@ -217,6 +304,7 @@ Java::
|
||||
@Order(0)
|
||||
SecurityFilterChain api(HttpSecurity http) throws Exception {
|
||||
http
|
||||
// implicit securityMatcher("/**")
|
||||
.authorizeHttpRequests(...)
|
||||
.httpBasic(...)
|
||||
|
||||
@@ -264,14 +352,36 @@ fun app(val http: HttpSecurity): SecurityFilterChain {
|
||||
----
|
||||
======
|
||||
You can read more https://github.com/spring-projects/spring-security/issues/15220[in the related ticket].
|
||||
* `ServerHttpSecurity` now https://github.com/spring-projects/spring-security/issues/15974[picks up `ServerWebExchangeFirewall` as a `@Bean`]
|
||||
|
||||
== One-Time Token Login
|
||||
== Observability
|
||||
|
||||
Spring Security now xref:servlet/authentication/onetimetoken.adoc[supports One-Time Token Login] via the `oneTimeTokenLogin()` DSL.
|
||||
Observability now supports xref:servlet/integrations/observability.adoc#observability-tracing-disable[toggling authorization, authentication, and request observations separately]
|
||||
For example, to turn off filter chain observations, you can publish a `@Bean` like this one:
|
||||
[tabs]
|
||||
======
|
||||
Java::
|
||||
+
|
||||
[source,java,role="primary"]
|
||||
----
|
||||
@Bean
|
||||
SecurityObservationSettings allSpringSecurityObservations() {
|
||||
return SecurityObservationSettings.withDefaults()
|
||||
.shouldObserveFilterChains(false).build();
|
||||
}
|
||||
----
|
||||
|
||||
== Passkeys
|
||||
|
||||
Spring Security now has xref:servlet/authentication/passkeys.adoc[Passkeys] support.
|
||||
Kotlin::
|
||||
+
|
||||
[source,kotlin,role="secondary"]
|
||||
----
|
||||
@Bean
|
||||
fun allSpringSecurityObservations(): SecurityObservationSettings {
|
||||
return SecurityObservationSettings.builder()
|
||||
.shouldObserveFilterChains(false).build()
|
||||
}
|
||||
----
|
||||
======
|
||||
|
||||
== Kotlin
|
||||
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@
|
||||
# limitations under the License.
|
||||
#
|
||||
springBootVersion=3.3.3
|
||||
version=6.4.0
|
||||
version=6.4.1
|
||||
samplesBranch=main
|
||||
org.gradle.jvmargs=-Xmx3g -XX:+HeapDumpOnOutOfMemoryError
|
||||
org.gradle.parallel=true
|
||||
|
||||
Reference in New Issue
Block a user