diff --git a/src/main/java/org/cyclonedx/generators/json/BomJsonGenerator.java b/src/main/java/org/cyclonedx/generators/json/BomJsonGenerator.java index a462d6bb1..cb9260bc2 100644 --- a/src/main/java/org/cyclonedx/generators/json/BomJsonGenerator.java +++ b/src/main/java/org/cyclonedx/generators/json/BomJsonGenerator.java @@ -45,6 +45,7 @@ public class BomJsonGenerator extends AbstractBomGenerator /** * Constructs a new BomGenerator object. * @param bom the BOM to generate + * @param version the version of the CycloneDX schema to use. */ public BomJsonGenerator(Bom bom, final Version version) { super(version, bom, Format.JSON); diff --git a/src/main/java/org/cyclonedx/generators/xml/BomXmlGenerator.java b/src/main/java/org/cyclonedx/generators/xml/BomXmlGenerator.java index fe721d092..e135dd69f 100644 --- a/src/main/java/org/cyclonedx/generators/xml/BomXmlGenerator.java +++ b/src/main/java/org/cyclonedx/generators/xml/BomXmlGenerator.java @@ -48,6 +48,7 @@ public class BomXmlGenerator extends AbstractBomGenerator /** * Constructs a new BomXmlGenerator object. * @param bom the BOM to generate + * @param version the version of the CycloneDX schema to use. */ public BomXmlGenerator(final Bom bom, final Version version) { super(version, bom, Format.XML); @@ -121,6 +122,7 @@ String toXML(final Bom bom, final boolean prettyPrint) throws GeneratorException * Creates a CycloneDX BoM from a set of Components. * @return an XML Document representing a CycloneDX BoM * @since 1.1.0 + * @throws ParserConfigurationException if an error occurs */ public Document generate() throws ParserConfigurationException { return generateDocument(bom); diff --git a/src/main/java/org/cyclonedx/model/Annotation.java b/src/main/java/org/cyclonedx/model/Annotation.java index ad9698405..4cfa8a362 100644 --- a/src/main/java/org/cyclonedx/model/Annotation.java +++ b/src/main/java/org/cyclonedx/model/Annotation.java @@ -58,6 +58,8 @@ public class Annotation extends ExtensibleElement private String text; + @JsonOnly + @JsonProperty("signature") private Signature signature; public String getBomRef() { diff --git a/src/main/java/org/cyclonedx/model/Evidence.java b/src/main/java/org/cyclonedx/model/Evidence.java index 3a925bd19..453e680c8 100644 --- a/src/main/java/org/cyclonedx/model/Evidence.java +++ b/src/main/java/org/cyclonedx/model/Evidence.java @@ -78,8 +78,8 @@ public void setLicenses(LicenseChoice licenses) { this.licenses = licenses; } - @JacksonXmlElementWrapper(useWrapping = false) - @JacksonXmlProperty(localName = "copyright") + @JacksonXmlElementWrapper(localName = "copyright") + @JacksonXmlProperty(localName = "text") @JsonProperty("copyright") public List getCopyright() { return copyright; diff --git a/src/main/java/org/cyclonedx/model/attestation/Attestation.java b/src/main/java/org/cyclonedx/model/attestation/Attestation.java index e7b3e67f9..f1c31b80c 100644 --- a/src/main/java/org/cyclonedx/model/attestation/Attestation.java +++ b/src/main/java/org/cyclonedx/model/attestation/Attestation.java @@ -8,6 +8,7 @@ import com.fasterxml.jackson.annotation.JsonPropertyOrder; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.Signature; @JsonIgnoreProperties(ignoreUnknown = true) @@ -26,6 +27,7 @@ public class Attestation private List map; + @JsonOnly private Signature signature; public String getSummary() { diff --git a/src/main/java/org/cyclonedx/model/attestation/Claim.java b/src/main/java/org/cyclonedx/model/attestation/Claim.java index 02b6c9382..0997efb38 100644 --- a/src/main/java/org/cyclonedx/model/attestation/Claim.java +++ b/src/main/java/org/cyclonedx/model/attestation/Claim.java @@ -10,6 +10,7 @@ import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; import org.cyclonedx.model.ExternalReference; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.Signature; @JsonIgnoreProperties(ignoreUnknown = true) @@ -44,6 +45,7 @@ public class Claim private List externalReferences; + @JsonOnly private Signature signature; public String getBomRef() { @@ -111,7 +113,7 @@ public void setCounterEvidence(final List counterEvidence) { } @JacksonXmlElementWrapper(localName = "externalReferences") - @JacksonXmlProperty(localName = "externalReference") + @JacksonXmlProperty(localName = "reference") public List getExternalReferences() { return externalReferences; } diff --git a/src/main/java/org/cyclonedx/model/attestation/Declarations.java b/src/main/java/org/cyclonedx/model/attestation/Declarations.java index 2943147bf..c1da306bf 100644 --- a/src/main/java/org/cyclonedx/model/attestation/Declarations.java +++ b/src/main/java/org/cyclonedx/model/attestation/Declarations.java @@ -8,6 +8,8 @@ import com.fasterxml.jackson.annotation.JsonPropertyOrder; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import org.cyclonedx.model.ExtensibleElement; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.Signature; import org.cyclonedx.model.attestation.affirmation.Affirmation; import org.cyclonedx.model.attestation.evidence.Evidence; @@ -23,7 +25,7 @@ "affirmation", "signature" }) -public class Declarations +public class Declarations extends ExtensibleElement { private List assessors; @@ -37,8 +39,11 @@ public class Declarations private Affirmation affirmation; + @JsonOnly private Signature signature; + @JacksonXmlElementWrapper(localName = "assessors") + @JacksonXmlProperty(localName = "assessor") public List getAssessors() { return assessors; } diff --git a/src/main/java/org/cyclonedx/model/attestation/affirmation/Affirmation.java b/src/main/java/org/cyclonedx/model/attestation/affirmation/Affirmation.java index fd76a100d..39dc42f2b 100644 --- a/src/main/java/org/cyclonedx/model/attestation/affirmation/Affirmation.java +++ b/src/main/java/org/cyclonedx/model/attestation/affirmation/Affirmation.java @@ -8,6 +8,8 @@ import com.fasterxml.jackson.annotation.JsonPropertyOrder; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import org.cyclonedx.model.ExtensibleElement; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.Signature; @JsonIgnoreProperties(ignoreUnknown = true) @@ -17,12 +19,13 @@ "signatories", "signature" }) -public class Affirmation +public class Affirmation extends ExtensibleElement { private String statement; private List signatories; + @JsonOnly private Signature signature; public String getStatement() { diff --git a/src/main/java/org/cyclonedx/model/attestation/affirmation/Signatory.java b/src/main/java/org/cyclonedx/model/attestation/affirmation/Signatory.java index 84c85454c..bd714e6c3 100644 --- a/src/main/java/org/cyclonedx/model/attestation/affirmation/Signatory.java +++ b/src/main/java/org/cyclonedx/model/attestation/affirmation/Signatory.java @@ -4,23 +4,27 @@ import com.fasterxml.jackson.annotation.JsonIgnoreProperties; import com.fasterxml.jackson.annotation.JsonInclude; +import com.fasterxml.jackson.annotation.JsonPropertyOrder; import com.fasterxml.jackson.annotation.JsonTypeName; import com.fasterxml.jackson.databind.annotation.JsonDeserialize; +import org.cyclonedx.model.ExtensibleElement; import org.cyclonedx.model.ExternalReference; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.OrganizationalEntity; import org.cyclonedx.model.Signature; import org.cyclonedx.util.deserializer.SignatoryDeserializer; @JsonIgnoreProperties(ignoreUnknown = true) @JsonInclude(JsonInclude.Include.NON_EMPTY) -@JsonTypeName("signatory") +@JsonPropertyOrder({"name", "role", "signature", "organization", "externalReference"}) @JsonDeserialize(using = SignatoryDeserializer.class) -public class Signatory +public class Signatory extends ExtensibleElement { private String name; private String role; + @JsonOnly private Signature signature; private OrganizationalEntity organization; diff --git a/src/main/java/org/cyclonedx/model/attestation/evidence/Evidence.java b/src/main/java/org/cyclonedx/model/attestation/evidence/Evidence.java index 68336cc2d..f3baa324a 100644 --- a/src/main/java/org/cyclonedx/model/attestation/evidence/Evidence.java +++ b/src/main/java/org/cyclonedx/model/attestation/evidence/Evidence.java @@ -11,6 +11,8 @@ import com.fasterxml.jackson.databind.annotation.JsonSerialize; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import org.cyclonedx.model.ExtensibleElement; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.OrganizationalContact; import org.cyclonedx.model.Signature; import org.cyclonedx.util.serializer.CustomDateSerializer; @@ -27,7 +29,7 @@ "reviewer", "signature" }) -public class Evidence +public class Evidence extends ExtensibleElement { @JacksonXmlProperty(isAttribute = true, localName = "bom-ref") @JsonProperty("bom-ref") @@ -49,6 +51,7 @@ public class Evidence private OrganizationalContact reviewer; + @JsonOnly private Signature signature; public String getBomRef() { diff --git a/src/main/java/org/cyclonedx/model/component/crypto/AlgorithmProperties.java b/src/main/java/org/cyclonedx/model/component/crypto/AlgorithmProperties.java index 946219aee..cd9971809 100644 --- a/src/main/java/org/cyclonedx/model/component/crypto/AlgorithmProperties.java +++ b/src/main/java/org/cyclonedx/model/component/crypto/AlgorithmProperties.java @@ -26,7 +26,10 @@ "curve", "executionEnvironment", "implementationPlatform", - "certificationLevel", "mode", "padding", "cryptoFunctions", + "certificationLevel", + "mode", + "padding", + "cryptoFunctions", "classicalSecurityLevel", "nistQuantumSecurityLevel" }) public class AlgorithmProperties diff --git a/src/main/java/org/cyclonedx/model/definition/Standard.java b/src/main/java/org/cyclonedx/model/definition/Standard.java index f0e5f3050..bee0df96b 100644 --- a/src/main/java/org/cyclonedx/model/definition/Standard.java +++ b/src/main/java/org/cyclonedx/model/definition/Standard.java @@ -10,6 +10,7 @@ import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; import org.cyclonedx.model.ExternalReference; +import org.cyclonedx.model.JsonOnly; import org.cyclonedx.model.Signature; @JsonIgnoreProperties(ignoreUnknown = true) @@ -44,6 +45,7 @@ public class Standard private List externalReferences; + @JsonOnly private Signature signature; public String getBomRef() { diff --git a/src/main/java/org/cyclonedx/model/vulnerability/ProofOfConcept.java b/src/main/java/org/cyclonedx/model/vulnerability/ProofOfConcept.java new file mode 100644 index 000000000..89f6a832d --- /dev/null +++ b/src/main/java/org/cyclonedx/model/vulnerability/ProofOfConcept.java @@ -0,0 +1,74 @@ +package org.cyclonedx.model.vulnerability; + +import java.util.List; +import java.util.Objects; + +import com.fasterxml.jackson.annotation.JsonIgnoreProperties; +import com.fasterxml.jackson.annotation.JsonInclude; +import com.fasterxml.jackson.annotation.JsonProperty; +import com.fasterxml.jackson.annotation.JsonPropertyOrder; +import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlElementWrapper; +import com.fasterxml.jackson.dataformat.xml.annotation.JacksonXmlProperty; +import org.cyclonedx.model.AttachmentText; + +@JsonIgnoreProperties(ignoreUnknown = true) +@JsonPropertyOrder({ + "reproductionSteps", + "environment", + "supportingMaterial" +}) +@JsonInclude(JsonInclude.Include.NON_EMPTY) +public class ProofOfConcept +{ + private String reproductionSteps; + + private String environment; + + private List supportingMaterial; + + public String getEnvironment() { + return environment; + } + + public void setEnvironment(final String environment) { + this.environment = environment; + } + + @JacksonXmlElementWrapper(localName = "supportingMaterial") + @JacksonXmlProperty(localName = "attachment") + @JsonProperty("supportingMaterial") + public List getSupportingMaterial() { + return supportingMaterial; + } + + public void setSupportingMaterial(final List supportingMaterial) { + this.supportingMaterial = supportingMaterial; + } + + public String getReproductionSteps() { + return reproductionSteps; + } + + public void setReproductionSteps(final String reproductionSteps) { + this.reproductionSteps = reproductionSteps; + } + + @Override + public boolean equals(final Object object) { + if (this == object) { + return true; + } + if (!(object instanceof ProofOfConcept)) { + return false; + } + ProofOfConcept that = (ProofOfConcept) object; + return Objects.equals(reproductionSteps, that.reproductionSteps) && + Objects.equals(environment, that.environment) && + Objects.equals(supportingMaterial, that.supportingMaterial); + } + + @Override + public int hashCode() { + return Objects.hash(reproductionSteps, environment, supportingMaterial); + } +} \ No newline at end of file diff --git a/src/main/java/org/cyclonedx/model/vulnerability/Vulnerability.java b/src/main/java/org/cyclonedx/model/vulnerability/Vulnerability.java index 13617daaa..3d7fe822e 100644 --- a/src/main/java/org/cyclonedx/model/vulnerability/Vulnerability.java +++ b/src/main/java/org/cyclonedx/model/vulnerability/Vulnerability.java @@ -47,6 +47,8 @@ "description", "detail", "recommendation", + "workaround", + "proofOfConcept", "advisories", "created", "published", @@ -74,6 +76,13 @@ public Vulnerability() {} private String description; private String detail; private String recommendation; + + @VersionFilter(org.cyclonedx.Version.VERSION_15) + private String workaround; + + @VersionFilter(org.cyclonedx.Version.VERSION_15) + private ProofOfConcept proofOfConcept; + private List advisories; @JsonSerialize(using = CustomDateSerializer.class) @VersionFilter(org.cyclonedx.Version.VERSION_14) @@ -273,6 +282,22 @@ public void setProperties(final List properties) { this.properties = properties; } + public String getWorkaround() { + return workaround; + } + + public void setWorkaround(final String workaround) { + this.workaround = workaround; + } + + public ProofOfConcept getProofOfConcept() { + return proofOfConcept; + } + + public void setProofOfConcept(final ProofOfConcept proofOfConcept) { + this.proofOfConcept = proofOfConcept; + } + @Override public boolean equals(Object o) { if (this == o) return true; @@ -296,31 +321,35 @@ public boolean equals(Object o) { Objects.equals(tools, rhs.tools) && Objects.equals(analysis, rhs.analysis) && Objects.equals(affects, rhs.affects) && + Objects.equals(workaround, rhs.workaround) && + Objects.equals(proofOfConcept, rhs.proofOfConcept) && Objects.equals(properties, rhs.properties); } @Override public int hashCode() { return Objects.hash( - bomRef, - id, - source, - references, - ratings, - cwes, - description, - detail, - recommendation, - advisories, - created, - published, - updated, - rejected, - credits, - tools, - analysis, - affects, - properties); + bomRef, + id, + source, + references, + ratings, + cwes, + description, + detail, + recommendation, + advisories, + created, + published, + updated, + rejected, + credits, + tools, + analysis, + affects, + workaround, + proofOfConcept, + properties); } @JsonInclude(JsonInclude.Include.NON_NULL) diff --git a/src/main/java/org/cyclonedx/util/deserializer/AttachmentTextDeserializer.java b/src/main/java/org/cyclonedx/util/deserializer/AttachmentTextDeserializer.java index 144941847..d2b0c0b27 100644 --- a/src/main/java/org/cyclonedx/util/deserializer/AttachmentTextDeserializer.java +++ b/src/main/java/org/cyclonedx/util/deserializer/AttachmentTextDeserializer.java @@ -31,6 +31,8 @@ public AttachmentText deserialize(JsonParser parser, DeserializationContext cont attachmentText.setText(contentNode.asText()); } else if (node.has("")) { attachmentText.setText(node.get("").asText()); + } else if (node.isTextual()) { + attachmentText.setText(node.textValue()); } JsonNode contentTypeNode = getContentTypeNode(node); diff --git a/src/main/java/org/cyclonedx/util/serializer/SignatorySerializer.java b/src/main/java/org/cyclonedx/util/serializer/SignatorySerializer.java index 544231d87..e3f6f2283 100644 --- a/src/main/java/org/cyclonedx/util/serializer/SignatorySerializer.java +++ b/src/main/java/org/cyclonedx/util/serializer/SignatorySerializer.java @@ -6,6 +6,7 @@ import com.fasterxml.jackson.databind.SerializerProvider; import com.fasterxml.jackson.databind.ser.std.StdSerializer; import com.fasterxml.jackson.dataformat.xml.ser.ToXmlGenerator; +import org.apache.commons.collections4.CollectionUtils; import org.apache.commons.lang3.StringUtils; import org.cyclonedx.model.attestation.affirmation.Signatory; @@ -34,29 +35,59 @@ public void serialize(Signatory value, JsonGenerator jsonGenerator, SerializerPr } } - private void serializeJson(final JsonGenerator gen, final Signatory signatory) + private void serializeXml(final ToXmlGenerator gen, final Signatory signatory, final SerializerProvider provider) throws IOException { - gen.writeStartObject(); + //It might have extensible types (signature) + if (CollectionUtils.isNotEmpty(signatory.getExtensibleTypes())) { + gen.writeStartObject(); - if (StringUtils.isNotBlank(signatory.getName())) { - gen.writeStringField("name", signatory.getName()); - } + if (StringUtils.isNotBlank(signatory.getName())) { + gen.writeStringField("name", signatory.getName()); + } + + if (StringUtils.isNotBlank(signatory.getRole())) { + gen.writeStringField("role", signatory.getRole()); + } - if (StringUtils.isNotBlank(signatory.getRole())) { - gen.writeStringField("role", signatory.getRole()); + new ExtensibleTypesSerializer().serialize(signatory.getExtensibleTypes(), gen, provider); + gen.writeEndObject(); } + } + + private void serializeJson(final JsonGenerator gen, final Signatory signatory) + throws IOException + { + boolean shouldSerialize = false; - if (signatory.getSignature() != null) { - gen.writeObjectField("signature", signatory.getSignature()); + if (signatory.getSignature() != null && !isXml) { + shouldSerialize = true; + } + else if (signatory.getExternalReference() != null && signatory.getOrganization() != null) { + shouldSerialize = true; } - else { - if (signatory.getExternalReference() != null && signatory.getOrganization() != null) { + + // Only serialize if the required values are set + if (shouldSerialize) { + gen.writeStartObject(); + + if (StringUtils.isNotBlank(signatory.getName())) { + gen.writeStringField("name", signatory.getName()); + } + + if (StringUtils.isNotBlank(signatory.getRole())) { + gen.writeStringField("role", signatory.getRole()); + } + + if (signatory.getSignature() != null) { + gen.writeObjectField("signature", signatory.getSignature()); + } + else if (signatory.getExternalReference() != null && signatory.getOrganization() != null) { gen.writeObjectField("organization", signatory.getOrganization()); gen.writeObjectField("externalReference", signatory.getExternalReference()); } + gen.writeEndObject(); } - gen.writeEndObject(); } @Override diff --git a/src/test/java/org/cyclonedx/BomJsonGeneratorTest.java b/src/test/java/org/cyclonedx/BomJsonGeneratorTest.java index 723c14092..ae1207108 100644 --- a/src/test/java/org/cyclonedx/BomJsonGeneratorTest.java +++ b/src/test/java/org/cyclonedx/BomJsonGeneratorTest.java @@ -290,6 +290,66 @@ public void schema16_testEvidence() throws Exception { assertTrue(parser.isValid(loadedFile, version)); } + @Test + public void schema16_testExpressions() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonXmlBom("/1.6/valid-license-expression-1.6.xml"); + + BomJsonGenerator generator = BomGeneratorFactory.createJson(version, bom); + File loadedFile = writeToFile(generator.toJsonString()); + + JsonParser parser = new JsonParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testAttestations() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonXmlBom("/1.6/valid-attestation-1.6.xml"); + + BomJsonGenerator generator = BomGeneratorFactory.createJson(version, bom); + File loadedFile = writeToFile(generator.toJsonString()); + + JsonParser parser = new JsonParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testAttestations_json() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonJsonBom("/1.6/valid-attestation-1.6.json"); + + BomJsonGenerator generator = BomGeneratorFactory.createJson(version, bom); + File loadedFile = writeToFile(generator.toJsonString()); + + JsonParser parser = new JsonParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testCompositions() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonXmlBom("/1.6/valid-compositions-1.6.xml"); + + BomJsonGenerator generator = BomGeneratorFactory.createJson(version, bom); + File loadedFile = writeToFile(generator.toJsonString()); + + JsonParser parser = new JsonParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testVulnerabilities() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonXmlBom("/1.6/valid-vulnerability-1.6.xml"); + + BomJsonGenerator generator = BomGeneratorFactory.createJson(version, bom); + File loadedFile = writeToFile(generator.toJsonString()); + + JsonParser parser = new JsonParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + @Test public void schema15_testEvidence() throws Exception { Version version = Version.VERSION_15; diff --git a/src/test/java/org/cyclonedx/BomXmlGeneratorTest.java b/src/test/java/org/cyclonedx/BomXmlGeneratorTest.java index 759486eff..3a4035239 100644 --- a/src/test/java/org/cyclonedx/BomXmlGeneratorTest.java +++ b/src/test/java/org/cyclonedx/BomXmlGeneratorTest.java @@ -24,6 +24,7 @@ import org.cyclonedx.generators.BomGeneratorFactory; import org.cyclonedx.generators.json.BomJsonGenerator; import org.cyclonedx.generators.xml.*; +import org.cyclonedx.model.Attribute; import org.cyclonedx.model.Bom; import org.cyclonedx.model.Component; import org.cyclonedx.model.ExtensibleType; @@ -411,6 +412,62 @@ public void schema16_testEvidence() throws Exception { assertTrue(parser.isValid(loadedFile, version)); } + @Test + public void schema16_testExpressions() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonJsonBom("/1.6/valid-license-expression-1.6.json"); + + BomXmlGenerator generator = BomGeneratorFactory.createXml(version, bom); + File loadedFile = writeToFile(generator.toXmlString()); + + XmlParser parser = new XmlParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testAttestations() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonJsonBom("/1.6/valid-attestation-1.6.json"); + + BomXmlGenerator generator = BomGeneratorFactory.createXml(version, bom); + File loadedFile = writeToFile(generator.toXmlString()); + + XmlParser parser = new XmlParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + @Test + public void schema16_testAttestations_xml() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonBomXml("/1.6/valid-attestation-1.6.xml"); + addSignature(bom); + + BomXmlGenerator generator = BomGeneratorFactory.createXml(version, bom); + File loadedFile = writeToFile(generator.toXmlString()); + + XmlParser parser = new XmlParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + + private void addSignature(Bom bom) { + List attributes = new ArrayList<>(); + attributes.add(new Attribute("xmlns", "http://www.w3.org/2000/09/xmldsig#")); + ExtensibleType signature = new ExtensibleType("ds", "Signature", attributes, ""); + bom.getDeclarations().getAffirmation().getSignatories().get(0).addExtensibleType(signature); + } + + @Test + public void schema16_testVulnerabilities() throws Exception { + Version version = Version.VERSION_16; + Bom bom = createCommonJsonBom("/1.6/valid-vulnerability-1.6.json"); + + BomXmlGenerator generator = BomGeneratorFactory.createXml(version, bom); + File loadedFile = writeToFile(generator.toXmlString()); + + XmlParser parser = new XmlParser(); + assertTrue(parser.isValid(loadedFile, version)); + } + @Test public void schema15_testEvidence() throws Exception { Version version = Version.VERSION_15;