Description
Summary
I'm currently update to Spring Security 5.2.1. and start to use the integrated SAML 2 implementation.
During the integration I noticed that my identity provider (Keycloak) does not accept the signed AuthNRequest.
The reason is that SAML 2 expects different signature for different bindings (POST or Redirect) - at least that's how I understand it.
- If a POST binding is used the signature is embedded in the XML.
- If a Redirect binding is used the signature is part of the URL query parameters.
(e.g. https://idp/?SAMLRequest=...&RelayState=...&SigAlg=...&Signature=...)
I checked the Spring Security SAML Extension online demo (https://saml-federation.appspot.com) and here it works as expected.
GET Parameters:
SAMLRequest: fZLLbsIwEEV/JfI...
SigAlg: http://www.w3.org/2000/09/xmldsig#rsa-sha1
Signature: LAB/NahduGHr5ew...
and a none signed AuthNRequest
<saml2p:AuthnRequest xmlns:saml2p="urn:oasis:names:tc:SAML:2.0:protocol"
AssertionConsumerServiceURL="https://saml-federation.appspot.com:443/saml/SSO"
Destination="https://idp.ssocircle.com:443/sso/SSORedirect/metaAlias/ssocircle"
[...]
>
<saml2:Issuer xmlns:saml2="urn:oasis:names:tc:SAML:2.0:assertion">saml-federation.appspot.com</saml2:Issuer>
</saml2p:AuthnRequest>
Currently the URL is created while using createSamlRequestRedirectUrl
in Saml2WebSsoAuthenticationRequestFilter
and these parameters aren't set.
private String createSamlRequestRedirectUrl(HttpServletRequest request, RelyingPartyRegistration relyingParty) {
[...]
String redirect = UriComponentsBuilder
.fromUriString(relyingParty.getIdpWebSsoUrl())
.queryParam("SAMLRequest", UriUtils.encode(encoded, StandardCharsets.ISO_8859_1))
.queryParam("RelayState", UriUtils.encode(relayState, StandardCharsets.ISO_8859_1))
.build(true)
.toUriString();
return redirect;
}
Expected Behavior
Using HTTP-Redirect binding SigAlg and Signature parameters are added to SAMLRequest Url and AuthNRequest XML is not signed.
Version
5.2.1.RELEASE