spring-projects/spring-security · error · Saml2Exception

Saml2Exception wrapping exception from signature signing par

Error message

Saml2Exception wrapping exception from signature signing parameters resolution (see also Assert: "Failed to resolve any signing credential")

What it means

During signature signing parameter resolution, any exception thrown by the resolver is rethrown as Saml2Exception. Additionally, if the resolver yields no SignatureSigningParameters at all, Spring's Assert fails with 'Failed to resolve any signing credential' which is then wrapped the same way. It means the template could not find any credential eligible for signing under the given criteria.

Source

Thrown at saml2/saml2-service-provider/src/opensaml5Main/java/org/springframework/security/saml2/provider/service/web/OpenSaml5Template.java:302

		private SignatureSigningParameters resolveSigningParameters() {
			List<Credential> credentials = resolveSigningCredentials();
			List<String> digests = Collections.singletonList(SignatureConstants.ALGO_ID_DIGEST_SHA256);
			String canonicalization = SignatureConstants.ALGO_ID_C14N_EXCL_OMIT_COMMENTS;
			SignatureSigningParametersResolver resolver = new SAMLMetadataSignatureSigningParametersResolver();
			BasicSignatureSigningConfiguration signingConfiguration = new BasicSignatureSigningConfiguration();
			signingConfiguration.setSigningCredentials(credentials);
			signingConfiguration.setSignatureAlgorithms(this.algs);
			signingConfiguration.setSignatureReferenceDigestMethods(digests);
			signingConfiguration.setSignatureCanonicalizationAlgorithm(canonicalization);
			signingConfiguration.setKeyInfoGeneratorManager(buildSignatureKeyInfoGeneratorManager());
			CriteriaSet criteria = new CriteriaSet(new SignatureSigningConfigurationCriterion(signingConfiguration));
			try {
				SignatureSigningParameters parameters = resolver.resolveSingle(criteria);
				Assert.notNull(parameters, "Failed to resolve any signing credential");
				return parameters;
			}
			catch (Exception ex) {
				throw new Saml2Exception(ex);
			}
		}

		private NamedKeyInfoGeneratorManager buildSignatureKeyInfoGeneratorManager() {
			final NamedKeyInfoGeneratorManager namedManager = new NamedKeyInfoGeneratorManager();

			namedManager.setUseDefaultManager(true);
			final KeyInfoGeneratorManager defaultManager = namedManager.getDefaultManager();

			// Generator for X509Credentials
			final X509KeyInfoGeneratorFactory x509Factory = new X509KeyInfoGeneratorFactory();
			x509Factory.setEmitEntityCertificate(true);
			x509Factory.setEmitEntityCertificateChain(true);

			defaultManager.registerFactory(x509Factory);

			return namedManager;
		}

View on GitHub (pinned to 96852e8860)

Solutions

  1. Configure a signing credential on the RelyingPartyRegistration (signWithX509PrivateKey or signWith(SignatureAlgorithm, credential))
  2. Verify credentials are not consumed solely for decryption/assertion signing
  3. Check that the signing algorithm allow-list includes an algorithm compatible with the credential
  4. Catch Saml2Exception and inspect the wrapped cause / assertion message

Example fix

// before
RelyingPartyRegistration.withRegistrationId("idp") // no signing credential
// after
.signWithX509PrivateKey(privateKey, certificateChain)
.build()
Defensive patterns

Strategy: validation

Validate before calling

List<Saml2X509Credential> signing = registration.getSigningX509Credentials();
if (signing.isEmpty()) throw new Saml2ConfigurationException("No signing credential on RelyingPartyRegistration " + id);

Try / catch

try { params = template.parameters(criteria); } catch (Saml2Exception e) { throw new Saml2ConfigurationException("Resolve signing params: " + e.getMessage(), e); }

Prevention

When it happens

Trigger: Calling sign()/parameters() when RelyingPartyRegistration has no signing credentials configured (no private key in the registration) or no credential satisfies SignatureSigningParametersResolver criteria (e.g. credential is encryption-only or algorithm allow-list excludes it).

Common situations: RelyingPartyRegistration built via registrationId(...) without signWithX509PrivateKey/assertingParty signing setup; credentials marked for encryption only; OpenSAML signing configuration (algorithms) excluding the configured key.

Related errors


AI-assisted analysis of spring-projects/spring-security@96852e8860 (2026-09-10). Data as JSON: /api/errors/e0791a6fa9c1e5eb. Report an issue: GitHub.