spring-projects/spring-security · error · Saml2Exception
Saml2Exception wrapping DecryptionException during encrypted
Error message
Saml2Exception wrapping DecryptionException during encrypted subject-confirmation NameID decryption
What it means
OpenSaml5Template.decryptSubject also iterates SubjectConfirmations and decrypts each <saml2:EncryptedID> inside them. A DecryptionException there is wrapped in a Saml2Exception. This means an encrypted NameID embedded in a SubjectConfirmation (common in Holder-of-Key / bearer confirmation) failed to decrypt.
Source
Thrown at saml2/saml2-service-provider/src/opensaml5Main/java/org/springframework/security/saml2/provider/service/registration/OpenSaml5Template.java:603
if (decrypted != null) {
subject.setNameID(decrypted);
}
}
catch (final DecryptionException ex) {
throw new Saml2Exception(ex);
}
}
for (final SubjectConfirmation sc : subject.getSubjectConfirmations()) {
if (sc.getEncryptedID() != null) {
try {
NameID decrypted = (NameID) this.decrypter.decrypt(sc.getEncryptedID());
if (decrypted != null) {
sc.setNameID(decrypted);
}
}
catch (final DecryptionException ex) {
throw new Saml2Exception(ex);
}
}
}
}
}
private void decryptLogoutRequest(LogoutRequest request) {
if (request.getEncryptedID() != null) {
try {
NameID decrypted = (NameID) this.decrypter.decrypt(request.getEncryptedID());
if (decrypted != null) {
request.setNameID(decrypted);
}
}
catch (DecryptionException ex) {
throw new Saml2Exception(ex);
}
}View on GitHub (pinned to 96852e8860)
Solutions
- Register all decryption credentials the IdP may use, including those for SubjectConfirmation EncryptedIDs
- Check the caught DecryptionException and its KeyInfo against each registered certificate
- Confirm key agreement/key-transport algorithms (RSA-OAEP, ECDH-ES) are supported by the JVM
- Sync encryption certificates in both SP and IdP metadata
Example fix
// before c -> c.add(credA) // only one decryption credential // after c -> c.add(credA).add(credB) // all certs the IdP may encrypt to
Defensive patterns
Strategy: try-catch
Validate before calling
for (SubjectConfirmation sc : subject.getSubjectConfirmations()) {
if (sc.getEncryptedID() != null && registration.getDecryptionX509Credentials().isEmpty())
throw new IllegalStateException("Encrypted SubjectConfirmation NameID without credentials");
} Type guard
if (sc.getEncryptedID() == null && sc.getNameID() != null) { /* already plain */ } Try / catch
try {
decryptSubject(subject);
} catch (Saml2Exception ex) {
if (ex.getCause() instanceof DecryptionException)
logger.warn("SubjectConfirmation NameID decryption failed");
throw ex;
} Prevention
- Register every certificate the IdP might encrypt to, not just one
- Check KeyInfo inside each SubjectConfirmation EncryptedID against registered certs
- Coordinate SSO and SLO certificate configs on the IdP side
When it happens
Trigger: decryptAssertion -> decryptSubject when SubjectConfirmation(s) contain EncryptedID elements; decryption credentials don't match or the ciphertext/algorithm is unsupported.
Common situations: IdP encrypts the SubjectConfirmation NameID with a different certificate than the subject NameID; SP only registered one decryption key; proxy/pass-through SSO flows where an intermediary's key was expected.
Related errors
- Saml2Exception wrapping DecryptionException during encrypted
- decryption_error
- Saml2Exception wrapping DecryptionException during encrypted
- Saml2Exception wrapping DecryptionException during encrypted
- Saml2Exception wrapping DecryptionException during encrypted
AI-assisted analysis of spring-projects/spring-security@96852e8860 (2026-09-10).
Data as JSON: /api/errors/f4b3f6ee78700d02.
Report an issue: GitHub.