generic IssuanceProbe
This commit is contained in:
parent
739facfe06
commit
ce89968837
@ -26,8 +26,8 @@ public class Assertion extends Credential {
|
||||
|
||||
final Assertion.Type assertionType;
|
||||
|
||||
protected Assertion(Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas) {
|
||||
super(resource.getID(), resource, data, jwt, schemas);
|
||||
protected Assertion(Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas, String issuedOnPropertyName) {
|
||||
super(resource.getID(), resource, data, jwt, schemas, issuedOnPropertyName);
|
||||
|
||||
JsonNode typeNode = jsonData.get("type");
|
||||
this.assertionType = Assertion.Type.valueOf(typeNode);
|
||||
@ -60,7 +60,7 @@ public class Assertion extends Credential {
|
||||
public Assertion build() {
|
||||
// transform key of schemas map to string because the type of the key in the base map is generic
|
||||
// and our specific key is an Enum
|
||||
return new Assertion(getResource(), getJsonData(), getJwt(), schemas);
|
||||
return new Assertion(getResource(), getJsonData(), getJwt(), schemas, ISSUED_ON_PROPERTY_NAME);
|
||||
}
|
||||
}
|
||||
|
||||
@ -300,4 +300,5 @@ public class Assertion extends Credential {
|
||||
.build();
|
||||
|
||||
public static final String ID = Assertion.class.getCanonicalName();
|
||||
private static final String ISSUED_ON_PROPERTY_NAME = "issuedOn";
|
||||
}
|
||||
|
@ -29,14 +29,16 @@ public abstract class Credential extends GeneratedObject {
|
||||
final Resource resource;
|
||||
final JsonNode jsonData;
|
||||
final String jwt;
|
||||
final String issuedOnPropertyName;
|
||||
final Map<CredentialEnum, SchemaKey> schemas;
|
||||
|
||||
protected Credential(String id, Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas) {
|
||||
protected Credential(String id, Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas, String issuedOnPropertyName) {
|
||||
super(id, GeneratedObject.Type.INTERNAL);
|
||||
this.resource = checkNotNull(resource);
|
||||
this.jsonData = checkNotNull(data);
|
||||
this.jwt = jwt; //may be null
|
||||
this.schemas = schemas;
|
||||
this.issuedOnPropertyName = issuedOnPropertyName;
|
||||
|
||||
checkTrue(RECOGNIZED_PAYLOAD_TYPES.contains(resource.getType()));
|
||||
}
|
||||
@ -53,6 +55,10 @@ public abstract class Credential extends GeneratedObject {
|
||||
return Optional.ofNullable(jwt);
|
||||
}
|
||||
|
||||
public String getIssuedOnPropertyName() {
|
||||
return issuedOnPropertyName;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the canonical schema for this credential if such exists.
|
||||
*/
|
||||
|
@ -111,7 +111,7 @@ public class EndorsementInspector extends VCInspector implements SubInspector {
|
||||
}
|
||||
|
||||
//revocation, expiration and issuance
|
||||
for(Probe<VerifiableCredential> probe : List.of(new RevocationListProbe(),
|
||||
for(Probe<Credential> probe : List.of(new RevocationListProbe(),
|
||||
new ExpirationProbe(), new IssuanceProbe())) {
|
||||
probeCount++;
|
||||
accumulator.add(probe.run(endorsement, ctx));
|
||||
|
@ -194,7 +194,7 @@ public class OB30Inspector extends VCInspector implements SubInspector {
|
||||
}
|
||||
|
||||
//revocation, expiration and issuance
|
||||
for(Probe<VerifiableCredential> probe : List.of(new RevocationListProbe(),
|
||||
for(Probe<Credential> probe : List.of(new RevocationListProbe(),
|
||||
new ExpirationProbe(), new IssuanceProbe())) {
|
||||
probeCount++;
|
||||
accumulator.add(probe.run(ob, ctx));
|
||||
|
@ -28,8 +28,8 @@ import com.google.common.collect.ImmutableMap;
|
||||
public class VerifiableCredential extends Credential {
|
||||
final VerifiableCredential.Type credentialType;
|
||||
|
||||
protected VerifiableCredential(Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas) {
|
||||
super(ID, resource, data, jwt, schemas);
|
||||
protected VerifiableCredential(Resource resource, JsonNode data, String jwt, Map<CredentialEnum, SchemaKey> schemas, String issuedOnPropertyName) {
|
||||
super(ID, resource, data, jwt, schemas, issuedOnPropertyName);
|
||||
|
||||
JsonNode typeNode = jsonData.get("type");
|
||||
this.credentialType = VerifiableCredential.Type.valueOf(typeNode);
|
||||
@ -133,9 +133,10 @@ public class VerifiableCredential extends Credential {
|
||||
public static class Builder extends Credential.Builder<VerifiableCredential> {
|
||||
@Override
|
||||
public VerifiableCredential build() {
|
||||
return new VerifiableCredential(getResource(), getJsonData(), getJwt(), schemas);
|
||||
return new VerifiableCredential(getResource(), getJsonData(), getJwt(), schemas, ISSUED_ON_PROPERTY_NAME);
|
||||
}
|
||||
}
|
||||
|
||||
public static final String ID = VerifiableCredential.class.getCanonicalName();
|
||||
private static final String ISSUED_ON_PROPERTY_NAME = "issuanceDate";
|
||||
}
|
||||
|
@ -5,7 +5,7 @@ import java.time.ZonedDateTime;
|
||||
import org.oneedtech.inspect.core.probe.Probe;
|
||||
import org.oneedtech.inspect.core.probe.RunContext;
|
||||
import org.oneedtech.inspect.core.report.ReportItems;
|
||||
import org.oneedtech.inspect.vc.VerifiableCredential;
|
||||
import org.oneedtech.inspect.vc.Credential;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
|
||||
@ -13,14 +13,14 @@ import com.fasterxml.jackson.databind.JsonNode;
|
||||
* A Probe that verifies a credential's expiration status
|
||||
* @author mgylling
|
||||
*/
|
||||
public class ExpirationProbe extends Probe<VerifiableCredential> {
|
||||
public class ExpirationProbe extends Probe<Credential> {
|
||||
|
||||
public ExpirationProbe() {
|
||||
super(ID);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReportItems run(VerifiableCredential crd, RunContext ctx) throws Exception {
|
||||
public ReportItems run(Credential crd, RunContext ctx) throws Exception {
|
||||
/*
|
||||
* If the AchievementCredential or EndorsementCredential has an “expirationDate” property
|
||||
* and the expiration date is prior to the current date, the credential has expired.
|
||||
|
@ -5,7 +5,7 @@ import java.time.ZonedDateTime;
|
||||
import org.oneedtech.inspect.core.probe.Probe;
|
||||
import org.oneedtech.inspect.core.probe.RunContext;
|
||||
import org.oneedtech.inspect.core.report.ReportItems;
|
||||
import org.oneedtech.inspect.vc.VerifiableCredential;
|
||||
import org.oneedtech.inspect.vc.Credential;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
|
||||
@ -13,19 +13,19 @@ import com.fasterxml.jackson.databind.JsonNode;
|
||||
* A Probe that verifies a credential's issuance status
|
||||
* @author mgylling
|
||||
*/
|
||||
public class IssuanceProbe extends Probe<VerifiableCredential> {
|
||||
public class IssuanceProbe extends Probe<Credential> {
|
||||
|
||||
public IssuanceProbe() {
|
||||
super(ID);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReportItems run(VerifiableCredential crd, RunContext ctx) throws Exception {
|
||||
public ReportItems run(Credential crd, RunContext ctx) throws Exception {
|
||||
/*
|
||||
* If the AchievementCredential or EndorsementCredential “issuanceDate”
|
||||
* property after the current date, the credential is not yet valid.
|
||||
*/
|
||||
JsonNode node = crd.getJson().get("issuanceDate");
|
||||
JsonNode node = crd.getJson().get(crd.getIssuedOnPropertyName());
|
||||
if(node != null) {
|
||||
try {
|
||||
ZonedDateTime issuanceDate = ZonedDateTime.parse(node.textValue());
|
||||
|
@ -10,6 +10,7 @@ import java.util.List;
|
||||
import org.oneedtech.inspect.core.probe.Probe;
|
||||
import org.oneedtech.inspect.core.probe.RunContext;
|
||||
import org.oneedtech.inspect.core.report.ReportItems;
|
||||
import org.oneedtech.inspect.vc.Credential;
|
||||
import org.oneedtech.inspect.vc.VerifiableCredential;
|
||||
import org.oneedtech.inspect.vc.util.JsonNodeUtil;
|
||||
|
||||
@ -20,14 +21,14 @@ import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
* A Probe that verifies a credential's revocation status.
|
||||
* @author mgylling
|
||||
*/
|
||||
public class RevocationListProbe extends Probe<VerifiableCredential> {
|
||||
public class RevocationListProbe extends Probe<Credential> {
|
||||
|
||||
public RevocationListProbe() {
|
||||
super(ID);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReportItems run(VerifiableCredential crd, RunContext ctx) throws Exception {
|
||||
public ReportItems run(Credential crd, RunContext ctx) throws Exception {
|
||||
|
||||
/*
|
||||
* If the AchievementCredential or EndorsementCredential has a “credentialStatus” property
|
||||
|
@ -0,0 +1,94 @@
|
||||
package org.oneedtech.inspect.vc.probe.validation;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
import org.oneedtech.inspect.core.probe.RunContext;
|
||||
import org.oneedtech.inspect.core.probe.RunContext.Key;
|
||||
import org.oneedtech.inspect.core.report.ReportItems;
|
||||
import org.oneedtech.inspect.util.resource.UriResource;
|
||||
import org.oneedtech.inspect.vc.Validation;
|
||||
import org.oneedtech.inspect.vc.jsonld.JsonLdGeneratedObject;
|
||||
import org.oneedtech.inspect.vc.jsonld.probe.JsonLDCompactionProve;
|
||||
import org.oneedtech.inspect.vc.util.PrimitiveValueValidator;
|
||||
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.ObjectReader;
|
||||
import com.google.common.io.Resources;
|
||||
|
||||
public class ValidationFlattenEmbeddedResourcePropertyProbe extends ValidationPropertyProbe {
|
||||
|
||||
public ValidationFlattenEmbeddedResourcePropertyProbe(Validation validation) {
|
||||
super(validation);
|
||||
}
|
||||
|
||||
public ValidationFlattenEmbeddedResourcePropertyProbe(Validation validation, boolean fullValidate) {
|
||||
super(validation, fullValidate);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected ReportItems reportForNonExistentProperty(JsonNode node, RunContext ctx) {
|
||||
return notRun("Expected property " + validation.getName() + " was missing in node " + node.toString(), ctx);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected ReportItems validate(JsonNode node, RunContext ctx) {
|
||||
try {
|
||||
UriResource uriResource = resolveUriResource(ctx, node.asText());
|
||||
JsonLdGeneratedObject resolved = (JsonLdGeneratedObject) ctx.getGeneratedObject(JsonLDCompactionProve.getId(uriResource));
|
||||
ObjectMapper mapper = (ObjectMapper) ctx.get(Key.JACKSON_OBJECTMAPPER);
|
||||
JsonNode fetchedNode = mapper.readTree(resolved.getJson());
|
||||
|
||||
if (fetchedNode.isTextual()) {
|
||||
return notRun("Property " + validation.getName() + " referenced from " + node.toString() + " is not embedded in need of flattening", ctx);
|
||||
}
|
||||
|
||||
if (!fetchedNode.isObject()) {
|
||||
return error("Property " + validation.getName() + " referenced from " + node.toString() + " is not a JSON object or string as expected", ctx);
|
||||
}
|
||||
|
||||
JsonNode idNode = fetchedNode.get("id");
|
||||
if (idNode == null) {
|
||||
// add a new node to the graph
|
||||
JsonNode newNode = mapper.readTree(Resources.getResource("contexts/ob-v2p0.json"));
|
||||
ObjectReader readerForUpdating = mapper.readerForUpdating(newNode);
|
||||
UUID newId = UUID.randomUUID();
|
||||
JsonNode merged = readerForUpdating.readValue("{\"id\": \"_:" + newId + "\"}");
|
||||
ctx.addGeneratedObject(new JsonLdGeneratedObject(JsonLDCompactionProve.getId(newId.toString()), merged.toString()));
|
||||
|
||||
return warning("Node id missing at " + node.toString() + ". A blank node ID has been assigned", ctx);
|
||||
} else if (!idNode.isTextual() && !PrimitiveValueValidator.validateIri(idNode)) {
|
||||
return error("Embedded JSON object at " + node.asText() + " has no proper assigned id.", ctx);
|
||||
} else if (/*node_class == Assertion && */ !PrimitiveValueValidator.validateUrl(idNode)) {
|
||||
/*
|
||||
if not re.match(URN_REGEX, embedded_node_id, re.IGNORECASE):
|
||||
actions.append(report_message(
|
||||
'ID format for {} at {} not in an expected HTTP or URN:UUID scheme'.format(
|
||||
embedded_node_id, abv_node(node_path=[node_id, prop_name])
|
||||
)))
|
||||
new_node = value.copy()
|
||||
new_node['@context'] = OPENBADGES_CONTEXT_V2_URI
|
||||
actions.append(add_node(embedded_node_id, data=value))
|
||||
actions.append(patch_node(node_id, {prop_name: embedded_node_id}))
|
||||
*/
|
||||
|
||||
} else {
|
||||
|
||||
/*
|
||||
actions.append(patch_node(node_id, {prop_name: embedded_node_id}))
|
||||
|
||||
if not node_match_exists(state, embedded_node_id) and not filter_tasks(
|
||||
state, node_id=embedded_node_id, task_type=FETCH_HTTP_NODE):
|
||||
# fetch
|
||||
actions.append(add_task(FETCH_HTTP_NODE, url=embedded_node_id))
|
||||
*/
|
||||
}
|
||||
} catch (Throwable t) {
|
||||
return fatal(t.getMessage(), ctx);
|
||||
}
|
||||
|
||||
return success(ctx);
|
||||
}
|
||||
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user