Change to Migrating to 6.2

Issue gh-13552
This commit is contained in:
Marcus Da Coregio 2023-07-19 10:30:23 -03:00
parent 34628594e8
commit 4c77a550ae
8 changed files with 11 additions and 532 deletions

View File

@ -4,13 +4,7 @@
* xref:whats-new.adoc[What's New]
* xref:migration-7/index.adoc[Preparing for 7.0]
** xref:migration-7/configuration.adoc[Configuration]
* xref:migration/index.adoc[Migrating to 6.0]
** xref:migration/servlet/index.adoc[Servlet Migrations]
*** xref:migration/servlet/session-management.adoc[Session Management]
*** xref:migration/servlet/exploits.adoc[Exploit Protection]
*** xref:migration/servlet/authentication.adoc[Authentication]
*** xref:migration/servlet/authorization.adoc[Authorization]
** xref:migration/reactive.adoc[Reactive Migrations]
* xref:migration/index.adoc[Migrating to 6.2]
* xref:getting-spring-security.adoc[Getting Spring Security]
* xref:features/index.adoc[Features]
** xref:features/authentication/index.adoc[Authentication]

View File

@ -1,31 +1,17 @@
[[migration]]
= Migrating to 6.0
= Migrating to 6.2
:spring-security-reference-base-url: https://docs.spring.io/spring-security/reference
The Spring Security team has prepared the 5.8 release to simplify upgrading to Spring Security 6.0.
Use 5.8 and
ifdef::spring-security-version[]
{spring-security-reference-base-url}/5.8/migration/index.html[its preparation steps]
endif::[]
ifndef::spring-security-version[]
its preparation steps
endif::[]
to simplify updating to 6.0.
This guide provides instructions for migrating from Spring Security 6.1 to Spring Security 6.2.
After updating to 5.8, follow this guide to perform any remaining migration or cleanup steps.
== Update to Spring Security 6.2
And recall that if you run into trouble, the preparation guide includes opt-out steps to revert to 5.x behaviors.
When updating to a new minor version, it is important that you are already using the latest patch release of the previous minor version.
For example, if you are upgrading to Spring Security 6.2, you should already be using the latest patch release of Spring Security 6.1.
This makes it easier to identify any changes that may have been introduced in the new minor version.
== Update to Spring Security 6.0
Therefore, the first step is to ensure you are on the latest patch release of Spring Boot 3.1.
Next, you should ensure you are on the latest patch release of Spring Security 6.1.
Typically, the latest patch release of Spring Boot uses the latest patch release of Spring Security.
The first step is to ensure you are the latest patch release of Spring Boot 3.0.
Next, you should ensure you are on the latest patch release of Spring Security 6.0.
For directions, on how to update to Spring Security 6.0 visit the xref:getting-spring-security.adoc[] section of the reference guide.
== Update Package Names
Now that you are updated, you need to change your `javax` imports to `jakarta` imports.
== Perform Application-Specific Steps
Next, there are steps you need to perform based on whether it is a xref:migration/servlet/index.adoc[Servlet] or xref:migration/reactive.adoc[Reactive] application.
With those two steps complete, you can now update to Spring Security 6.2.

View File

@ -1,100 +0,0 @@
= Reactive
If you have already performed the xref:migration/index.adoc[initial migration steps] for your Reactive application, you're now ready to perform steps specific to Reactive applications.
== Use `AuthorizationManager` for Method Security
In 6.0, `@EnableReactiveMethodSecurity` defaults `useAuthorizationManager` to `true`.
So, to complete migration, {security-api-url}org/springframework/security/config/annotation/method/configuration/EnableReactiveMethodSecurity.html[`@EnableReactiveMethodSecurity`] remove the `useAuthorizationManager` attribute:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
@EnableReactiveMethodSecurity(useAuthorizationManager = true)
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
@EnableReactiveMethodSecurity(useAuthorizationManager = true)
----
======
changes to:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
@EnableReactiveMethodSecurity
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
@EnableReactiveMethodSecurity
----
======
== Propagate ``AuthenticationServiceException``s
{security-api-url}org/springframework/security/web/server/authentication/AuthenticationWebFilter.html[`AuthenticationWebFilter`] propagates {security-api-url}org/springframework/security/authentication/AuthenticationServiceException.html[``AuthenticationServiceException``]s to the {security-api-url}org/springframework/security/web/server/ServerAuthenticationEntryPoint.html[`ServerAuthenticationEntryPoint`].
Because ``AuthenticationServiceException``s represent a server-side error instead of a client-side error, in 6.0, this changes to propagate them to the container.
So, if you opted into this behavior by setting `rethrowAuthenticationServiceException` too `true`, you can now remove it like so:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
AuthenticationFailureHandler bearerFailureHandler = new ServerAuthenticationEntryPointFailureHandler(bearerEntryPoint);
bearerFailureHandler.setRethrowAuthenticationServiceException(true);
AuthenticationFailureHandler basicFailureHandler = new ServerAuthenticationEntryPointFailureHandler(basicEntryPoint);
basicFailureHandler.setRethrowAuthenticationServiceException(true);
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
val bearerFailureHandler: AuthenticationFailureHandler = ServerAuthenticationEntryPointFailureHandler(bearerEntryPoint)
bearerFailureHandler.setRethrowAuthenticationServiceException(true)
val basicFailureHandler: AuthenticationFailureHandler = ServerAuthenticationEntryPointFailureHandler(basicEntryPoint)
basicFailureHandler.setRethrowAuthenticationServiceException(true)
----
======
changes to:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
AuthenticationFailureHandler bearerFailureHandler = new ServerAuthenticationEntryPointFailureHandler(bearerEntryPoint);
AuthenticationFailureHandler basicFailureHandler = new ServerAuthenticationEntryPointFailureHandler(basicEntryPoint);
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
val bearerFailureHandler: AuthenticationFailureHandler = ServerAuthenticationEntryPointFailureHandler(bearerEntryPoint)
val basicFailureHandler: AuthenticationFailureHandler = ServerAuthenticationEntryPointFailureHandler(basicEntryPoint)
----
======
[NOTE]
====
If you configured the `ServerAuthenticationFailureHandler` only for the purpose of updating to 6.0, you can remove it completely.
====

View File

@ -1,187 +0,0 @@
= Authentication Migrations
The following steps relate to how to finish migrating authentication support.
== Propagate ``AuthenticationServiceException``s
{security-api-url}org/springframework/security/web/authentication/AuthenticationFilter.html[`AuthenticationFilter`] propagates {security-api-url}org/springframework/security/authentication/AuthenticationServiceException.html[``AuthenticationServiceException``]s to the {security-api-url}org/springframework/security/web/AuthenticationEntryPoint.html[`AuthenticationEntryPoint`].
Because ``AuthenticationServiceException``s represent a server-side error instead of a client-side error, in 6.0, this changes to propagate them to the container.
So, if you opted into this behavior by setting `rethrowAuthenticationServiceException` to `true`, you can now remove it like so:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
AuthenticationFilter authenticationFilter = new AuthenticationFilter(...);
AuthenticationEntryPointFailureHandler handler = new AuthenticationEntryPointFailureHandler(...);
handler.setRethrowAuthenticationServiceException(true);
authenticationFilter.setAuthenticationFailureHandler(handler);
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
val authenticationFilter: AuthenticationFilter = AuthenticationFilter(...)
val handler: AuthenticationEntryPointFailureHandler = AuthenticationEntryPointFailureHandler(...)
handler.setRethrowAuthenticationServiceException(true)
authenticationFilter.setAuthenticationFailureHandler(handler)
----
Xml::
+
[source,xml,role="secondary"]
----
<bean id="authenticationFilter" class="org.springframework.security.web.authentication.AuthenticationFilter">
<!-- ... -->
<property ref="authenticationFailureHandler"/>
</bean>
<bean id="authenticationFailureHandler" class="org.springframework.security.web.authentication.AuthenticationEntryPointFailureHandler">
<property name="rethrowAuthenticationServiceException" value="true"/>
</bean>
----
======
changes to:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
AuthenticationFilter authenticationFilter = new AuthenticationFilter(...);
AuthenticationEntryPointFailureHandler handler = new AuthenticationEntryPointFailureHandler(...);
authenticationFilter.setAuthenticationFailureHandler(handler);
----
Kotlin::
+
[source,kotlin,role="secondary"]
----
val authenticationFilter: AuthenticationFilter = AuthenticationFilter(...)
val handler: AuthenticationEntryPointFailureHandler = AuthenticationEntryPointFailureHandler(...)
authenticationFilter.setAuthenticationFailureHandler(handler)
----
Xml::
+
[source,xml,role="secondary"]
----
<bean id="authenticationFilter" class="org.springframework.security.web.authentication.AuthenticationFilter">
<!-- ... -->
<property ref="authenticationFailureHandler"/>
</bean>
<bean id="authenticationFailureHandler" class="org.springframework.security.web.authentication.AuthenticationEntryPointFailureHandler">
<!-- ... -->
</bean>
----
======
[[servlet-opt-in-sha256-rememberme]]
== Use SHA-256 in Remember Me
In 6.0, the `TokenBasedRememberMeServices` uses SHA-256 to encode and match the token.
To complete the migration, any default values can be removed.
For example, if you opted in to the 6.0 default for `encodingAlgorithm` and `matchingAlgorithm` like so:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
@Configuration
@EnableWebSecurity
public class SecurityConfig {
@Bean
SecurityFilterChain securityFilterChain(HttpSecurity http, RememberMeServices rememberMeServices) throws Exception {
http
// ...
.rememberMe((remember) -> remember
.rememberMeServices(rememberMeServices)
);
return http.build();
}
@Bean
RememberMeServices rememberMeServices(UserDetailsService userDetailsService) {
RememberMeTokenAlgorithm encodingAlgorithm = RememberMeTokenAlgorithm.SHA256;
TokenBasedRememberMeServices rememberMe = new TokenBasedRememberMeServices(myKey, userDetailsService, encodingAlgorithm);
rememberMe.setMatchingAlgorithm(RememberMeTokenAlgorithm.SHA256);
return rememberMe;
}
}
----
XML::
+
[source,xml,role="secondary"]
----
<http>
<remember-me services-ref="rememberMeServices"/>
</http>
<bean id="rememberMeServices" class=
"org.springframework.security.web.authentication.rememberme.TokenBasedRememberMeServices">
<property name="userDetailsService" ref="myUserDetailsService"/>
<property name="key" value="springRocks"/>
<property name="matchingAlgorithm" value="SHA256"/>
<property name="encodingAlgorithm" value="SHA256"/>
</bean>
----
======
then the defaults can be removed:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
@Configuration
@EnableWebSecurity
public class SecurityConfig {
@Bean
SecurityFilterChain securityFilterChain(HttpSecurity http, RememberMeServices rememberMeServices) throws Exception {
http
// ...
.rememberMe((remember) -> remember
.rememberMeServices(rememberMeServices)
);
return http.build();
}
@Bean
RememberMeServices rememberMeServices(UserDetailsService userDetailsService) {
return new TokenBasedRememberMeServices(myKey, userDetailsService);
}
}
----
XML::
+
[source,xml,role="secondary"]
----
<http>
<remember-me services-ref="rememberMeServices"/>
</http>
<bean id="rememberMeServices" class=
"org.springframework.security.web.authentication.rememberme.TokenBasedRememberMeServices">
<property name="userDetailsService" ref="myUserDetailsService"/>
<property name="key" value="springRocks"/>
</bean>
----
======
== Default authorities for oauth2Login()
In Spring Security 5, the default `GrantedAuthority` given to a user that authenticates with an OAuth2 or OpenID Connect 1.0 provider (via `oauth2Login()`) is `ROLE_USER`.
In Spring Security 6, the default authority given to a user authenticating with an OAuth2 provider is `OAUTH2_USER`.
The default authority given to a user authenticating with an OpenID Connect 1.0 provider is `OIDC_USER`.
If you configured the `GrantedAuthoritiesMapper` only for the purpose of updating to 6.0, you can remove it completely.

View File

@ -1,117 +0,0 @@
= Authorization Migrations
The following steps relate to how to finish migrating authorization support.
== Use `AuthorizationManager` for Method Security
There are no further migration steps for this feature.
== Use `AuthorizationManager` for Message Security
In 6.0, `<websocket-message-broker>` defaults `use-authorization-manager` to `true`.
So, to complete migration, remove any `websocket-message-broker@use-authorization-manager=true` attribute.
For example:
[tabs]
======
Xml::
+
[source,xml,role="primary"]
----
<websocket-message-broker use-authorization-manager="true"/>
----
======
changes to:
[tabs]
======
Xml::
+
[source,xml,role="primary"]
----
<websocket-message-broker/>
----
======
There are no further migrations steps for Java or Kotlin for this feature.
== Use `AuthorizationManager` for Request Security
In 6.0, `<http>` defaults `once-per-request` to `false`, `filter-all-dispatcher-types` to `true`, and `use-authorization-manager` to `true`.
Also, {security-api-url}org/springframework/security/config/annotation/web/configurers/AbstractInterceptUrlConfigurer.AbstractInterceptUrlRegistry.html#filterSecurityInterceptorOncePerRequest(boolean)[`authorizeRequests#filterSecurityInterceptorOncePerRequest`] defaults to `false` and xref:servlet/authorization/authorize-http-requests.adoc[`authorizeHttpRequests#filterAllDispatcherTypes`] defaults to `true`.
So, to complete migration, any defaults values can be removed.
For example, if you opted in to the 6.0 default for `filter-all-dispatcher-types` or `authorizeHttpRequests#filterAllDispatcherTypes` like so:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
http
.authorizeHttpRequests((authorize) -> authorize
.filterAllDispatcherTypes(true)
// ...
)
----
Kotlin::
+
[source,java,role="secondary"]
----
http {
authorizeHttpRequests {
filterAllDispatcherTypes = true
// ...
}
}
----
Xml::
+
[source,xml,role="secondary"]
----
<http use-authorization-manager="true" filter-all-dispatcher-types="true"/>
----
======
then the defaults may be removed:
[tabs]
======
Java::
+
[source,java,role="primary"]
----
http
.authorizeHttpRequests((authorize) -> authorize
// ...
)
----
Kotlin::
+
[source,java,role="secondary"]
----
http {
authorizeHttpRequests {
// ...
}
}
----
Xml::
+
[source,xml,role="secondary"]
----
<http/>
----
======
[NOTE]
====
`once-per-request` applies only when `use-authorization-manager="false"` and `filter-all-dispatcher-types` only applies when `use-authorization-manager="true"`
====

View File

@ -1,44 +0,0 @@
= Exploit Protection Migrations
:spring-security-reference-base-url: https://docs.spring.io/spring-security/reference
The 5.8 migration guide contains several steps for
ifdef::spring-security-version[]
{spring-security-reference-base-url}/5.8/migration/servlet/exploits.html[exploit protection migrations] when updating to 6.0.
endif::[]
ifndef::spring-security-version[]
exploit protection migrations when updating to 6.0.
endif::[]
You are encouraged to follow those steps first.
The following steps relate to how to finish migrating exploit protection support.
== Defer Loading CsrfToken
In Spring Security 5.8, the default `CsrfTokenRequestHandler` for making the `CsrfToken` available to the application is `CsrfTokenRequestAttributeHandler`.
The default for the field `csrfRequestAttributeName` is `null`, which causes the CSRF token to be loaded on every request.
In Spring Security 6, `csrfRequestAttributeName` defaults to `_csrf`.
If you configured the following only for the purpose of updating to 6.0, you can now remove it:
requestHandler.setCsrfRequestAttributeName("_csrf");
== Protect against CSRF BREACH
In Spring Security 5.8, the default `CsrfTokenRequestHandler` for making the `CsrfToken` available to the application is `CsrfTokenRequestAttributeHandler`.
`XorCsrfTokenRequestAttributeHandler` was added to allow opting into CSRF BREACH support.
In Spring Security 6, `XorCsrfTokenRequestAttributeHandler` is the default `CsrfTokenRequestHandler` for making the `CsrfToken` available.
If you configured the `XorCsrfTokenRequestAttributeHandler` only for the purpose of updating to 6.0, you can remove it completely.
[NOTE]
====
If you have set the `csrfRequestAttributeName` to `null` in order to opt out of deferred tokens, or if you have configured a `CsrfTokenRequestHandler` for any other reason, you can leave the configuration in place.
====
== CSRF BREACH with WebSocket support
In Spring Security 5.8, the default `ChannelInterceptor` for making the `CsrfToken` available with xref:servlet/integrations/websocket.adoc[WebSocket Security] is `CsrfChannelInterceptor`.
`XorCsrfChannelInterceptor` was added to allow opting into CSRF BREACH support.
In Spring Security 6, `XorCsrfChannelInterceptor` is the default `ChannelInterceptor` for making the `CsrfToken` available.
If you configured the `XorCsrfChannelInterceptor` only for the purpose of updating to 6.0, you can remove it completely.

View File

@ -1,4 +0,0 @@
= Servlet Migrations
:page-section-summary-toc: 1
If you have already performed the xref:migration/index.adoc[initial migration steps] for your Servlet application, you're now ready to perform steps specific to Servlet applications.

View File

@ -1,49 +0,0 @@
= Session Management Migrations
The following steps relate to how to finish migrating session management support.
== Require Explicit Saving of SecurityContextRepository
In Spring Security 5, the default behavior is for the xref:servlet/authentication/architecture.adoc#servlet-authentication-securitycontext[`SecurityContext`] to automatically be saved to the xref:servlet/authentication/persistence.adoc#securitycontextrepository[`SecurityContextRepository`] using the xref:servlet/authentication/persistence.adoc#securitycontextpersistencefilter[`SecurityContextPersistenceFilter`].
Saving must be done just prior to the `HttpServletResponse` being committed and just before `SecurityContextPersistenceFilter`.
Unfortunately, automatic persistence of the `SecurityContext` can surprise users when it is done prior to the request completing (i.e. just prior to committing the `HttpServletResponse`).
It also is complex to keep track of the state to determine if a save is necessary causing unnecessary writes to the `SecurityContextRepository` (i.e. `HttpSession`) at times.
In Spring Security 6, the default behavior is that the xref:servlet/authentication/persistence.adoc#securitycontextholderfilter[`SecurityContextHolderFilter`] will only read the `SecurityContext` from `SecurityContextRepository` and populate it in the `SecurityContextHolder`.
Users now must explicitly save the `SecurityContext` with the `SecurityContextRepository` if they want the `SecurityContext` to persist between requests.
This removes ambiguity and improves performance by only requiring writing to the `SecurityContextRepository` (i.e. `HttpSession`) when it is necessary.
[NOTE]
====
Saving the context is also needed when clearing it out, for example during logout. Refer to this section to xref:servlet/authentication/session-management.adoc#properly-clearing-authentication[know more about that].
====
If you are explicitly opting into Spring Security 6's new defaults, the following configuration can be removed to accept the Spring Security 6 defaults.
include::partial$servlet/architecture/security-context-explicit.adoc[]
== Multiple SecurityContextRepository
In Spring Security 5, the default xref:servlet/authentication/persistence.adoc#securitycontextrepository[`SecurityContextRepository`] was `HttpSessionSecurityContextRepository`.
In Spring Security 6, the default `SecurityContextRepository` is `DelegatingSecurityContextRepository`.
If you configured the `SecurityContextRepository` only for the purpose of updating to 6.0, you can remove it completely.
== Deprecation in SecurityContextRepository
There are no further migration steps for this deprecation.
[[requestcache-query-optimization]]
== Optimize Querying of `RequestCache`
In Spring Security 5, the default behavior is to query the xref:servlet/architecture.adoc#savedrequests[saved request] on every request.
This means that in a typical setup, that in order to use the xref:servlet/architecture.adoc#requestcache[`RequestCache`] the `HttpSession` is queried on every request.
In Spring Security 6, the default is that `RequestCache` will only be queried for a cached request if the HTTP parameter `continue` is defined.
This allows Spring Security to avoid unnecessarily reading the `HttpSession` with the `RequestCache`.
In Spring Security 5 the default is to use `HttpSessionRequestCache` which will be queried for a cached request on every request.
If you are not overriding the defaults (i.e. using `NullRequestCache`), then the following configuration can be used to explicitly opt into the Spring Security 6 behavior in Spring Security 5.8:
include::partial$servlet/architecture/request-cache-continue.adoc[]