[TEST] Add SAML Redirect Signing test (#34562)
Add a test to verify that we generate correct signatures for our SAML2 Single Logout requests when using the redirect binding.
This commit is contained in:
parent
fe623acf66
commit
59033e0e45
|
@ -12,6 +12,15 @@ import org.opensaml.saml.saml2.core.LogoutRequest;
|
|||
import org.opensaml.saml.saml2.core.NameID;
|
||||
import org.opensaml.security.x509.X509Credential;
|
||||
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.URLDecoder;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.security.InvalidKeyException;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.security.Signature;
|
||||
import java.security.SignatureException;
|
||||
import java.util.Base64;
|
||||
|
||||
import static java.util.Collections.emptySet;
|
||||
import static java.util.Collections.singleton;
|
||||
import static org.hamcrest.Matchers.equalTo;
|
||||
|
@ -67,6 +76,46 @@ public class SamlRedirectTests extends SamlTestCase {
|
|||
"1yHnLOX4Edtz0eDuf2uJjHy9Z%2Fl5ZEapyLQvGraBZdZm6ER59RV%2F8izGKwLg38VL4B1sji%2FPxxgeIb"));
|
||||
}
|
||||
|
||||
public void testLogoutRequestSigning() throws Exception {
|
||||
final X509Credential credential = (X509Credential) buildOpenSamlCredential(readRandomKeyPair()).get(0);
|
||||
X509Credential invalidCredential = (X509Credential) buildOpenSamlCredential(readRandomKeyPair()).get(0);
|
||||
while (invalidCredential.getEntityCertificate().getSerialNumber().equals(credential.getEntityCertificate().getSerialNumber())) {
|
||||
invalidCredential = (X509Credential) buildOpenSamlCredential(readRandomKeyPair()).get(0);
|
||||
}
|
||||
final SigningConfiguration spConfig =
|
||||
new SigningConfiguration(singleton("*"), credential);
|
||||
final SamlRedirect redirect = new SamlRedirect(buildLogoutRequest(LOGOUT_URL + "?"), spConfig);
|
||||
final String url = redirect.getRedirectUrl();
|
||||
final String queryParam = url.split("\\?")[1].split("&Signature")[0];
|
||||
final String params[] = url.split("\\?")[1].split("&");
|
||||
assert (params.length == 3);
|
||||
String sigAlg = parseAndUrlDecodeParameter(params[1]);
|
||||
// We currently only support signing with SHA256withRSA, this test should be updated if we add support for more
|
||||
assertThat(sigAlg, equalTo("http://www.w3.org/2001/04/xmldsig-more#rsa-sha256"));
|
||||
sigAlg = "SHA256withRSA";
|
||||
final String signature = parseAndUrlDecodeParameter(params[2]);
|
||||
assertThat(validateSignature(queryParam, sigAlg, signature, credential), equalTo(true));
|
||||
assertThat(validateSignature(queryParam, sigAlg, signature, invalidCredential), equalTo(false));
|
||||
assertThat(validateSignature(queryParam.substring(0, queryParam.length() - 5), sigAlg, signature, credential), equalTo(false));
|
||||
}
|
||||
|
||||
private String parseAndUrlDecodeParameter(String parameter) throws UnsupportedEncodingException {
|
||||
final String value = parameter.split("=", 2)[1];
|
||||
return URLDecoder.decode(value, "UTF-8");
|
||||
}
|
||||
|
||||
private boolean validateSignature(String queryParam, String sigAlg, String signature, X509Credential credential) {
|
||||
try {
|
||||
Signature sig = Signature.getInstance(sigAlg);
|
||||
sig.initVerify(credential.getPublicKey());
|
||||
sig.update(queryParam.getBytes(StandardCharsets.UTF_8));
|
||||
return sig.verify(Base64.getDecoder().decode(signature));
|
||||
} catch (NoSuchAlgorithmException | InvalidKeyException | SignatureException e) {
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private LogoutRequest buildLogoutRequest(String logoutUrl) {
|
||||
final LogoutRequest logoutRequest = SamlUtils.buildObject(LogoutRequest.class, LogoutRequest.DEFAULT_ELEMENT_NAME);
|
||||
logoutRequest.setDestination(logoutUrl);
|
||||
|
|
Loading…
Reference in New Issue