[java-oidfed-common] 02/03: Refactor trust mark SignedJWT references into exploiting our TrustMark interface
Codeberg
noreply at shibboleth.net
Thu Jun 4 14:13:07 UTC 2026
This is an automated email from the git hooks/post-receive script.
codeberg pushed a commit to branch main
in repository java-oidfed-common.
View the commit online:
https://codeberg.org/Shibboleth/java-oidfed-common/commit/a792328928ad88cd943d8c5496d7bac1d54a305a
commit a792328928ad88cd943d8c5496d7bac1d54a305a
Author: Henri Mikkonen <henri.mikkonen at iki.fi>
AuthorDate: Thu Jun 4 17:09:49 2026 +0300
Refactor trust mark SignedJWT references into exploiting our TrustMark interface
---
.../context/RelyingPartyTrustChainContext.java | 9 +-
.../oidfed/profile/impl/CallResolveEntityApi.java | 35 ++++----
.../oidfed/profile/impl/ResolveTrustMarks.java | 100 ++++++++-------------
.../oidfed/profile/impl/ValidateTrustMarks.java | 15 ++--
...DefaultTrustChainTrustMarksParsingStrategy.java | 61 ++++++++++---
5 files changed, 111 insertions(+), 109 deletions(-)
diff --git a/oidfed-common-api/src/main/java/net/shibboleth/oidfed/profile/context/RelyingPartyTrustChainContext.java b/oidfed-common-api/src/main/java/net/shibboleth/oidfed/profile/context/RelyingPartyTrustChainContext.java
index 5329012..f96b529 100644
--- a/oidfed-common-api/src/main/java/net/shibboleth/oidfed/profile/context/RelyingPartyTrustChainContext.java
+++ b/oidfed-common-api/src/main/java/net/shibboleth/oidfed/profile/context/RelyingPartyTrustChainContext.java
@@ -24,9 +24,8 @@ import javax.annotation.Nullable;
import org.opensaml.messaging.context.BaseContext;
-import com.nimbusds.jwt.SignedJWT;
-
import net.shibboleth.oidfed.metadata.EntityStatement;
+import net.shibboleth.oidfed.metadata.TrustMark;
import net.shibboleth.oidfed.profile.TrustedRemoteResolverEntity;
import net.shibboleth.shared.annotation.constraint.Live;
@@ -54,7 +53,7 @@ public final class RelyingPartyTrustChainContext extends BaseContext {
@Nullable private Map<String, List<String>> verifiedTrustMarkIds;
/** Verified trust marks for the selected trust chain. */
- @Nullable private Map<String, List<SignedJWT>> verifiedTrustMarks;
+ @Nullable private Map<String, List<TrustMark>> verifiedTrustMarks;
/** Verified trust mark issuers. */
@Nonnull @Live private Map<String, EntityStatement<?>> verifiedTrustMarkIssuers;
@@ -208,7 +207,7 @@ public final class RelyingPartyTrustChainContext extends BaseContext {
*
* @return verified trust marks
*/
- @Nullable public Map<String, List<SignedJWT>> getVerifiedTrustMarks() {
+ @Nullable public Map<String, List<TrustMark>> getVerifiedTrustMarks() {
return verifiedTrustMarks;
}
@@ -220,7 +219,7 @@ public final class RelyingPartyTrustChainContext extends BaseContext {
* @return this context
*/
@Nonnull public RelyingPartyTrustChainContext setVerifiedTrustMarks(
- @Nullable final Map<String, List<SignedJWT>> trustMarks) {
+ @Nullable final Map<String, List<TrustMark>> trustMarks) {
verifiedTrustMarks = trustMarks;
return this;
}
diff --git a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/CallResolveEntityApi.java b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/CallResolveEntityApi.java
index fd49db6..a710cb2 100644
--- a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/CallResolveEntityApi.java
+++ b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/CallResolveEntityApi.java
@@ -39,6 +39,7 @@ import org.opensaml.profile.context.ProfileRequestContext;
import org.opensaml.profile.context.navigate.InboundMessageContextLookup;
import org.slf4j.Logger;
+import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.nimbusds.jwt.SignedJWT;
@@ -49,6 +50,7 @@ import net.shibboleth.oidc.metadata.cache.MetadataCacheException;
import net.shibboleth.oidfed.metadata.EntityConfiguration;
import net.shibboleth.oidfed.metadata.EntityStatement;
import net.shibboleth.oidfed.metadata.ResolveEntityResponse;
+import net.shibboleth.oidfed.metadata.TrustMark;
import net.shibboleth.oidfed.metadata.cache.FederationEndpointEntityStatementCriterion;
import net.shibboleth.oidfed.metadata.cache.ResponseContainerExpirationCriterion;
import net.shibboleth.oidfed.metadata.cache.SubjectEntityIDCriterion;
@@ -57,6 +59,7 @@ import net.shibboleth.oidfed.metadata.cache.configuration.EntityConfigurationCon
import net.shibboleth.oidfed.metadata.cache.resolver.ResolveEntityCacheContainerIdentifier;
import net.shibboleth.oidfed.metadata.cache.resolver.ResolveEntityCacheIdentifierCriterion;
import net.shibboleth.oidfed.metadata.cache.resolver.ResolveEntityResponseContainer;
+import net.shibboleth.oidfed.metadata.impl.TrustMarkImpl;
import net.shibboleth.oidfed.metadata.payload.ResolveEntityResponsePayload;
import net.shibboleth.oidfed.metadata.payload.claim.Metadata;
import net.shibboleth.oidfed.metadata.util.EntityStatementHelper;
@@ -460,7 +463,7 @@ public class CallResolveEntityApi extends AbstractProfileAction {
trustChainContext.setPolicyCompliantTrustChains(policyCompliantChains);
log.debug("{} Populated policy compliant trust chains with {}", getLogPrefix(), policyCompliantChains);
- final List<SignedJWT> trustMarks = rawTrustMarks == null ? null : rawTrustMarks
+ final List<TrustMark> trustMarks = rawTrustMarks == null ? null : rawTrustMarks
.stream()
.filter(Map.class::isInstance)
.map(Map.class::cast)
@@ -468,16 +471,11 @@ public class CallResolveEntityApi extends AbstractProfileAction {
.filter(Objects::nonNull)
.toList();
if (trustMarks != null) {
- final Map<String, List<SignedJWT>> trustMarksByEntity = new HashMap<>();
+ final Map<String, List<TrustMark>> trustMarksByEntity = new HashMap<>();
for (final String entity : chain.stream().map(entity -> entity.getSubject()).toList()) {
- final List<SignedJWT> trustMarksForEntity = trustMarks.stream()
- .filter(jwt -> {
- try {
- return entity.equals(jwt.getJWTClaimsSet().getSubject());
- } catch (final ParseException e1) {
- return false;
- }
- }).toList();
+ final List<TrustMark> trustMarksForEntity = trustMarks.stream()
+ .filter(trustMark -> entity.equals(trustMark.getParsedPayload().getSubject()))
+ .toList();
if (!trustMarksForEntity.isEmpty()) {
trustMarksByEntity.put(entity, trustMarksForEntity);
}
@@ -486,14 +484,7 @@ public class CallResolveEntityApi extends AbstractProfileAction {
trustChainContext.setVerifiedTrustMarks(trustMarksByEntity);
final Map<String, List<String>> trustMarkIds = trustMarksByEntity.entrySet().stream()
.collect(Collectors.toMap(entry -> entry.getKey(), entry -> entry.getValue().stream()
- .map(jwt -> {
- try {
- return jwt.getJWTClaimsSet().getStringClaim("trust_mark_type");
- } catch (final ParseException e1) {
- return null;
- }
- })
- .filter(Objects::nonNull)
+ .map(trustMark -> trustMark.getParsedPayload().getTrustMarkType())
.toList()));
log.debug("{} The following trust marks are included: {}", getLogPrefix(), trustMarkIds);
trustChainContext.setVerifiedTrustMarkIds(trustMarkIds);
@@ -520,12 +511,16 @@ public class CallResolveEntityApi extends AbstractProfileAction {
* @param trustMark trust mark to be verified, expected to be parseable from string
* @return trust mark JWT if valid, null otherwise
*/
- @Nullable private SignedJWT parseTrustMark(@Nullable final Object trustMark) {
+ @Nullable private TrustMark parseTrustMark(@Nullable final Object trustMark) {
if (trustMark instanceof String string) {
try {
- return SignedJWT.parse(string);
+ final SignedJWT jwt = SignedJWT.parse(string);
+ assert jwt != null; assert objectMapper != null;
+ return TrustMarkImpl.parse(jwt, objectMapper);
} catch (final ParseException e) {
log.error("{} Could not parse the trust mark into a JWT", getLogPrefix(), e);
+ } catch (final JsonProcessingException e) {
+ log.error("{} Could not parse JWT payload into a trust mark", getLogPrefix(), e);
}
}
return null;
diff --git a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ResolveTrustMarks.java b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ResolveTrustMarks.java
index cadb3b9..f082794 100644
--- a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ResolveTrustMarks.java
+++ b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ResolveTrustMarks.java
@@ -45,10 +45,12 @@ import net.shibboleth.oidc.jwt.claims.JWTValidationException;
import net.shibboleth.oidc.metadata.cache.MetadataCache;
import net.shibboleth.oidc.metadata.cache.MetadataCacheException;
import net.shibboleth.oidfed.metadata.EntityStatement;
+import net.shibboleth.oidfed.metadata.TrustMark;
import net.shibboleth.oidfed.metadata.cache.SubjectEntityIDCriterion;
import net.shibboleth.oidfed.metadata.cache.SubjectEntityStatementCriterion;
import net.shibboleth.oidfed.metadata.cache.TrustMarkOwnersCriterion;
import net.shibboleth.oidfed.metadata.cache.trustchain.TrustChainsContainer;
+import net.shibboleth.oidfed.metadata.payload.TrustMarkPayload;
import net.shibboleth.oidfed.metadata.payload.claim.TrustMarkOwner;
import net.shibboleth.oidfed.profile.context.RelyingPartyTrustChainContext;
import net.shibboleth.oidfed.profile.context.VerifiedTrustChain;
@@ -80,7 +82,7 @@ public class ResolveTrustMarks extends AbstractProfileAction {
/** Strategy used to parse trust marks from the selected trust chain. */
@NonnullAfterInit
- private Function<List<EntityStatement<?>>,Map<String,List<SignedJWT>>> trustChainTrustMarksParsingStrategy;
+ private Function<List<EntityStatement<?>>,Map<String,List<TrustMark>>> trustChainTrustMarksParsingStrategy;
/** Strategy used to lookup trusted trust mark issuers for the trust chain. */
@NonnullAfterInit
@@ -151,7 +153,7 @@ public class ResolveTrustMarks extends AbstractProfileAction {
* @param strategy parsing strategy
*/
public void setTrustChainTrustMarksParsingStrategy(
- @Nonnull final Function<List<EntityStatement<?>>,Map<String,List<SignedJWT>>> strategy) {
+ @Nonnull final Function<List<EntityStatement<?>>,Map<String,List<TrustMark>>> strategy) {
checkSetterPreconditions();
trustChainTrustMarksParsingStrategy =
Constraint.isNotNull(strategy, "TrustChainTrustMarksParsingStrategy cannot be null");
@@ -328,14 +330,15 @@ public class ResolveTrustMarks extends AbstractProfileAction {
trustChainContext.setVerifiedTrustMarks(CollectionSupport.emptyMap());
trustChainContext.setVerifiedTrustMarkIds(CollectionSupport.emptyMap());
- final Map<String, List<SignedJWT>> chainTrustMarks =
+ final Map<String, List<TrustMark>> chainTrustMarks =
Optional.ofNullable(trustChainTrustMarksParsingStrategy.apply(selectedTrustChain))
.orElseGet(NonnullSupplier.of(CollectionSupport.emptyMap()))
.entrySet().stream()
.collect(Collectors.toMap(entry -> entry.getKey(),
entry -> entry.getValue().stream()
.filter(trustMark ->
- validateClaims(trustMarkClaimsValidator, trustMark, profileRequestContext))
+ validateClaims(trustMarkClaimsValidator, trustMark.getJwt(),
+ profileRequestContext))
.toList()));
if (chainTrustMarks == null || chainTrustMarks.isEmpty()) {
log.debug("{} No valid trust marks found from the selected trust chain", getLogPrefix());
@@ -354,9 +357,9 @@ public class ResolveTrustMarks extends AbstractProfileAction {
log.debug("{} Trusted trust mark owners {}", getLogPrefix(), trustedOwners);
assert trustedOwners != null;
- final Map<String, List<SignedJWT>> verifiedTrustMarks = new HashMap<>();
+ final Map<String, List<TrustMark>> verifiedTrustMarks = new HashMap<>();
for (final EntityStatement<?> statement : selectedTrustChain) {
- final List<SignedJWT> trustMarks = chainTrustMarks.get(statement.getSubject());
+ final List<TrustMark> trustMarks = chainTrustMarks.get(statement.getSubject());
if (trustMarks == null || trustMarks.isEmpty()) {
break;
}
@@ -373,7 +376,7 @@ public class ResolveTrustMarks extends AbstractProfileAction {
trustChainContext.setVerifiedTrustMarks(verifiedTrustMarks);
final Map<String, List<String>> verifiedTrustMarkIds = verifiedTrustMarks.entrySet().stream()
.collect(Collectors.toMap(entry -> entry.getKey(), entry -> entry.getValue().stream()
- .map(list -> getTrustMarkId(list))
+ .map(trustMark -> trustMark.getParsedPayload().getTrustMarkType())
.collect(Collectors.toList())));
log.debug("{} The following trust marks are validated: {}", getLogPrefix(), verifiedTrustMarkIds);
trustChainContext.setVerifiedTrustMarkIds(verifiedTrustMarkIds);
@@ -406,43 +409,36 @@ public class ResolveTrustMarks extends AbstractProfileAction {
/**
* Verifies the given trust mark meets configuration for trusted trust mark issuers.
*
- * @param jwt the trust mark to be verified
+ * @param trustMark the trust mark to be verified
* @param trustedIssuers the trusted trust mark issuers
* @param trustedOwners the trusted trust mark owners
* @return true if the trust mark meets configuration, false otherwise
*/
- protected boolean checkTrustedIssuer(@Nullable final SignedJWT jwt,
+ protected boolean checkTrustedIssuer(@Nullable final TrustMark trustMark,
@Nonnull final Map<String, List<String>> trustedIssuers,
@Nonnull final Map<String, TrustMarkOwner> trustedOwners) {
- if (jwt == null) {
+ if (trustMark == null) {
return false;
}
- try {
- final JWTClaimsSet claimsSet = jwt.getJWTClaimsSet();
- final String id = StringSupport.trimOrNull(getTrustMarkId(jwt));
- if (id == null) {
+ final String id = StringSupport.trimOrNull(trustMark.getParsedPayload().getTrustMarkType());
+ if (id == null) {
+ return false;
+ }
+ if (trustedIssuers.containsKey(id)) {
+ final String issuer = trustMark.getIssuer();
+ final List<String> validIssuers = trustedIssuers.get(id);
+ if (validIssuers == null || !validIssuers.contains(issuer)) {
+ log.debug("{} Issuer {} is not valid trust mark issuer", getLogPrefix(), issuer);
return false;
}
- if (trustedIssuers.containsKey(id)) {
- final String issuer = claimsSet.getIssuer();
- assert issuer != null;
- final List<String> validIssuers = trustedIssuers.get(id);
- if (validIssuers == null || !validIssuers.contains(issuer)) {
- log.debug("{} Issuer {} is not valid trust mark issuer", getLogPrefix(), issuer);
- return false;
- }
- } else if (trustedOwners.containsKey(id)) {
- log.debug("{} Trust mark ID {} is included in trusted owners", getLogPrefix(), id);
- if (claimsSet.getStringClaim("delegation") == null) {
- log.debug("(} Trust mark ID {} does not contain a delegation claim", getLogPrefix(), id);
- return false;
- }
- } else {
- log.debug("{} Trust mark ID {} is not included in the trusted issuers", getLogPrefix(), id);
+ } else if (trustedOwners.containsKey(id)) {
+ log.debug("{} Trust mark ID {} is included in trusted owners", getLogPrefix(), id);
+ if (trustMark.getParsedPayload().getDelegation() == null) {
+ log.debug("(} Trust mark ID {} does not contain a delegation claim", getLogPrefix(), id);
return false;
}
- } catch (final ParseException e) {
- log.error("{} Could not parse TrustMark JWT contents", getLogPrefix(), e);
+ } else {
+ log.debug("{} Trust mark ID {} is not included in the trusted issuers", getLogPrefix(), id);
return false;
}
return true;
@@ -452,27 +448,20 @@ public class ResolveTrustMarks extends AbstractProfileAction {
* Verifies the given trust mark by exploiting (1) the trust chain cache for fetching the trust chain for the issuer
* entity configuration and (2) the trust engine for validating the trust mark signature.
*
- * @param jwt the trust mark to be verified
+ * @param trustMark the trust mark to be verified
* @param trustedOwners the trusted trust mark owners
* @param profileRequestContext the profile request context
* @param trustedTrustMarkIssuers the map of trusted issuers that will be populated if issuer was verified
* @return true if trust mark verification was successful, false otherwise
*/
- protected boolean verifyTrustMark(@Nullable final SignedJWT jwt,
+ protected boolean verifyTrustMark(@Nullable final TrustMark trustMark,
@Nonnull final Map<String, TrustMarkOwner> trustedOwners,
@Nonnull final ProfileRequestContext profileRequestContext,
@Nonnull @Live final Map<String, EntityStatement<?>> trustedTrustMarkIssuers) {
- if (jwt == null) {
+ if (trustMark == null) {
return false;
}
- final JWTClaimsSet trustMarkClaims;
- try {
- trustMarkClaims = jwt.getJWTClaimsSet();
- } catch (final ParseException e) {
- log.error("{} Could not parse the TrustMark JWT contents", getLogPrefix(), e);
- return false;
- }
- final String issuer = trustMarkClaims.getIssuer();
+ final String issuer = trustMark.getIssuer();
assert issuer != null;
log.debug("{} Resolving trust chain for {}", getLogPrefix(), issuer);
final List<TrustChainsContainer> cacheResult;
@@ -493,12 +482,12 @@ public class ResolveTrustMarks extends AbstractProfileAction {
trustedTrustMarkIssuers.put(trustMarkIssuer.getSubject(), trustMarkIssuer);
log.trace("{} Validating entity statement {}", getLogPrefix(), trustMarkIssuer.getJwt().serialize());
try {
- if (trustEngine.validate(jwt, criteria)) {
- final String id = getTrustMarkId(jwt);
+ if (trustEngine.validate(trustMark.getJwt(), criteria)) {
+ final String id = trustMark.getParsedPayload().getTrustMarkType();
assert id != null;
log.debug("{} Successfully validated trust mark {} issued by {}", getLogPrefix(), id, issuer);
if (trustedOwners.containsKey(id)) {
- return validateDelegatedTrustMark(trustMarkClaims, id, trustedOwners, profileRequestContext);
+ return validateDelegatedTrustMark(trustMark.getParsedPayload(), id, trustedOwners, profileRequestContext);
} else {
return true;
}
@@ -518,13 +507,13 @@ public class ResolveTrustMarks extends AbstractProfileAction {
* @param profileRequestContext the profile request context
* @return true if delegation JWT was valid, false otherwise
*/
- protected boolean validateDelegatedTrustMark(@Nonnull final JWTClaimsSet trustMarkClaims,
+ protected boolean validateDelegatedTrustMark(@Nonnull final TrustMarkPayload trustMarkClaims,
@Nonnull final String id,
@Nonnull final Map<String, TrustMarkOwner> trustedOwners,
@Nonnull final ProfileRequestContext profileRequestContext) {
log.debug("{} Validating delegated trust mark {}", getLogPrefix(), id);
try {
- final SignedJWT delegationJwt = SignedJWT.parse(trustMarkClaims.getStringClaim("delegation"));
+ final SignedJWT delegationJwt = SignedJWT.parse(trustMarkClaims.getDelegation());
final CriteriaSet delegationCriteria = new CriteriaSet(
new TrustMarkOwnersCriterion(trustedOwners),
new SubjectEntityIDCriterion(id));
@@ -551,19 +540,4 @@ public class ResolveTrustMarks extends AbstractProfileAction {
}
return false;
}
-
- /**
- * Parses the trust mark ID for the given trust mark.
- *
- * @param trustMark the trust mark
- * @return the ID, or null if it could not be parsed
- */
- @Nullable private String getTrustMarkId(@Nullable final SignedJWT trustMark) {
- try {
- return trustMark == null ? null : trustMark.getJWTClaimsSet().getStringClaim("trust_mark_type");
- } catch (final ParseException e) {
- log.error("{} Could not parse the TrustMark JWT contents", getLogPrefix(), e);
- }
- return null;
- }
}
\ No newline at end of file
diff --git a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ValidateTrustMarks.java b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ValidateTrustMarks.java
index d3e7e88..2500e82 100644
--- a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ValidateTrustMarks.java
+++ b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/impl/ValidateTrustMarks.java
@@ -36,6 +36,7 @@ import net.shibboleth.idp.profile.AbstractProfileAction;
import net.shibboleth.oidc.metadata.cache.MetadataCache;
import net.shibboleth.oidc.metadata.cache.MetadataCacheException;
import net.shibboleth.oidfed.metadata.EntityStatement;
+import net.shibboleth.oidfed.metadata.TrustMark;
import net.shibboleth.oidfed.metadata.cache.trustmark.TrustMarkStatusCacheIdentifier;
import net.shibboleth.oidfed.metadata.cache.trustmark.TrustMarkStatusContainer;
import net.shibboleth.oidfed.metadata.cache.trustmark.TrustMarkStatusIdentifierCriterion;
@@ -165,10 +166,10 @@ public class ValidateTrustMarks extends AbstractProfileAction {
/** {@inheritDoc} */
@Override
protected void doExecute(@Nonnull final ProfileRequestContext profileRequestContext) {
- final Map<String, List<SignedJWT>> verifiedTrustMarks = trustChainContext.getVerifiedTrustMarks();
+ final Map<String, List<TrustMark>> verifiedTrustMarks = trustChainContext.getVerifiedTrustMarks();
final Map<String, List<String>> verifiedTrustMarkIds = trustChainContext.getVerifiedTrustMarkIds();
final String subject = selectedTrustChain.get(0).getSubject();
- final List<SignedJWT> subjectTrustMarks = verifiedTrustMarks != null ? verifiedTrustMarks.get(subject) : null;
+ final List<TrustMark> subjectTrustMarks = verifiedTrustMarks != null ? verifiedTrustMarks.get(subject) : null;
final List<String> subjectTrustMarkIds =
verifiedTrustMarkIds != null ? verifiedTrustMarkIds.get(subject) : null;
if (subjectTrustMarks == null || subjectTrustMarks.isEmpty()) {
@@ -181,12 +182,12 @@ public class ValidateTrustMarks extends AbstractProfileAction {
return;
}
log.trace("{} Subject trust marks before validation {}", getLogPrefix(), subjectTrustMarks);
- for (final SignedJWT trustMark : CollectionSupport.copyToList(subjectTrustMarks)) {
+ for (final TrustMark trustMark : CollectionSupport.copyToList(subjectTrustMarks)) {
assert trustMark != null;
try {
- final String issuer = trustMark.getJWTClaimsSet().getIssuer();
- final String trustMarkSubject = trustMark.getJWTClaimsSet().getSubject();
- final String trustMarkType = trustMark.getJWTClaimsSet().getStringClaim("trust_mark_type");
+ final String issuer = trustMark.getIssuer();
+ final String trustMarkSubject = trustMark.getParsedPayload().getSubject();
+ final String trustMarkType = trustMark.getParsedPayload().getTrustMarkType();
final EntityStatement<?> issuerStatement = trustChainContext.getVerifiedTrustMarkIssuers().get(issuer);
if (issuerStatement == null) {
log.warn("{} Could not resolve trust mark issuer statement for {}", getLogPrefix(), issuer);
@@ -205,7 +206,7 @@ public class ValidateTrustMarks extends AbstractProfileAction {
continue;
}
final TrustMarkStatusCacheIdentifier cacheIdentifier =
- new TrustMarkStatusCacheIdentifier(uri, trustMark);
+ new TrustMarkStatusCacheIdentifier(uri, trustMark.getJwt());
final CriteriaSet criteria = new CriteriaSet(new TrustMarkStatusIdentifierCriterion(cacheIdentifier));
final List<TrustMarkStatusContainer> cacheResult = trustMarkStatusCache.get(criteria);
if (cacheResult.isEmpty()) {
diff --git a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/navigate/DefaultTrustChainTrustMarksParsingStrategy.java b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/navigate/DefaultTrustChainTrustMarksParsingStrategy.java
index f0529ba..f5e2d08 100644
--- a/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/navigate/DefaultTrustChainTrustMarksParsingStrategy.java
+++ b/oidfed-common-impl/src/main/java/net/shibboleth/oidfed/profile/navigate/DefaultTrustChainTrustMarksParsingStrategy.java
@@ -26,13 +26,19 @@ import javax.annotation.Nullable;
import org.slf4j.Logger;
-import com.nimbusds.jwt.JWTClaimsSet;
+import com.fasterxml.jackson.core.JsonProcessingException;
+import com.fasterxml.jackson.databind.ObjectMapper;
import com.nimbusds.jwt.SignedJWT;
import net.shibboleth.oidfed.metadata.EntityStatement;
+import net.shibboleth.oidfed.metadata.TrustMark;
+import net.shibboleth.oidfed.metadata.impl.TrustMarkImpl;
import net.shibboleth.oidfed.metadata.payload.EntityConfigurationPayload;
+import net.shibboleth.shared.annotation.constraint.NonnullAfterInit;
import net.shibboleth.shared.annotation.constraint.ThreadSafeAfterInit;
import net.shibboleth.shared.component.AbstractIdentifiableInitializableComponent;
+import net.shibboleth.shared.component.ComponentInitializationException;
+import net.shibboleth.shared.logic.Constraint;
import net.shibboleth.shared.primitive.LoggerFactory;
import net.shibboleth.shared.primitive.StringSupport;
@@ -42,21 +48,45 @@ import net.shibboleth.shared.primitive.StringSupport;
*/
@ThreadSafeAfterInit
public class DefaultTrustChainTrustMarksParsingStrategy extends AbstractIdentifiableInitializableComponent
- implements Function<List<EntityStatement<?>>,Map<String,List<SignedJWT>>> {
+ implements Function<List<EntityStatement<?>>,Map<String,List<TrustMark>>> {
/** Class logger. */
@Nonnull private Logger log = LoggerFactory.getLogger(DefaultTrustChainTrustMarksParsingStrategy.class);
+ /** JSON object mapper used for decoding JSON into Map. */
+ @NonnullAfterInit protected ObjectMapper objectMapper;
+
+ /**
+
+ * Set the JSON {@link ObjectMapper} used for decoding JSON into Map.
+ *
+ * @param mapper object mapper
+ */
+ public void setObjectMapper(@Nonnull final ObjectMapper mapper) {
+ checkSetterPreconditions();
+
+ objectMapper = Constraint.isNotNull(mapper, "Object mapper cannot be null");
+ }
+
+ /** {@inheritDoc} */
+ @Override
+ protected void doInitialize() throws ComponentInitializationException {
+ super.doInitialize();
+ if (objectMapper == null) {
+ throw new ComponentInitializationException("Object mapper cannot be null");
+ }
+ }
+
/** {@inheritDoc} */
@Override @Nullable
- public Map<String, List<SignedJWT>> apply(@Nullable final List<EntityStatement<?>> trustChain) {
+ public Map<String, List<TrustMark>> apply(@Nullable final List<EntityStatement<?>> trustChain) {
checkComponentActive();
if (trustChain == null || trustChain.size() < 3) {
log.error("Unexpected length in the trust chain: {}", trustChain == null ? "null" : trustChain.size());
return null;
}
- final Map<String, List<SignedJWT>> result = new HashMap<>();
+ final Map<String, List<TrustMark>> result = new HashMap<>();
for (final EntityStatement<?> statement : trustChain) {
assert statement != null;
if (statement.getParsedPayload() instanceof EntityConfigurationPayload ecp) {
@@ -67,7 +97,7 @@ public class DefaultTrustChainTrustMarksParsingStrategy extends AbstractIdentifi
if (rawTrustMarks != null && !rawTrustMarks.isEmpty()) {
log.trace("Transforming the trust mark into a JWT");
- final List<SignedJWT> trustMarks = rawTrustMarks
+ final List<TrustMark> trustMarks = rawTrustMarks
.stream()
.map(entry -> parseTrustMark(entry))
.filter(Objects::nonNull)
@@ -88,7 +118,7 @@ public class DefaultTrustChainTrustMarksParsingStrategy extends AbstractIdentifi
* @param trustMarkEntry trust mark entry as Strign to be parsed into a JWT
* @return trust mark JWT if valid, null otherwise
*/
- @Nullable private SignedJWT parseTrustMark(@Nullable final Map<String, String> trustMarkEntry) {
+ @Nullable private TrustMark parseTrustMark(@Nullable final Map<String, String> trustMarkEntry) {
if (trustMarkEntry == null) {
return null;
}
@@ -100,28 +130,31 @@ public class DefaultTrustChainTrustMarksParsingStrategy extends AbstractIdentifi
*
* @param trustMark trust mark to be verified
* @param id the id to be verified from the JWT claims set
- * @return trust mark JWT if valid, null otherwise
+ * @return trust mark if valid, null otherwise
*/
- @Nullable private SignedJWT verifyTrustMark(@Nullable final String trustMark, @Nullable final String id) {
+ @Nullable private TrustMark verifyTrustMark(@Nullable final String trustMark, @Nullable final String id) {
if (trustMark == null || id == null) {
log.trace("Could not parse trust mark {} with trust_mark_type {}", trustMark, id);
return null;
}
try {
final SignedJWT jwt = SignedJWT.parse((String) trustMark);
- final JWTClaimsSet trustMarkClaims = jwt.getJWTClaimsSet();
- if (StringSupport.trimOrNull(trustMarkClaims.getIssuer()) == null) {
+ assert jwt != null; assert objectMapper != null;
+ final TrustMarkImpl result = TrustMarkImpl.parse(jwt, objectMapper);
+ if (StringSupport.trimOrNull(result.getIssuer()) == null) {
log.error("Trust Mark {} is missing mandatory issuer",
- trustMarkClaims.getStringClaim("trust_mark_type"));
+ result.getParsedPayload().getTrustMarkType());
return null;
}
- if (id.equals(trustMarkClaims.getStringClaim("trust_mark_type"))) {
- return jwt;
+ if (id.equals(result.getParsedPayload().getTrustMarkType())) {
+ return result;
}
log.error("The id {} is not matching with the trust_mark_type-claim {}", id,
- trustMarkClaims.getStringClaim("trust_mark_type"));
+ result.getParsedPayload().getTrustMarkType());
} catch (final ParseException e) {
log.error("Could not parse id-claim from the trust mark", e);
+ } catch (final JsonProcessingException e) {
+ log.error("Could not parse trust mark from the JWT", e);
}
return null;
}
--
To stop receiving notification emails like this one, please contact
the administrator of this repository.
More information about the commits
mailing list