| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110 | 
							- = SAML 2.0 Migrations
 
- == Expect `<saml2:LogoutResponse>` When `<saml2:LogoutRequest>` Validation Fails
 
- SAML identity providers expect service providers to return an error `<saml2:LogoutResponse>` if it fails to process the `<saml2:LogoutRequest>`.
 
- Past versions of Spring Security returned a 401 in some cases, breaking the chain of logout requests and responses from each relying party.
 
- In Spring Security 7, this behavior is repaired, and you need do nothing.
 
- However, if this gives you trouble, you can revert back to the old behavior by publishing a `Saml2LogoutRequestResolver` that returns `null` when an error `<saml2:LogoutRequest>` is needed.
 
- You can create a delegate like this one:
 
- [tabs]
 
- ======
 
- Java::
 
- +
 
- [source,java,role="primary"]
 
- ----
 
- @Bean
 
- Saml2LogoutResponseResolver logoutResponseResolver(RelyingPartyRegistrationRepository registrations) {
 
-     OpenSaml5LogoutResponseResolver delegate = new OpenSaml5LogoutResponseResolver(registrations);
 
-     return new Saml2LogoutResponseResolver() {
 
-         @Override
 
-         public void resolve(HttpServletRequest request, Authentication authentication) {
 
-             delegate.resolve(request, authentication);
 
-         }
 
-         @Override
 
-         public void resolve(HttpServletRequest request, Authentication authentication, Saml2AuthenticationException error) {
 
-             return null;
 
-         }
 
-     };
 
- }
 
- ----
 
- Kotlin::
 
- +
 
- [source,kotlin,role="secondary"]
 
- ----
 
- @Bean
 
- fun logoutResponseResolver(registrations: RelyingPartyRegistrationRepository?): Saml2LogoutResponseResolver {
 
-     val delegate = OpenSaml5LogoutResponseResolver(registrations)
 
-     return object : Saml2LogoutResponseResolver() {
 
-         override fun resolve(request: HttpServletRequest?, authentication: Authentication?) {
 
-             delegate.resolve(request, authentication)
 
-         }
 
-         override fun resolve(request: HttpServletRequest?, authentication: Authentication?, error: Saml2AuthenticationException?) {
 
-             return null
 
-         }
 
-     }
 
- }
 
- ----
 
- ======
 
- == Favor `Saml2ResponseAuthenticationAccessor` over `Saml2AuthenticatedPrincipal`
 
- Spring Security 7 separates `<saml2:Assertion>` details from the principal.
 
- This allows Spring Security to retrieve needed assertion details to perform Single Logout.
 
- This deprecates `Saml2AuthenticatedPrincipal`.
 
- You no longer need to implement it to use `Saml2Authentication`.
 
- Instead, the credential implements `Saml2ResponseAssertionAccessor`, which Spring Security 7 favors when determining the appropriate action based on the authentication.
 
- This change is made automatically for you when using the defaults.
 
- If this causes you trouble when upgrading, you can publish a custom `ResponseAuhenticationConverter` to return a `Saml2Authentication` instead of returning a `Saml2AssertionAuthentication` like so:
 
- [tabs]
 
- ======
 
- Java::
 
- +
 
- [source,java,role="primary"]
 
- ----
 
- @Bean
 
- OpenSaml5AuthenticationProvider authenticationProvider() {
 
- 	OpenSaml5AuthenticationProvider authenticationProvider =
 
- 		new OpenSaml5AuthenticationProvider();
 
- 	ResponseAuthenticationConverter defaults = new ResponseAuthenticationConverter();
 
- 	authenticationProvider.setResponseAuthenticationConverter(
 
- 		defaults.andThen((authentication) -> new Saml2Authentication(
 
- 			authentication.getPrincipal(),
 
- 			authentication.getSaml2Response(),
 
- 			authentication.getAuthorities())));
 
- 	return authenticationProvider;
 
- }
 
- ----
 
- Kotlin::
 
- +
 
- [source,kotlin,role="secondary"]
 
- ----
 
- @Bean
 
- fun authenticationProvider(): OpenSaml5AuthenticationProvider {
 
- 	val authenticationProvider = OpenSaml5AuthenticationProvider()
 
- 	val defaults = ResponseAuthenticationConverter()
 
- 	authenticationProvider.setResponseAuthenticationConverter(
 
- 		defaults.andThen { authentication ->
 
- 			Saml2Authentication(authentication.getPrincipal(),
 
- 				authentication.getSaml2Response(),
 
- 				authentication.getAuthorities())
 
- 		})
 
- 	return authenticationProvider
 
- }
 
- ----
 
- ======
 
- If you are constructing a `Saml2Authentication` instance yourself, consider changing to `Saml2AssertionAuthentication` to get the same benefit as the current default.
 
 
  |