@mitre/hdf-converters 3.0.1 → 3.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE.md +55 -0
- package/README.md +130 -92
- package/dist/detect.d.ts +28 -0
- package/dist/detect.d.ts.map +1 -0
- package/dist/detect.js +3 -0
- package/dist/index.d.ts +713 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +6988 -0
- package/dist/index.js.map +1 -0
- package/dist/register-all-DaYHszLd.js +945 -0
- package/dist/register-all-DaYHszLd.js.map +1 -0
- package/dist/registry.d.ts +38 -0
- package/dist/registry.d.ts.map +1 -0
- package/dist/registry.js +23 -0
- package/dist/registry.js.map +1 -0
- package/package.json +32 -32
- package/dist/converters/aws-config-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/aws-config-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/aws-config-to-hdf/typescript/converter.js +0 -132
- package/dist/converters/aws-config-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/aws-config-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/aws-config-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/aws-config-to-hdf/typescript/fingerprint.js +0 -32
- package/dist/converters/aws-config-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/aws-config-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/aws-config-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/aws-config-to-hdf/typescript/index.js +0 -2
- package/dist/converters/aws-config-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/converter.d.ts +0 -11
- package/dist/converters/burpsuite-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/converter.js +0 -169
- package/dist/converters/burpsuite-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/fingerprint.d.ts +0 -9
- package/dist/converters/burpsuite-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/fingerprint.js +0 -33
- package/dist/converters/burpsuite-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/burpsuite-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/burpsuite-to-hdf/typescript/index.js +0 -2
- package/dist/converters/burpsuite-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/conveyor-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/converter.js +0 -206
- package/dist/converters/conveyor-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/conveyor-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/fingerprint.js +0 -37
- package/dist/converters/conveyor-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/conveyor-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/conveyor-to-hdf/typescript/index.js +0 -2
- package/dist/converters/conveyor-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/converter.d.ts +0 -8
- package/dist/converters/cyclonedx-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/converter.js +0 -199
- package/dist/converters/cyclonedx-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/cyclonedx-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/fingerprint.js +0 -34
- package/dist/converters/cyclonedx-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/cyclonedx-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/cyclonedx-to-hdf/typescript/index.js +0 -2
- package/dist/converters/cyclonedx-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/converter.d.ts +0 -10
- package/dist/converters/dbprotect-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/converter.js +0 -171
- package/dist/converters/dbprotect-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/dbprotect-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/fingerprint.js +0 -35
- package/dist/converters/dbprotect-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/dbprotect-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/dbprotect-to-hdf/typescript/index.js +0 -2
- package/dist/converters/dbprotect-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/converter.d.ts +0 -8
- package/dist/converters/deptrack-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/converter.js +0 -120
- package/dist/converters/deptrack-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/deptrack-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/fingerprint.js +0 -46
- package/dist/converters/deptrack-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/deptrack-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/deptrack-to-hdf/typescript/index.js +0 -2
- package/dist/converters/deptrack-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/converter.d.ts +0 -12
- package/dist/converters/fortify-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/converter.js +0 -211
- package/dist/converters/fortify-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/fortify-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/fingerprint.js +0 -42
- package/dist/converters/fortify-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/fortify-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/fortify-to-hdf/typescript/index.js +0 -2
- package/dist/converters/fortify-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/gitlab-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/converter.js +0 -222
- package/dist/converters/gitlab-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/gitlab-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/fingerprint.js +0 -37
- package/dist/converters/gitlab-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/gitlab-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/gitlab-to-hdf/typescript/index.js +0 -2
- package/dist/converters/gitlab-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/converter.d.ts +0 -10
- package/dist/converters/gosec-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/converter.js +0 -126
- package/dist/converters/gosec-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/gosec-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/fingerprint.js +0 -32
- package/dist/converters/gosec-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/gosec-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/gosec-to-hdf/typescript/index.js +0 -2
- package/dist/converters/gosec-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/grype-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/converter.js +0 -222
- package/dist/converters/grype-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/grype-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/fingerprint.js +0 -38
- package/dist/converters/grype-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/grype-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/grype-to-hdf/typescript/index.js +0 -2
- package/dist/converters/grype-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/converter.d.ts +0 -7
- package/dist/converters/hdf-to-csv/typescript/converter.d.ts.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/converter.js +0 -108
- package/dist/converters/hdf-to-csv/typescript/converter.js.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/hdf-to-csv/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/fingerprint.js +0 -28
- package/dist/converters/hdf-to-csv/typescript/fingerprint.js.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/index.d.ts +0 -2
- package/dist/converters/hdf-to-csv/typescript/index.d.ts.map +0 -1
- package/dist/converters/hdf-to-csv/typescript/index.js +0 -2
- package/dist/converters/hdf-to-csv/typescript/index.js.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/converter.d.ts +0 -13
- package/dist/converters/hdf-to-oscal-poam/typescript/converter.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/converter.js +0 -156
- package/dist/converters/hdf-to-oscal-poam/typescript/converter.js.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/hdf-to-oscal-poam/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/fingerprint.js +0 -28
- package/dist/converters/hdf-to-oscal-poam/typescript/fingerprint.js.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/index.d.ts +0 -2
- package/dist/converters/hdf-to-oscal-poam/typescript/index.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-poam/typescript/index.js +0 -2
- package/dist/converters/hdf-to-oscal-poam/typescript/index.js.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/converter.d.ts +0 -22
- package/dist/converters/hdf-to-oscal-sar/typescript/converter.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/converter.js +0 -276
- package/dist/converters/hdf-to-oscal-sar/typescript/converter.js.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/hdf-to-oscal-sar/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/fingerprint.js +0 -28
- package/dist/converters/hdf-to-oscal-sar/typescript/fingerprint.js.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/index.d.ts +0 -2
- package/dist/converters/hdf-to-oscal-sar/typescript/index.d.ts.map +0 -1
- package/dist/converters/hdf-to-oscal-sar/typescript/index.js +0 -2
- package/dist/converters/hdf-to-oscal-sar/typescript/index.js.map +0 -1
- package/dist/converters/hdf-to-xccdf/typescript/converter.d.ts +0 -8
- package/dist/converters/hdf-to-xccdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/hdf-to-xccdf/typescript/converter.js +0 -186
- package/dist/converters/hdf-to-xccdf/typescript/converter.js.map +0 -1
- package/dist/converters/hdf-to-xccdf/typescript/index.d.ts +0 -2
- package/dist/converters/hdf-to-xccdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/hdf-to-xccdf/typescript/index.js +0 -2
- package/dist/converters/hdf-to-xccdf/typescript/index.js.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/converter.d.ts +0 -7
- package/dist/converters/hdf-to-xml/typescript/converter.d.ts.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/converter.js +0 -140
- package/dist/converters/hdf-to-xml/typescript/converter.js.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/hdf-to-xml/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/fingerprint.js +0 -28
- package/dist/converters/hdf-to-xml/typescript/fingerprint.js.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/index.d.ts +0 -2
- package/dist/converters/hdf-to-xml/typescript/index.d.ts.map +0 -1
- package/dist/converters/hdf-to-xml/typescript/index.js +0 -2
- package/dist/converters/hdf-to-xml/typescript/index.js.map +0 -1
- package/dist/converters/hdf-v2-passthrough/typescript/fingerprint.d.ts +0 -15
- package/dist/converters/hdf-v2-passthrough/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/hdf-v2-passthrough/typescript/fingerprint.js +0 -33
- package/dist/converters/hdf-v2-passthrough/typescript/fingerprint.js.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/ionchannel-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/converter.js +0 -150
- package/dist/converters/ionchannel-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/ionchannel-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/fingerprint.js +0 -41
- package/dist/converters/ionchannel-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/ionchannel-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/ionchannel-to-hdf/typescript/index.js +0 -2
- package/dist/converters/ionchannel-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/converter.d.ts +0 -8
- package/dist/converters/jfrog-xray-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/converter.js +0 -149
- package/dist/converters/jfrog-xray-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/jfrog-xray-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/fingerprint.js +0 -28
- package/dist/converters/jfrog-xray-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/jfrog-xray-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/jfrog-xray-to-hdf/typescript/index.js +0 -2
- package/dist/converters/jfrog-xray-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/converter.d.ts +0 -5
- package/dist/converters/junit-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/converter.js +0 -142
- package/dist/converters/junit-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/fingerprint.d.ts +0 -9
- package/dist/converters/junit-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/fingerprint.js +0 -28
- package/dist/converters/junit-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/junit-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/junit-to-hdf/typescript/index.js +0 -2
- package/dist/converters/junit-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/converter.d.ts +0 -232
- package/dist/converters/legacyhdf-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/converter.js +0 -418
- package/dist/converters/legacyhdf-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/fingerprint.d.ts +0 -17
- package/dist/converters/legacyhdf-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/fingerprint.js +0 -49
- package/dist/converters/legacyhdf-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/index.d.ts +0 -8
- package/dist/converters/legacyhdf-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/legacyhdf-to-hdf/typescript/index.js +0 -8
- package/dist/converters/legacyhdf-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/converter.d.ts +0 -8
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/converter.js +0 -153
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/fingerprint.js +0 -37
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/index.js +0 -2
- package/dist/converters/msft-defender-cloud-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/converter.d.ts +0 -7
- package/dist/converters/msft-defender-devops-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/converter.js +0 -126
- package/dist/converters/msft-defender-devops-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/fingerprint.d.ts +0 -13
- package/dist/converters/msft-defender-devops-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/fingerprint.js +0 -62
- package/dist/converters/msft-defender-devops-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/msft-defender-devops-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/msft-defender-devops-to-hdf/typescript/index.js +0 -2
- package/dist/converters/msft-defender-devops-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/converter.js +0 -194
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/fingerprint.js +0 -39
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/index.js +0 -2
- package/dist/converters/msft-defender-endpoint-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/converter.d.ts +0 -11
- package/dist/converters/msft-secure-score-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/converter.js +0 -160
- package/dist/converters/msft-secure-score-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/msft-secure-score-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/fingerprint.js +0 -41
- package/dist/converters/msft-secure-score-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/msft-secure-score-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/msft-secure-score-to-hdf/typescript/index.js +0 -2
- package/dist/converters/msft-secure-score-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/converter.d.ts +0 -6
- package/dist/converters/nessus-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/converter.js +0 -329
- package/dist/converters/nessus-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/fingerprint.d.ts +0 -9
- package/dist/converters/nessus-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/fingerprint.js +0 -34
- package/dist/converters/nessus-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/nessus-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/nessus-to-hdf/typescript/index.js +0 -2
- package/dist/converters/nessus-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/netsparker-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/converter.js +0 -211
- package/dist/converters/netsparker-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/netsparker-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/fingerprint.js +0 -29
- package/dist/converters/netsparker-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/netsparker-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/netsparker-to-hdf/typescript/index.js +0 -2
- package/dist/converters/netsparker-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/converter.d.ts +0 -16
- package/dist/converters/neuvector-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/converter.js +0 -148
- package/dist/converters/neuvector-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/neuvector-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/fingerprint.js +0 -37
- package/dist/converters/neuvector-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/neuvector-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/neuvector-to-hdf/typescript/index.js +0 -2
- package/dist/converters/neuvector-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/nikto-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/converter.js +0 -111
- package/dist/converters/nikto-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/nikto-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/fingerprint.js +0 -33
- package/dist/converters/nikto-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/nikto-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/nikto-to-hdf/typescript/index.js +0 -2
- package/dist/converters/nikto-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-catalog.d.ts +0 -20
- package/dist/converters/oscal-to-hdf/typescript/converter-catalog.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-catalog.js +0 -134
- package/dist/converters/oscal-to-hdf/typescript/converter-catalog.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-component.d.ts +0 -13
- package/dist/converters/oscal-to-hdf/typescript/converter-component.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-component.js +0 -92
- package/dist/converters/oscal-to-hdf/typescript/converter-component.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-poam.d.ts +0 -13
- package/dist/converters/oscal-to-hdf/typescript/converter-poam.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-poam.js +0 -196
- package/dist/converters/oscal-to-hdf/typescript/converter-poam.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-profile.d.ts +0 -26
- package/dist/converters/oscal-to-hdf/typescript/converter-profile.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-profile.js +0 -239
- package/dist/converters/oscal-to-hdf/typescript/converter-profile.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-sap.d.ts +0 -13
- package/dist/converters/oscal-to-hdf/typescript/converter-sap.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-sap.js +0 -196
- package/dist/converters/oscal-to-hdf/typescript/converter-sap.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-sar.d.ts +0 -13
- package/dist/converters/oscal-to-hdf/typescript/converter-sar.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-sar.js +0 -270
- package/dist/converters/oscal-to-hdf/typescript/converter-sar.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-ssp.d.ts +0 -13
- package/dist/converters/oscal-to-hdf/typescript/converter-ssp.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/converter-ssp.js +0 -246
- package/dist/converters/oscal-to-hdf/typescript/converter-ssp.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/detect.d.ts +0 -15
- package/dist/converters/oscal-to-hdf/typescript/detect.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/detect.js +0 -33
- package/dist/converters/oscal-to-hdf/typescript/detect.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/fingerprint.d.ts +0 -12
- package/dist/converters/oscal-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/fingerprint.js +0 -57
- package/dist/converters/oscal-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/index.d.ts +0 -9
- package/dist/converters/oscal-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/index.js +0 -9
- package/dist/converters/oscal-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/shared.d.ts +0 -85
- package/dist/converters/oscal-to-hdf/typescript/shared.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/shared.js +0 -251
- package/dist/converters/oscal-to-hdf/typescript/shared.js.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/types.d.ts +0 -5372
- package/dist/converters/oscal-to-hdf/typescript/types.d.ts.map +0 -1
- package/dist/converters/oscal-to-hdf/typescript/types.js +0 -2340
- package/dist/converters/oscal-to-hdf/typescript/types.js.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/converter.d.ts +0 -16
- package/dist/converters/prisma-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/converter.js +0 -197
- package/dist/converters/prisma-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/prisma-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/fingerprint.js +0 -39
- package/dist/converters/prisma-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/prisma-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/prisma-to-hdf/typescript/index.js +0 -2
- package/dist/converters/prisma-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/sarif-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/converter.js +0 -406
- package/dist/converters/sarif-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/sarif-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/fingerprint.js +0 -34
- package/dist/converters/sarif-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/sarif-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/sarif-to-hdf/typescript/index.js +0 -2
- package/dist/converters/sarif-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/scoutsuite-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/converter.js +0 -173
- package/dist/converters/scoutsuite-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/scoutsuite-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/fingerprint.js +0 -29
- package/dist/converters/scoutsuite-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/scoutsuite-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/scoutsuite-to-hdf/typescript/index.js +0 -2
- package/dist/converters/scoutsuite-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/converter.d.ts +0 -11
- package/dist/converters/snyk-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/converter.js +0 -131
- package/dist/converters/snyk-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/fingerprint.d.ts +0 -12
- package/dist/converters/snyk-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/fingerprint.js +0 -44
- package/dist/converters/snyk-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/snyk-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/snyk-to-hdf/typescript/index.js +0 -2
- package/dist/converters/snyk-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/converter.d.ts +0 -8
- package/dist/converters/sonarqube-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/converter.js +0 -266
- package/dist/converters/sonarqube-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/fingerprint.d.ts +0 -10
- package/dist/converters/sonarqube-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/fingerprint.js +0 -35
- package/dist/converters/sonarqube-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/sonarqube-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/sonarqube-to-hdf/typescript/index.js +0 -2
- package/dist/converters/sonarqube-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/converter.d.ts +0 -13
- package/dist/converters/splunk-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/converter.js +0 -165
- package/dist/converters/splunk-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/splunk-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/fingerprint.js +0 -36
- package/dist/converters/splunk-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/splunk-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/splunk-to-hdf/typescript/index.js +0 -2
- package/dist/converters/splunk-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/converter.d.ts +0 -9
- package/dist/converters/trufflehog-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/converter.js +0 -189
- package/dist/converters/trufflehog-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/fingerprint.d.ts +0 -18
- package/dist/converters/trufflehog-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/fingerprint.js +0 -50
- package/dist/converters/trufflehog-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/trufflehog-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/trufflehog-to-hdf/typescript/index.js +0 -2
- package/dist/converters/trufflehog-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/converter.d.ts +0 -11
- package/dist/converters/twistlock-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/converter.js +0 -153
- package/dist/converters/twistlock-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/fingerprint.d.ts +0 -18
- package/dist/converters/twistlock-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/fingerprint.js +0 -49
- package/dist/converters/twistlock-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/twistlock-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/twistlock-to-hdf/typescript/index.js +0 -2
- package/dist/converters/twistlock-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/converter.d.ts +0 -20
- package/dist/converters/veracode-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/converter.js +0 -350
- package/dist/converters/veracode-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/fingerprint.d.ts +0 -16
- package/dist/converters/veracode-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/fingerprint.js +0 -35
- package/dist/converters/veracode-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/veracode-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/veracode-to-hdf/typescript/index.js +0 -2
- package/dist/converters/veracode-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/converter.d.ts +0 -29
- package/dist/converters/xccdf-results-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/converter.js +0 -604
- package/dist/converters/xccdf-results-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/fingerprint.d.ts +0 -12
- package/dist/converters/xccdf-results-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/fingerprint.js +0 -33
- package/dist/converters/xccdf-results-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/xccdf-results-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/xccdf-results-to-hdf/typescript/index.js +0 -2
- package/dist/converters/xccdf-results-to-hdf/typescript/index.js.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/converter.d.ts +0 -2
- package/dist/converters/zap-to-hdf/typescript/converter.d.ts.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/converter.js +0 -237
- package/dist/converters/zap-to-hdf/typescript/converter.js.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/fingerprint.d.ts +0 -11
- package/dist/converters/zap-to-hdf/typescript/fingerprint.d.ts.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/fingerprint.js +0 -34
- package/dist/converters/zap-to-hdf/typescript/fingerprint.js.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/index.d.ts +0 -2
- package/dist/converters/zap-to-hdf/typescript/index.d.ts.map +0 -1
- package/dist/converters/zap-to-hdf/typescript/index.js +0 -2
- package/dist/converters/zap-to-hdf/typescript/index.js.map +0 -1
- package/dist/package.json +0 -71
- package/dist/shared/typescript/compare.d.ts +0 -14
- package/dist/shared/typescript/compare.d.ts.map +0 -1
- package/dist/shared/typescript/compare.js +0 -91
- package/dist/shared/typescript/compare.js.map +0 -1
- package/dist/shared/typescript/converter-contract.d.ts +0 -20
- package/dist/shared/typescript/converter-contract.d.ts.map +0 -1
- package/dist/shared/typescript/converter-contract.js +0 -35
- package/dist/shared/typescript/converter-contract.js.map +0 -1
- package/dist/shared/typescript/converterutil.d.ts +0 -158
- package/dist/shared/typescript/converterutil.d.ts.map +0 -1
- package/dist/shared/typescript/converterutil.js +0 -220
- package/dist/shared/typescript/converterutil.js.map +0 -1
- package/dist/shared/typescript/fingerprint.d.ts +0 -17
- package/dist/shared/typescript/fingerprint.d.ts.map +0 -1
- package/dist/shared/typescript/fingerprint.js +0 -85
- package/dist/shared/typescript/fingerprint.js.map +0 -1
- package/dist/shared/typescript/fptest.d.ts +0 -40
- package/dist/shared/typescript/fptest.d.ts.map +0 -1
- package/dist/shared/typescript/fptest.js +0 -70
- package/dist/shared/typescript/fptest.js.map +0 -1
- package/dist/shared/typescript/hdf-version.d.ts +0 -20
- package/dist/shared/typescript/hdf-version.d.ts.map +0 -1
- package/dist/shared/typescript/hdf-version.js +0 -206
- package/dist/shared/typescript/hdf-version.js.map +0 -1
- package/dist/shared/typescript/register-all.d.ts +0 -12
- package/dist/shared/typescript/register-all.d.ts.map +0 -1
- package/dist/shared/typescript/register-all.js +0 -111
- package/dist/shared/typescript/register-all.js.map +0 -1
- package/dist/shared/typescript/registry.d.ts +0 -35
- package/dist/shared/typescript/registry.d.ts.map +0 -1
- package/dist/shared/typescript/registry.js +0 -27
- package/dist/shared/typescript/registry.js.map +0 -1
- package/dist/shared/typescript/xml-utils.d.ts +0 -16
- package/dist/shared/typescript/xml-utils.d.ts.map +0 -1
- package/dist/shared/typescript/xml-utils.js +0 -66
- package/dist/shared/typescript/xml-utils.js.map +0 -1
- package/dist/src/detect.d.ts +0 -15
- package/dist/src/detect.d.ts.map +0 -1
- package/dist/src/detect.js +0 -15
- package/dist/src/detect.js.map +0 -1
- package/dist/src/index.d.ts +0 -52
- package/dist/src/index.d.ts.map +0 -1
- package/dist/src/index.js +0 -91
- package/dist/src/index.js.map +0 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":["DEFAULT_REMEDIATION_NIST_TAGS","impactToSeverity","IMPACT_MAPPING","extractSourceLocation","buildDescriptions","buildTags","CONVERTER_VERSION","ARRAY_TAGS","buildCodeDesc","extractVersion","buildRequirement","IMPACT_MAPPING","getImpact","buildCodeDesc","IMPACT_MAPPING","buildTags","buildResult","getStatus","TargetType","buildNistTags","buildCodeDesc","buildRequirement","IMPACT_MAPPING","buildRequirement","DEFAULT_REMEDIATION_NIST_TAGS","buildNistTags","buildCodeDesc","buildNistTags","buildCodeDesc","formatCodeDesc","mapStatus","wrap","buildCodeDesc","buildCodeDesc","buildRequirement","IMPACT_MAPPING","getImpact","formatCodeDesc","buildRequirement","IMPACT_MAPPING","getStatus","getImpact","formatDesc","buildRequirement","buildTitle","formatCodeDesc","buildRequirement","getImpact","getTitle","buildRequirement","extractCWEs","formatCodeDesc","buildRequirement","getImpact","buildRequirement","buildCodeDesc","buildRequirement","DEFAULT_STATIC_ANALYSIS_NIST_TAGS","getImpact","DEFAULT_REMEDIATION_NIST_TAGS","buildRequirement","IMPACT_MAPPING","getImpact","formatMessage","buildRequirement","getImpact","getStatus","buildRequirement","buildCodeDesc","IMPACT_MAPPING","DEFAULT_REMEDIATION_NIST_TAGS","buildRequirement","IMPACT_MAPPING","severityToImpact","buildTags","impactToSeverity","buildRiskMap"],"sources":["../shared/typescript/converterutil.ts","../converters/legacyhdf-to-hdf/typescript/converter.ts","../converters/sarif-to-hdf/typescript/converter.ts","../converters/junit-to-hdf/typescript/converter.ts","../converters/xccdf-results-to-hdf/typescript/converter.ts","../converters/snyk-to-hdf/typescript/converter.ts","../converters/grype-to-hdf/typescript/converter.ts","../converters/nessus-to-hdf/typescript/converter.ts","../converters/sonarqube-to-hdf/typescript/converter.ts","../converters/aws-config-to-hdf/typescript/converter.ts","../converters/gosec-to-hdf/typescript/converter.ts","../converters/nikto-to-hdf/typescript/converter.ts","../converters/zap-to-hdf/typescript/converter.ts","../converters/cyclonedx-to-hdf/typescript/converter.ts","../converters/hdf-to-csv/typescript/converter.ts","../converters/splunk-to-hdf/typescript/converter.ts","../converters/hdf-to-xml/typescript/converter.ts","../converters/gitlab-to-hdf/typescript/converter.ts","../converters/trufflehog-to-hdf/typescript/converter.ts","../converters/burpsuite-to-hdf/typescript/converter.ts","../converters/dbprotect-to-hdf/typescript/converter.ts","../converters/twistlock-to-hdf/typescript/converter.ts","../converters/deptrack-to-hdf/typescript/converter.ts","../converters/jfrog-xray-to-hdf/typescript/converter.ts","../converters/neuvector-to-hdf/typescript/converter.ts","../converters/fortify-to-hdf/typescript/converter.ts","../converters/prisma-to-hdf/typescript/converter.ts","../converters/netsparker-to-hdf/typescript/converter.ts","../converters/scoutsuite-to-hdf/typescript/converter.ts","../converters/conveyor-to-hdf/typescript/converter.ts","../converters/veracode-to-hdf/typescript/converter.ts","../converters/msft-secure-score-to-hdf/typescript/converter.ts","../converters/msft-defender-devops-to-hdf/typescript/converter.ts","../converters/msft-defender-cloud-to-hdf/typescript/converter.ts","../converters/msft-defender-endpoint-to-hdf/typescript/converter.ts","../converters/hdf-to-xccdf/typescript/converter.ts","../converters/oscal-to-hdf/typescript/shared.ts","../converters/hdf-to-oscal-sar/typescript/converter.ts","../converters/hdf-to-oscal-poam/typescript/converter.ts","../converters/ionchannel-to-hdf/typescript/converter.ts","../converters/oscal-to-hdf/typescript/detect.ts","../converters/oscal-to-hdf/typescript/converter-catalog.ts","../converters/oscal-to-hdf/typescript/converter-profile.ts","../converters/oscal-to-hdf/typescript/converter-component.ts","../converters/oscal-to-hdf/typescript/converter-ssp.ts","../converters/oscal-to-hdf/typescript/converter-sap.ts","../converters/oscal-to-hdf/typescript/converter-poam.ts","../converters/oscal-to-hdf/typescript/converter-sar.ts"],"sourcesContent":["/**\n * Shared utilities for TypeScript HDF converters.\n *\n * Provides common patterns used across all converter implementations:\n * - Input checksum computation\n * - Re-exports of shared constants and utilities\n */\n\nimport { sha256 } from '@mitre/hdf-utilities';\nimport type { Checksum, Component, EvaluatedBaseline, HdfResults, Integrity, Statistics } from '@mitre/hdf-schema';\nimport { HashAlgorithm } from '@mitre/hdf-schema';\nimport { getCweNistControl } from '@mitre/hdf-mappings';\n\n/**\n * Compute a SHA-256 checksum of raw converter input.\n *\n * Wraps the common 3-line pattern used in every converter into a single call.\n * The returned Checksum is suitable for the EvaluatedBaseline.resultsChecksum field.\n *\n * @param input - Raw input string (JSON, XML, etc.)\n * @returns Checksum with algorithm set to SHA-256\n */\nexport async function inputChecksum(input: string): Promise<Checksum> {\n return {\n algorithm: HashAlgorithm.Sha256,\n value: await sha256(input),\n };\n}\n\n/**\n * Compute an Integrity object (for root-level document integrity) from raw input.\n *\n * Returns an Integrity with algorithm and checksum fields, suitable for\n * HdfBaseline.integrity, HdfSystem.integrity, HdfPlan.integrity, etc.\n *\n * @param input - Raw input string (JSON, XML, etc.)\n * @returns Integrity object with SHA-256 algorithm and checksum\n */\nexport async function inputIntegrity(input: string): Promise<Integrity> {\n const checksum = await inputChecksum(input);\n return { algorithm: checksum.algorithm, checksum: checksum.value };\n}\n\n/**\n * Build a tags object with NIST controls and optional CCI mappings.\n *\n * If cci is empty, the \"cci\" key is omitted from the result.\n * Additional key-value pairs can be passed via extras.\n *\n * @param nist - NIST 800-53 control identifiers\n * @param cci - CCI identifiers (omitted if empty)\n * @param extras - Additional tag key-value pairs\n * @returns Tags object for HDF requirement\n */\nexport function buildNistCciTags(\n nist: string[],\n cci: string[],\n extras?: Record<string, unknown>,\n): Record<string, unknown> {\n const tags: Record<string, unknown> = { nist };\n if (cci.length > 0) {\n tags.cci = cci;\n }\n if (extras) {\n Object.assign(tags, extras);\n }\n return tags;\n}\n\n/** Maximum number of items processed from any single input array. */\nexport const DEFAULT_MAX_ITEMS = 100_000;\n\n/**\n * Limit an array to at most maxItems elements.\n *\n * Returns the (possibly truncated) array and a flag indicating whether\n * truncation occurred. When truncated, callers should log a warning.\n *\n * @param items - Array to limit\n * @param maxItems - Maximum items (defaults to DEFAULT_MAX_ITEMS)\n * @returns Object with limited items array and truncated flag\n */\nexport function limitArray<T>(\n items: T[],\n maxItems = DEFAULT_MAX_ITEMS,\n): { items: T[]; truncated: boolean } {\n if (items.length <= maxItems) {\n return { items, truncated: false };\n }\n return { items: items.slice(0, maxItems), truncated: true };\n}\n\n// Re-export stripHTML from @mitre/hdf-utilities (canonical location).\n// Named stripHTML (uppercase H) for backwards compatibility with existing\n// converter imports; hdf-utilities exports stripHtml (lowercase h).\nexport { stripHtml as stripHTML } from '@mitre/hdf-utilities';\n\n/**\n * Limit an array and log a warning if truncated.\n *\n * Wraps {@link limitArray} with a console.warn call when items are truncated.\n *\n * @param items - Array to limit\n * @param label - Item type label for warning message (e.g., \"vulnerability\")\n * @param maxItems - Maximum items (defaults to DEFAULT_MAX_ITEMS)\n * @returns Limited array (original if within limit)\n */\nexport function limitArrayWithWarning<T>(\n items: T[],\n label: string,\n maxItems = DEFAULT_MAX_ITEMS,\n): T[] {\n const { items: limited, truncated } = limitArray(items, maxItems);\n if (truncated) {\n // eslint-disable-next-line no-console -- Intentional warning for truncated input\n console.warn(`WARNING: Input truncated at ${limited.length} ${label} items (original: ${items.length})`);\n }\n return limited;\n}\n\n/**\n * Map CWE identifiers to NIST 800-53 controls.\n *\n * Looks up each CWE ID, deduplicates, sorts, and falls back to the provided\n * default when no CWE has a mapping. CWE IDs may optionally have a \"CWE-\"\n * prefix (e.g., \"CWE-79\" or \"79\").\n *\n * @param cweIDs - CWE identifiers (e.g., [\"CWE-79\", \"89\"])\n * @param fallback - Default NIST controls when no mapping is found\n * @returns Sorted, deduplicated NIST control identifiers\n */\nexport function mapCWEToNIST(\n cweIDs: string[],\n fallback: string[],\n): string[] {\n const controls = new Set<string>();\n for (const id of cweIDs) {\n const numericStr = id.replace(/^CWE-/i, '');\n const numericId = parseInt(numericStr, 10);\n if (!isNaN(numericId)) {\n const nistControl = getCweNistControl(numericId);\n if (nistControl) {\n controls.add(nistControl);\n }\n }\n }\n return controls.size > 0 ? [...controls].sort() : fallback;\n}\n\n/** Matches CWE identifiers like \"CWE-79\", \"CWE 89\", \"cwe22\". */\nconst CWE_PATTERN = /CWE[- ]?(\\d+)/gi;\n\n/**\n * Extract all numeric CWE IDs from text.\n * Returns deduplicated sorted array of numeric ID strings (e.g., [\"79\", \"89\"]).\n *\n * @param text - Text potentially containing CWE identifiers\n * @returns Sorted, deduplicated numeric CWE ID strings\n */\nexport function extractCWEIDs(text: string): string[] {\n const matches = [...text.matchAll(CWE_PATTERN)];\n if (matches.length === 0) return [];\n const ids = [...new Set(matches.map(m => m[1]!))];\n ids.sort();\n return ids;\n}\n\n/** Default maximum input size for converters (50MB) */\nexport const DEFAULT_MAX_INPUT_SIZE = 50 * 1024 * 1024;\n\n/**\n * Validates that input string doesn't exceed maximum allowed size.\n *\n * Note: string.length gives char count, not bytes. For multi-byte chars this\n * underestimates. This is acceptable as a coarse safety check — exact byte\n * counting would require TextEncoder.\n *\n * @param input - Raw input string to validate\n * @param converterName - Name of the converter (used in error message)\n * @param maxSize - Maximum allowed character count (defaults to DEFAULT_MAX_INPUT_SIZE)\n * @throws Error if input exceeds maxSize\n */\nexport function validateInputSize(\n input: string,\n converterName: string,\n maxSize = DEFAULT_MAX_INPUT_SIZE,\n): void {\n if (input.length > maxSize) {\n throw new Error(\n `${converterName}: input exceeds maximum allowed size of ${maxSize} characters`,\n );\n }\n}\n\n/**\n * Normalise a value that may be a single item, an array, undefined, or null\n * into a guaranteed array.\n *\n * XML-to-JSON parsers often produce a single object when there is one child\n * element and an array when there are multiple. This helper smooths that out.\n *\n * @param value - A single item, an array of items, undefined, or null\n * @returns An array (empty if the input was nullish)\n */\nexport function ensureArray<T>(value: T | T[] | undefined | null): T[] {\n if (value === undefined || value === null) return [];\n return Array.isArray(value) ? value : [value];\n}\n\n// Re-export shared constants for converter convenience\nexport { DEFAULT_STATIC_ANALYSIS_NIST_TAGS } from '@mitre/hdf-mappings';\n\n/**\n * Default NIST 800-53 fallback for tools that identify outdated packages or\n * flaws requiring patching (SI-2: Flaw Remediation, RA-5: Vulnerability\n * Monitoring and Scanning).\n *\n * Mirrors Go shared.DefaultRemediationNIST.\n */\nexport const DEFAULT_REMEDIATION_NIST_TAGS = ['SI-2', 'RA-5'];\n\n/**\n * Options for building an HDF Results document.\n * Mirrors the Go shared.HDFResultsOptions struct.\n */\nexport interface HdfResultsOptions {\n /** Name of the converter that produced this HDF file (e.g., 'grype-to-hdf') */\n generatorName: string;\n /** Version of the converter */\n converterVersion: string;\n /** Name of the source security tool (e.g., 'Grype', 'Nessus') */\n toolName?: string;\n /** Version of the source tool */\n toolVersion?: string;\n /** Output format of the source tool (e.g., 'SARIF', 'XCCDF') */\n toolFormat?: string;\n /** Evaluated baselines with findings */\n baselines: EvaluatedBaseline[];\n /** Components that were assessed */\n components?: Component[];\n /** When the assessment was executed */\n timestamp?: Date;\n /** Assessment statistics */\n statistics?: Statistics;\n}\n\n/**\n * Build an HDF Results document from options.\n *\n * Eliminates the repeated boilerplate of constructing generator, tool,\n * and assembling the top-level HdfResults in every converter. Mirrors\n * the Go shared.BuildHDFResults() function.\n *\n * @returns JSON string of the HDF Results document (pretty-printed)\n */\nexport function buildHdfResults(opts: HdfResultsOptions): string {\n const hdf: HdfResults = {\n baselines: opts.baselines,\n generator: {\n name: opts.generatorName,\n version: opts.converterVersion,\n },\n };\n\n if (opts.toolName || opts.toolVersion || opts.toolFormat) {\n hdf.tool = {};\n if (opts.toolName) hdf.tool.name = opts.toolName;\n if (opts.toolVersion) hdf.tool.version = opts.toolVersion;\n if (opts.toolFormat) hdf.tool.format = opts.toolFormat;\n }\n\n if (opts.components) hdf.components = opts.components;\n if (opts.timestamp) hdf.timestamp = opts.timestamp;\n if (opts.statistics) hdf.statistics = opts.statistics;\n\n return JSON.stringify(hdf, null, 2);\n}\n","/**\n * HDF v1.0 to v2.0 converter.\n *\n * Comprehensive transformations:\n * - Top-level: version removed, profiles → baselines, platform → components\n * - Baseline: sha256 → checksum, controls → requirements\n * - Control: source_location → sourceLocation, waiver_data → waiverData, status → effectiveStatus\n * - Results: snake_case → camelCase for all fields\n * - Overlay flattening: merge overlay/wrapper baselines so every requirement has results\n */\n\nimport { flattenOverlays } from '@mitre/hdf-parsers';\nimport type { HdfResults } from '@mitre/hdf-schema';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\n\n// ===== V1.0 Type Definitions =====\n\nexport interface V1Result {\n status: string;\n code_desc?: string;\n run_time?: number;\n start_time?: string;\n message?: string;\n exception?: string;\n backtrace?: unknown;\n resource_class?: string;\n resource_params?: string;\n resource_id?: string;\n skip_message?: string;\n [key: string]: unknown;\n}\n\nexport interface V1Control {\n id: string;\n title?: string;\n desc?: string;\n descriptions?: Array<{label: string; data: string}>;\n impact: number;\n refs?: unknown[];\n tags?: Record<string, unknown>;\n code?: string;\n source_location?: {\n ref?: string;\n line?: number;\n };\n waiver_data?: Record<string, unknown>;\n results?: V1Result[];\n status?: string; // overall_status in some v1.0 variants\n [key: string]: unknown;\n}\n\nexport interface V1Group {\n id: string;\n title?: string;\n controls: string[]; // Array of control IDs\n [key: string]: unknown;\n}\n\nexport interface V1Dependency {\n name?: string;\n url?: string;\n path?: string;\n git?: string;\n branch?: string;\n tag?: string;\n commit?: string;\n version?: string;\n supermarket?: string;\n compliance?: string;\n status?: string;\n skip_message?: string;\n [key: string]: unknown;\n}\n\nexport interface V1Profile {\n name: string;\n version?: string;\n title?: string;\n maintainer?: string;\n summary?: string;\n license?: string;\n copyright?: string;\n copyright_email?: string;\n supports?: unknown[];\n attributes?: unknown[];\n groups?: V1Group[];\n controls?: V1Control[];\n sha256?: string;\n depends?: V1Dependency[];\n parent_profile?: string;\n status?: string;\n status_message?: string;\n skip_message?: string;\n [key: string]: unknown;\n}\n\nexport interface V1Platform {\n name: string;\n release?: string;\n target_id?: string;\n [key: string]: unknown;\n}\n\nexport interface HDFV1Results {\n version: string;\n platform: V1Platform;\n profiles: V1Profile[];\n statistics: unknown;\n generator?: unknown;\n timestamp?: string;\n [key: string]: unknown;\n}\n\n// ===== V2.0 Type Definitions =====\n\nexport interface V2Result {\n status: string;\n codeDesc?: string;\n runTime?: number;\n startTime?: string;\n message?: string;\n exception?: string;\n backtrace?: unknown;\n resourceClass?: string;\n resourceParams?: string;\n resourceId?: string;\n skipMessage?: string;\n [key: string]: unknown;\n}\n\nexport interface V2Requirement {\n id: string;\n title?: string;\n desc?: string;\n descriptions?: Array<{label: string; data: string}>;\n impact: number;\n refs?: unknown[];\n tags?: Record<string, unknown>;\n code?: string;\n sourceLocation?: {\n ref?: string;\n line?: number;\n };\n waiverData?: Record<string, unknown>;\n results?: V2Result[];\n effectiveStatus?: string;\n [key: string]: unknown;\n}\n\nexport interface V2Group {\n id: string;\n title?: string;\n requirements: string[]; // Array of requirement IDs\n [key: string]: unknown;\n}\n\nexport interface V2Dependency {\n name?: string;\n url?: string;\n path?: string;\n git?: string;\n branch?: string;\n tag?: string;\n commit?: string;\n version?: string;\n supermarket?: string;\n compliance?: string;\n status?: string;\n skipMessage?: string;\n [key: string]: unknown;\n}\n\nexport interface V2Baseline {\n name: string;\n version?: string;\n title?: string;\n maintainer?: string;\n summary?: string;\n license?: string;\n copyright?: string;\n copyright_email?: string;\n supports?: unknown[];\n inputs?: unknown[];\n groups?: V2Group[];\n requirements?: V2Requirement[];\n checksum?: {\n algorithm: string;\n value: string;\n };\n depends?: V2Dependency[];\n parentBaseline?: string;\n status?: string;\n statusMessage?: string;\n skipMessage?: string;\n [key: string]: unknown;\n}\n\nexport interface HDFV2Results {\n baselines: V2Baseline[];\n statistics: unknown;\n components?: unknown[];\n generator?: unknown;\n tool?: { name?: string; version?: string; format?: string };\n timestamp?: string;\n id?: string;\n integrity?: unknown;\n runner?: unknown;\n remediation?: unknown;\n extensions?: Record<string, unknown>;\n}\n\n// ===== Severity Helpers =====\n\n/** Valid severity values per HDF v2.0 schema. */\nconst VALID_SEVERITIES = new Set(['critical', 'high', 'medium', 'low', 'informational', 'none']);\n\n/**\n * Convert tags.severity string to a valid severity value.\n * Returns null if the value is not a recognized severity.\n */\nfunction tagSeverityToSeverity(tagSeverity: unknown): string | null {\n if (typeof tagSeverity !== 'string') return null;\n const normalized = tagSeverity.toLowerCase().trim();\n return VALID_SEVERITIES.has(normalized) ? normalized : null;\n}\n\n/**\n * Derive severity from numeric impact score.\n * Follows InSpec conventions: 0.9+ critical, 0.7+ high, 0.5+ medium, >0 low, 0 none.\n */\nfunction impactToSeverity(impact: number): string {\n if (impact >= 0.9) return 'critical';\n if (impact >= 0.7) return 'high';\n if (impact >= 0.5) return 'medium';\n if (impact > 0) return 'low';\n return 'none';\n}\n\n// ===== Conversion Functions =====\n\n/**\n * Normalize status values from v1.0 to v2.0 format.\n * Converts snake_case to camelCase.\n */\nfunction normalizeStatus(status: string): string {\n const statusMap: Record<string, string> = {\n 'passed': 'passed',\n 'failed': 'failed',\n 'error': 'error',\n 'not_applicable': 'notApplicable',\n 'not_reviewed': 'notReviewed',\n 'skipped': 'notReviewed', // v1.0 skipped → v2.0 notReviewed\n };\n return statusMap[status] || 'notReviewed'; // unknown statuses default to notReviewed (matches Go)\n}\n\n/**\n * Compute effectiveStatus from impact and v2 results.\n * Implements InSpec enhanced outcomes precedence:\n * impact=0 → notApplicable\n * error > failed > passed > notApplicable > notReviewed\n *\n * See docs/design/status-determination.md for full specification.\n */\nfunction computeEffectiveStatus(impact: number, results: V2Result[]): string {\n if (impact === 0) return 'notApplicable';\n if (results.length === 0) return 'notReviewed';\n\n let hasFailed = false;\n let hasPassed = false;\n let hasNotApplicable = false;\n\n for (const r of results) {\n switch (r.status) {\n case 'error': return 'error'; // fail-fast: highest precedence\n case 'failed': hasFailed = true; break;\n case 'passed': hasPassed = true; break;\n case 'notApplicable': hasNotApplicable = true; break;\n }\n }\n\n if (hasFailed) return 'failed';\n if (hasPassed) return 'passed';\n if (hasNotApplicable) return 'notApplicable';\n return 'notReviewed';\n}\n\n/**\n * Convert v1.0 result to v2.0 result.\n * Transforms snake_case field names to camelCase.\n */\nfunction convertResult(v1Result: V1Result): V2Result {\n const v2Result: V2Result = {\n status: normalizeStatus(v1Result.status),\n };\n\n // Transform snake_case to camelCase\n if (v1Result.code_desc !== undefined) v2Result.codeDesc = v1Result.code_desc;\n if (v1Result.run_time !== undefined) v2Result.runTime = v1Result.run_time;\n if (v1Result.start_time !== undefined) v2Result.startTime = v1Result.start_time;\n if (v1Result.message !== undefined) v2Result.message = v1Result.message;\n if (v1Result.exception !== undefined) v2Result.exception = v1Result.exception;\n if (v1Result.backtrace !== undefined) v2Result.backtrace = v1Result.backtrace;\n if (v1Result.resource_class !== undefined) v2Result.resourceClass = v1Result.resource_class;\n if (v1Result.resource_params !== undefined) v2Result.resourceParams = v1Result.resource_params;\n if (v1Result.resource_id !== undefined) v2Result.resourceId = v1Result.resource_id;\n if (v1Result.skip_message !== undefined) v2Result.skipMessage = v1Result.skip_message;\n\n // Preserve any other fields\n const knownFields = new Set([\n 'status', 'code_desc', 'run_time', 'start_time', 'message', 'exception',\n 'backtrace', 'resource_class', 'resource_params', 'resource_id', 'skip_message'\n ]);\n for (const [key, value] of Object.entries(v1Result)) {\n if (!knownFields.has(key) && !(key in v2Result)) {\n v2Result[key] = value;\n }\n }\n\n return v2Result;\n}\n\n/**\n * Convert v1.0 control to v2.0 requirement.\n * Transforms field names and structure.\n */\nfunction convertControl(v1Control: V1Control): V2Requirement {\n const v2Req: V2Requirement = {\n id: v1Control.id,\n impact: v1Control.impact,\n };\n\n // Copy simple fields\n if (v1Control.title !== undefined) v2Req.title = v1Control.title;\n if (v1Control.desc !== undefined) v2Req.desc = v1Control.desc;\n if (v1Control.descriptions !== undefined) v2Req.descriptions = v1Control.descriptions;\n if (v1Control.refs !== undefined) v2Req.refs = v1Control.refs;\n if (v1Control.tags !== undefined) v2Req.tags = v1Control.tags;\n if (v1Control.code !== undefined) v2Req.code = v1Control.code;\n\n // Transform snake_case to camelCase\n if (v1Control.source_location !== undefined) {\n v2Req.sourceLocation = v1Control.source_location;\n }\n if (v1Control.waiver_data !== undefined) {\n v2Req.waiverData = v1Control.waiver_data;\n }\n\n // Transform status to effectiveStatus with normalization\n if (v1Control.status !== undefined) {\n v2Req.effectiveStatus = normalizeStatus(v1Control.status);\n }\n\n // Transform results array\n if (v1Control.results && Array.isArray(v1Control.results)) {\n v2Req.results = v1Control.results.map(convertResult);\n }\n\n // Always compute effectiveStatus when not explicitly set.\n // Uses InSpec enhanced outcomes precedence:\n // impact=0 → notApplicable, error > failed > passed > notApplicable > notReviewed\n if (!v2Req.effectiveStatus) {\n v2Req.effectiveStatus = computeEffectiveStatus(v1Control.impact, v2Req.results ?? []);\n }\n\n // Populate severity: prefer tags.severity (preserves original STIG severity),\n // fall back to impact-derived. InSpec sets impact=0 for NA controls, losing\n // the original severity — tags.severity preserves it.\n v2Req.severity = tagSeverityToSeverity(v1Control.tags?.severity) ?? impactToSeverity(v1Control.impact);\n\n // Preserve any other fields\n const knownFields = new Set([\n 'id', 'title', 'desc', 'descriptions', 'impact', 'refs', 'tags', 'code',\n 'source_location', 'waiver_data', 'results', 'status'\n ]);\n for (const [key, value] of Object.entries(v1Control)) {\n if (!knownFields.has(key) && !(key in v2Req)) {\n v2Req[key] = value;\n }\n }\n\n return v2Req;\n}\n\n/**\n * Convert v1.0 group to v2.0 group.\n * Renames controls array to requirements.\n */\nfunction convertGroup(v1Group: V1Group): V2Group {\n const v2Group: V2Group = {\n id: v1Group.id,\n requirements: v1Group.controls, // Rename controls to requirements\n };\n\n if (v1Group.title !== undefined) {\n v2Group.title = v1Group.title;\n }\n\n // Preserve any other fields\n const knownFields = new Set(['id', 'title', 'controls']);\n for (const [key, value] of Object.entries(v1Group)) {\n if (!knownFields.has(key) && !(key in v2Group)) {\n v2Group[key] = value;\n }\n }\n\n return v2Group;\n}\n\n/**\n * Convert v1.0 dependency to v2.0 dependency.\n * Transforms snake_case to camelCase for skip_message.\n */\nfunction convertDependency(v1Dep: V1Dependency): V2Dependency {\n const v2Dep: V2Dependency = {};\n\n // Copy most fields as-is\n if (v1Dep.name !== undefined) v2Dep.name = v1Dep.name;\n if (v1Dep.url !== undefined) v2Dep.url = v1Dep.url;\n if (v1Dep.path !== undefined) v2Dep.path = v1Dep.path;\n if (v1Dep.git !== undefined) v2Dep.git = v1Dep.git;\n if (v1Dep.branch !== undefined) v2Dep.branch = v1Dep.branch;\n if (v1Dep.tag !== undefined) v2Dep.tag = v1Dep.tag;\n if (v1Dep.commit !== undefined) v2Dep.commit = v1Dep.commit;\n if (v1Dep.version !== undefined) v2Dep.version = v1Dep.version;\n if (v1Dep.supermarket !== undefined) v2Dep.supermarket = v1Dep.supermarket;\n if (v1Dep.compliance !== undefined) v2Dep.compliance = v1Dep.compliance;\n if (v1Dep.status !== undefined) v2Dep.status = v1Dep.status;\n\n // Transform snake_case to camelCase\n if (v1Dep.skip_message !== undefined) {\n v2Dep.skipMessage = v1Dep.skip_message;\n }\n\n // Preserve any other fields\n const knownFields = new Set([\n 'name', 'url', 'path', 'git', 'branch', 'tag', 'commit', 'version',\n 'supermarket', 'compliance', 'status', 'skip_message'\n ]);\n for (const [key, value] of Object.entries(v1Dep)) {\n if (!knownFields.has(key) && !(key in v2Dep)) {\n v2Dep[key] = value;\n }\n }\n\n return v2Dep;\n}\n\n/**\n * Convert v1.0 profile to v2.0 baseline.\n * Transforms field names and nested structures.\n */\nfunction convertProfile(v1Profile: V1Profile): V2Baseline {\n const v2Baseline: V2Baseline = {\n name: v1Profile.name,\n };\n\n // Copy simple fields\n if (v1Profile.version !== undefined) v2Baseline.version = v1Profile.version;\n if (v1Profile.title !== undefined) v2Baseline.title = v1Profile.title;\n if (v1Profile.maintainer !== undefined) v2Baseline.maintainer = v1Profile.maintainer;\n if (v1Profile.summary !== undefined) v2Baseline.summary = v1Profile.summary;\n if (v1Profile.license !== undefined) v2Baseline.license = v1Profile.license;\n if (v1Profile.copyright !== undefined) v2Baseline.copyright = v1Profile.copyright;\n if (v1Profile.copyright_email !== undefined) v2Baseline.copyright_email = v1Profile.copyright_email;\n if (v1Profile.supports !== undefined) v2Baseline.supports = v1Profile.supports;\n if (v1Profile.attributes !== undefined) v2Baseline.inputs = v1Profile.attributes;\n if (v1Profile.status !== undefined) v2Baseline.status = v1Profile.status;\n\n // Transform sha256 to integrity object\n if (v1Profile.sha256) {\n v2Baseline.integrity = {\n algorithm: 'sha256',\n checksum: v1Profile.sha256,\n };\n }\n\n // Transform snake_case to camelCase\n if (v1Profile.parent_profile !== undefined) {\n v2Baseline.parentBaseline = v1Profile.parent_profile;\n }\n if (v1Profile.status_message !== undefined) {\n v2Baseline.statusMessage = v1Profile.status_message;\n }\n if (v1Profile.skip_message !== undefined) {\n v2Baseline.skipMessage = v1Profile.skip_message;\n }\n\n // Transform groups (controls → requirements)\n if (v1Profile.groups && Array.isArray(v1Profile.groups)) {\n v2Baseline.groups = v1Profile.groups.map(convertGroup);\n }\n\n // Transform controls to requirements\n if (v1Profile.controls && Array.isArray(v1Profile.controls)) {\n v2Baseline.requirements = v1Profile.controls.map(convertControl);\n }\n\n // Transform depends\n if (v1Profile.depends && Array.isArray(v1Profile.depends)) {\n v2Baseline.depends = v1Profile.depends.map(convertDependency);\n }\n\n // Preserve any other fields\n const knownFields = new Set([\n 'name', 'version', 'title', 'maintainer', 'summary', 'license', 'copyright',\n 'copyright_email', 'supports', 'attributes', 'groups', 'controls', 'sha256',\n 'depends', 'parent_profile', 'status', 'status_message', 'skip_message'\n ]);\n for (const [key, value] of Object.entries(v1Profile)) {\n if (!knownFields.has(key) && !(key in v2Baseline)) {\n v2Baseline[key] = value;\n }\n }\n\n return v2Baseline;\n}\n\n/**\n * Convert HDF v1.0 results to v2.0 format.\n *\n * Performs comprehensive transformation at all levels:\n * - Top-level: version removed, profiles → baselines, platform → components\n * - Baselines: sha256 → checksum, controls → requirements, field renaming\n * - Requirements: snake_case → camelCase, status → effectiveStatus\n * - Results: snake_case → camelCase for all fields\n *\n * @param v1Data - HDF v1.0 results object\n * @returns HDF v2.0 results object\n *\n * @example\n * ```typescript\n * const v1 = {\n * version: \"1.0.0\",\n * platform: { name: \"ubuntu\", release: \"20.04\" },\n * profiles: [...],\n * statistics: {...}\n * };\n * const v2 = convertV1ToV2(v1);\n * // v2 = { baselines: [...], components: [{...}], statistics: {...} }\n * ```\n */\nexport function convertV1ToV2(v1Data: HDFV1Results): HDFV2Results {\n validateInputSize(JSON.stringify(v1Data), 'legacyhdf-to-hdf');\n const v2: HDFV2Results = {\n baselines: (v1Data.profiles || []).map(convertProfile),\n statistics: v1Data.statistics || {},\n };\n\n // Transform platform to components array\n if (v1Data.platform) {\n v2.components = [\n {\n type: 'host', // v2.0 uses 'host' instead of 'system'\n id: v1Data.platform.target_id || v1Data.platform.name,\n name: v1Data.platform.name,\n ...(v1Data.platform.release && { release: v1Data.platform.release }),\n labels: {},\n },\n ];\n }\n\n // Copy optional fields\n if (v1Data.generator) {\n v2.generator = v1Data.generator;\n }\n\n v2.tool = { name: 'Heimdall Data Format v1' };\n\n if (v1Data.timestamp) {\n v2.timestamp = v1Data.timestamp;\n }\n\n // Preserve any extension fields not part of core schema\n const knownV1Fields = new Set(['version', 'platform', 'profiles', 'statistics', 'generator', 'timestamp']);\n const extensionFields: Record<string, unknown> = {};\n\n for (const [key, value] of Object.entries(v1Data)) {\n if (!knownV1Fields.has(key)) {\n extensionFields[key] = value;\n }\n }\n\n if (Object.keys(extensionFields).length > 0) {\n v2.extensions = {\n ...extensionFields,\n v1_version: v1Data.version, // Preserve original version for tracking\n };\n }\n\n // Flatten overlays: merge overlay/wrapper baselines so every requirement\n // has results and consumers don't see duplicated controls (741→247 fix).\n const flat = flattenOverlays(v2 as unknown as HdfResults);\n return flat.results as unknown as HDFV2Results;\n}\n\n/**\n * Validate that data appears to be HDF v1.0 format.\n *\n * @param data - Unknown data to validate\n * @returns true if data looks like HDF v1.0\n */\nexport function isHDFV1(data: unknown): data is HDFV1Results {\n if (typeof data !== 'object' || data === null) {\n return false;\n }\n\n const obj = data as Record<string, unknown>;\n\n // V1.0 has version field, profiles, and platform\n return (\n typeof obj.version === 'string' &&\n Array.isArray(obj.profiles) &&\n typeof obj.platform === 'object' &&\n obj.platform !== null\n );\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, mapCWEToNIST, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type { EvaluatedBaseline, EvaluatedRequirement, RequirementResult, Checksum, Description } from '@mitre/hdf-schema';\nimport { ResultStatus, createMinimalBaseline, createRequirement, createDescription, createResult } from '@mitre/hdf-schema';\n\n// --- SARIF 2.1.0 type definitions ---\n\ninterface SarifFile {\n $schema?: string;\n version: string;\n runs: SarifRun[];\n}\n\ninterface SarifRun {\n tool?: {\n driver?: SarifDriver;\n };\n results: SarifResult[];\n taxonomies?: SarifTaxonomy[];\n}\n\ninterface SarifDriver {\n name?: string;\n version?: string;\n informationUri?: string;\n rules?: ReportingDescriptor[];\n}\n\ninterface ReportingDescriptor {\n id: string;\n name?: string;\n shortDescription?: MultiformatMessage;\n fullDescription?: MultiformatMessage;\n helpUri?: string;\n help?: MultiformatMessage;\n defaultConfiguration?: ReportingConfiguration;\n relationships?: ReportingDescriptorRelation[];\n properties?: Record<string, unknown>;\n messageStrings?: Record<string, MultiformatMessage>;\n}\n\ninterface MultiformatMessage {\n text: string;\n markdown?: string;\n}\n\ninterface ReportingConfiguration {\n level?: string;\n}\n\ninterface ReportingDescriptorRelation {\n target: DescriptorReference;\n kinds?: string[];\n}\n\ninterface DescriptorReference {\n id: string;\n guid?: string;\n toolComponent?: ToolComponentReference;\n}\n\ninterface ToolComponentReference {\n name: string;\n guid?: string;\n}\n\ninterface SarifTaxonomy {\n name: string;\n version?: string;\n organization?: string;\n taxa?: ReportingDescriptor[];\n}\n\ninterface SarifResult {\n ruleId: string;\n ruleIndex?: number;\n kind?: string;\n level?: string;\n message: {\n text?: string;\n id?: string;\n arguments?: string[];\n };\n locations?: SarifLocation[];\n relatedLocations?: SarifLocation[];\n suppressions?: Suppression[];\n fixes?: Fix[];\n codeFlows?: CodeFlow[];\n fingerprints?: Record<string, string>;\n partialFingerprints?: Record<string, string>;\n}\n\ninterface Suppression {\n kind: string;\n status?: string;\n justification?: string;\n}\n\ninterface Fix {\n description?: {\n text: string;\n };\n}\n\ninterface CodeFlow {\n threadFlows: ThreadFlow[];\n}\n\ninterface ThreadFlow {\n locations: ThreadFlowLocation[];\n}\n\ninterface ThreadFlowLocation {\n location: SarifLocation;\n importance?: string;\n}\n\ninterface SarifLocation {\n id?: number;\n physicalLocation?: {\n artifactLocation?: {\n uri?: string;\n };\n region?: {\n startLine?: number;\n startColumn?: number;\n endLine?: number;\n endColumn?: number;\n snippet?: {\n text: string;\n };\n };\n };\n message?: {\n text: string;\n };\n}\n\n// --- Impact mapping ---\n\nconst IMPACT_MAPPING: Record<string, number> = {\n error: 0.7,\n warning: 0.5,\n note: 0.3,\n};\n\n// --- Conversion entry point ---\n\nexport async function convertSarifToHdf(input: string): Promise<string> {\n validateInputSize(input, 'sarif');\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const sarif = parseJSON<SarifFile>(input);\n\n if (!sarif || typeof sarif !== 'object') {\n throw new Error('Invalid SARIF structure: not a valid JSON object');\n }\n\n if (!Array.isArray(sarif.runs)) {\n throw new Error('Invalid SARIF structure: missing or invalid runs field');\n }\n\n const firstDriver = sarif.runs[0]?.tool?.driver;\n\n const { items: limitedRuns, truncated: truncatedRuns } = limitArray(sarif.runs);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedRuns) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedRuns.length} run items (original: ${sarif.runs.length})`);\n }\n\n return buildHdfResults({\n generatorName: 'sarif-to-hdf',\n converterVersion: '1.0.0',\n toolName: firstDriver?.name,\n toolVersion: firstDriver?.version,\n toolFormat: 'SARIF',\n baselines: limitedRuns.map(run => convertRun(run, sarif.version, resultsChecksum)),\n components: [],\n timestamp: new Date(),\n });\n}\n\n// --- Run-level conversion ---\n\nfunction convertRun(run: SarifRun, version: string, resultsChecksum: Checksum): EvaluatedBaseline {\n const ruleMap = buildRuleMap(run);\n\n // Group SARIF results by ruleId — each group becomes one EvaluatedRequirement.\n // When ruleId is absent, fall back to message text as the grouping key.\n const { items: limitedResults, truncated: truncatedResults } = limitArray(run.results);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedResults) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedResults.length} result items (original: ${run.results.length})`);\n }\n const groupOrder: string[] = [];\n const groupMap = new Map<string, { rule?: ReportingDescriptor; results: SarifResult[] }>();\n for (const result of limitedResults) {\n const groupKey = result.ruleId || resolveMessageText(result.message, undefined);\n let group = groupMap.get(groupKey);\n if (!group) {\n const rule = ruleMap.get(result.ruleId);\n group = { rule, results: [] };\n groupMap.set(groupKey, group);\n groupOrder.push(groupKey);\n }\n group.results.push(result);\n }\n\n const requirements = groupOrder.map(ruleId => {\n const group = groupMap.get(ruleId)!;\n return convertResultGroup(ruleId, group.rule, group.results);\n });\n\n // Use tool name for baseline name if available\n const baselineName = run.tool?.driver?.name || 'SARIF';\n\n return createMinimalBaseline(baselineName, requirements, {\n version,\n title: 'Static Analysis Results Interchange Format',\n resultsChecksum,\n });\n}\n\nfunction buildRuleMap(run: SarifRun): Map<string, ReportingDescriptor> {\n const map = new Map<string, ReportingDescriptor>();\n if (run.tool?.driver?.rules) {\n for (const rule of run.tool.driver.rules) {\n map.set(rule.id, rule);\n }\n }\n return map;\n}\n\n// --- Result-group conversion (one EvaluatedRequirement per ruleId) ---\n\nfunction convertResultGroup(ruleId: string, rule: ReportingDescriptor | undefined, sarifResults: SarifResult[]): EvaluatedRequirement {\n const firstResult = sarifResults[0]!;\n\n // Derive requirement-level metadata from the rule and first result\n const { title, description } = deriveMetadata(firstResult, rule);\n\n // Extract CWE IDs from rule (or first result message as fallback)\n let cweIds = extractCweFromRule(rule);\n if (cweIds.length === 0) {\n cweIds = extractCweIds(resolveMessageText(firstResult.message, rule));\n }\n\n const nistControls = mapCWEToNIST(cweIds, DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n const cciControls = nistToCci(nistControls);\n\n // Determine requirement-level impact from the rule's inherent severity\n const ruleLevel = resolveRuleLevel(rule, sarifResults);\n const impact = IMPACT_MAPPING[ruleLevel] || 0.1;\n\n // Source location from first result's first location\n const sourceLocation = firstResult.locations && firstResult.locations.length > 0\n ? extractSourceLocation(firstResult.locations[0]!)\n : undefined;\n\n // Convert each SARIF result into RequirementResult(s)\n const results: RequirementResult[] = [];\n for (const sr of sarifResults) {\n results.push(...convertSarifResultToHDFResults(sr));\n }\n\n // Build descriptions from rule metadata and first result\n const descriptions = buildDescriptions(description, rule, firstResult);\n\n // Build tags\n const tags = buildTags(firstResult, rule, ruleLevel, cweIds, nistControls, cciControls);\n\n const options: {\n sourceLocation?: { ref: string; line: number };\n tags: Record<string, unknown>;\n } = { tags };\n\n if (sourceLocation) {\n options.sourceLocation = sourceLocation;\n }\n\n return createRequirement(ruleId, title, descriptions, impact, results, options);\n}\n\n// Determines the inherent severity level for a rule, independent of per-result kind overrides.\nfunction resolveRuleLevel(rule: ReportingDescriptor | undefined, results: SarifResult[]): string {\n if (rule?.defaultConfiguration?.level) {\n return rule.defaultConfiguration.level;\n }\n // Find first result that represents a failure with an explicit level\n for (const r of results) {\n if (!r.kind || r.kind === 'fail') {\n if (r.level) {\n return r.level;\n }\n }\n }\n return 'warning';\n}\n\n// Converts a single SARIF result into one or more HDF RequirementResults.\nfunction convertSarifResultToHDFResults(result: SarifResult): RequirementResult[] {\n // Map kind to HDF status\n let status = mapKindToStatus(result.kind);\n\n // Handle suppressions\n let suppressionJustification = '';\n if (status === ResultStatus.Failed || status === ResultStatus.Passed) {\n const suppResult = applySuppression(result.suppressions);\n if (suppResult.suppressed) {\n status = ResultStatus.NotReviewed;\n suppressionJustification = suppResult.justification;\n }\n }\n\n // Build backtrace from code flows\n const backtrace = extractBacktrace(result.codeFlows);\n\n // Create results for each location\n const results = (result.locations || [])\n .filter(loc => loc.physicalLocation?.artifactLocation?.uri)\n .map(loc => createHDFResult(loc, status, backtrace, suppressionJustification));\n\n // If no locations, create a location-less result so the finding isn't silently dropped\n if (results.length === 0) {\n const locationlessResult: RequirementResult = {\n status,\n codeDesc: 'No source location',\n startTime: new Date(),\n backtrace,\n };\n if (suppressionJustification) {\n locationlessResult.message = `Suppressed: ${suppressionJustification}`;\n }\n results.push(locationlessResult);\n }\n\n return results;\n}\n\n// --- Message resolution ---\n\nfunction resolveMessageText(msg: SarifResult['message'], rule?: ReportingDescriptor): string {\n if (msg?.text) {\n return msg.text;\n }\n if (msg?.id && rule) {\n const tmpl = rule.messageStrings?.[msg.id];\n if (tmpl) {\n let text = tmpl.text;\n for (const [i, arg] of (msg.arguments ?? []).entries()) {\n text = text.split(`{${i}}`).join(arg);\n }\n return text;\n }\n }\n return '';\n}\n\n// --- Metadata derivation ---\n\nfunction deriveMetadata(result: SarifResult, rule?: ReportingDescriptor): { title: string; description: string } {\n const messageText = resolveMessageText(result.message, rule);\n if (rule?.name) {\n return { title: rule.name, description: messageText };\n }\n if (rule?.shortDescription?.text) {\n return { title: rule.shortDescription.text, description: messageText };\n }\n return parseMessage(messageText);\n}\n\nfunction parseMessage(text: string): { title: string; description: string } {\n const colonIndex = (text ?? '').indexOf(':');\n if (colonIndex === -1) {\n return { title: text, description: '' };\n }\n return {\n title: text.substring(0, colonIndex).trim(),\n description: text.substring(colonIndex + 1).trim(),\n };\n}\n\n// --- CWE extraction with priority ---\n\nfunction extractCweFromRule(rule?: ReportingDescriptor): string[] {\n if (!rule) {\n return [];\n }\n\n // Priority 1: rule.relationships where toolComponent.name == \"CWE\"\n if (rule.relationships) {\n const cweIds: string[] = [];\n for (const rel of rule.relationships) {\n if (rel.target.toolComponent?.name?.toLowerCase() === 'cwe') {\n const id = rel.target.id.startsWith('CWE-') ? rel.target.id : `CWE-${rel.target.id}`;\n cweIds.push(id);\n }\n }\n if (cweIds.length > 0) {\n return cweIds;\n }\n }\n\n // Priority 2: rule.properties.tags containing CWE-\\d+ patterns\n if (rule.properties?.tags && Array.isArray(rule.properties.tags)) {\n const cweTagPattern = /^CWE-\\d+$/;\n const cweIds: string[] = [];\n for (const tag of rule.properties.tags as string[]) {\n if (typeof tag === 'string' && cweTagPattern.test(tag)) {\n cweIds.push(tag);\n }\n }\n if (cweIds.length > 0) {\n return cweIds;\n }\n }\n\n return [];\n}\n\nfunction extractCweIds(text: string): string[] {\n const cwePattern = /\\(([^)]+)\\)/g;\n const matches = text.match(cwePattern);\n\n if (!matches) {\n return [];\n }\n\n const cweIds: string[] = [];\n for (const match of matches) {\n const content = match.slice(1, -1);\n if (content.includes('CWE-')) {\n const parts = content.split(/,\\s*|!\\//);\n for (const part of parts) {\n const trimmed = part.trim();\n if (trimmed.startsWith('CWE-')) {\n cweIds.push(trimmed);\n }\n }\n }\n }\n\n return cweIds;\n}\n\n// --- Kind → Status mapping ---\n\nfunction mapKindToStatus(kind?: string): ResultStatus {\n switch (kind) {\n case 'pass':\n return ResultStatus.Passed;\n case 'open':\n return ResultStatus.Failed;\n case 'review':\n return ResultStatus.NotReviewed;\n case 'informational':\n return ResultStatus.NotApplicable;\n case 'notApplicable':\n return ResultStatus.NotApplicable;\n default: // \"fail\" or undefined\n return ResultStatus.Failed;\n }\n}\n\n// --- Suppression handling ---\n\nfunction applySuppression(suppressions?: Suppression[]): { suppressed: boolean; justification: string } {\n if (!suppressions || suppressions.length === 0) {\n return { suppressed: false, justification: '' };\n }\n\n const justifications: string[] = [];\n let hasSuppression = false;\n\n for (const s of suppressions) {\n if (s.status === 'rejected') {\n continue;\n }\n hasSuppression = true;\n if (s.justification) {\n justifications.push(s.justification);\n }\n }\n\n if (!hasSuppression) {\n return { suppressed: false, justification: '' };\n }\n\n return { suppressed: true, justification: justifications.join('; ') };\n}\n\n// --- Code flow → backtrace ---\n\nfunction extractBacktrace(codeFlows?: CodeFlow[]): string[] {\n if (!codeFlows || codeFlows.length === 0) {\n return [];\n }\n\n const backtrace: string[] = [];\n for (const cf of codeFlows) {\n for (const tf of cf.threadFlows) {\n for (const tfl of tf.locations) {\n const loc = tfl.location;\n const uri = loc.physicalLocation?.artifactLocation?.uri || '';\n const line = loc.physicalLocation?.region?.startLine || 0;\n const msg = loc.message?.text || '';\n\n let entry = `${uri}:${line}`;\n if (msg) {\n entry = `${uri}:${line} - ${msg}`;\n }\n backtrace.push(entry);\n }\n }\n }\n\n return backtrace;\n}\n\n// --- Description building ---\n\nfunction buildDescriptions(defaultDesc: string, rule: ReportingDescriptor | undefined, result: SarifResult): Description[] {\n const descriptions: Description[] = [\n createDescription('default', defaultDesc),\n ];\n\n if (rule) {\n if (rule.fullDescription?.text) {\n descriptions.push(createDescription('rationale', rule.fullDescription.text));\n } else if (rule.shortDescription?.text && !defaultDesc) {\n descriptions[0] = createDescription('default', rule.shortDescription.text);\n }\n\n if (rule.help?.text) {\n descriptions.push(createDescription('check', rule.help.text));\n }\n }\n\n if (result.fixes && result.fixes.length > 0 && result.fixes[0]?.description?.text) {\n descriptions.push(createDescription('fix', result.fixes[0].description.text));\n }\n\n return descriptions;\n}\n\n// --- Tag building ---\n\nfunction buildTags(\n result: SarifResult,\n rule: ReportingDescriptor | undefined,\n resolvedLevel: string,\n cweIds: string[],\n nistControls: string[],\n cciControls: string[]\n): Record<string, unknown> {\n const tags: Record<string, unknown> = {\n severity: resolvedLevel,\n cwe: cweIds,\n nist: nistControls,\n cci: cciControls,\n };\n\n if (result.kind) {\n tags.kind = result.kind;\n }\n\n if (rule?.helpUri) {\n tags.helpUri = rule.helpUri;\n }\n\n if (result.suppressions && result.suppressions.length > 0) {\n tags.suppressions = result.suppressions.map(s => {\n const entry: Record<string, string> = { kind: s.kind };\n if (s.status) {\n entry.status = s.status;\n }\n if (s.justification) {\n entry.justification = s.justification;\n }\n return entry;\n });\n }\n\n if ((result.fingerprints && Object.keys(result.fingerprints).length > 0) ||\n (result.partialFingerprints && Object.keys(result.partialFingerprints).length > 0)) {\n const fp: Record<string, unknown> = {};\n if (result.fingerprints && Object.keys(result.fingerprints).length > 0) {\n fp.fingerprints = result.fingerprints;\n }\n if (result.partialFingerprints && Object.keys(result.partialFingerprints).length > 0) {\n fp.partialFingerprints = result.partialFingerprints;\n }\n tags.fingerprints = fp;\n }\n\n return tags;\n}\n\n// --- Location helpers ---\n\nfunction extractSourceLocation(location: SarifLocation): { ref: string; line: number } | undefined {\n const uri = location.physicalLocation?.artifactLocation?.uri;\n const line = location.physicalLocation?.region?.startLine;\n\n if (!uri || !line) {\n return undefined;\n }\n\n return { ref: uri, line };\n}\n\nfunction createHDFResult(\n location: SarifLocation,\n status: ResultStatus,\n backtrace: string[],\n suppressionMessage?: string\n): RequirementResult {\n const uri = location.physicalLocation?.artifactLocation?.uri || '';\n const line = location.physicalLocation?.region?.startLine || 0;\n const column = location.physicalLocation?.region?.startColumn || 0;\n const snippet = location.physicalLocation?.region?.snippet?.text;\n\n let codeDesc = `URL : ${uri} LINE : ${line} COLUMN : ${column}`;\n if (snippet) {\n codeDesc = `${codeDesc}\\n${snippet}`;\n }\n\n const message = suppressionMessage ? `Suppressed: ${suppressionMessage}` : '';\n\n return createResult(\n status,\n message,\n {\n codeDesc,\n startTime: new Date(),\n backtrace,\n }\n );\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport { inputChecksum, limitArray, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n Copyright,\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n// JUnit XML parsed types (from fast-xml-parser via parseXmlWithArrays)\n\ninterface JUnitTestSuites {\n testsuites?: {\n name?: string;\n testsuite?: JUnitTestSuite[];\n };\n testsuite?: JUnitTestSuite;\n}\n\ninterface JUnitTestSuite {\n name?: string;\n tests?: number;\n failures?: number;\n errors?: number;\n skipped?: number;\n time?: string;\n timestamp?: string;\n hostname?: string;\n testcase?: JUnitTestCase[];\n}\n\ninterface JUnitTestCase {\n classname?: string;\n name: string;\n time?: string;\n failure?: JUnitFailure;\n error?: JUnitError;\n skipped?: JUnitSkipped | '';\n}\n\ninterface JUnitFailure {\n message?: string;\n type?: string;\n '#text'?: string;\n}\n\ninterface JUnitError {\n message?: string;\n type?: string;\n '#text'?: string;\n}\n\ninterface JUnitSkipped {\n message?: string;\n}\n\nconst DEFAULT_NIST = ['SA-11'];\nconst CONVERTER_VERSION = '1.0.0';\n\n// Tags to always parse as arrays (even when single element)\nconst ARRAY_TAGS = ['testsuite', 'testcase'];\n\n/**\n * Converts JUnit XML test results to HDF format.\n */\nexport async function convertJunitToHdf(input: string): Promise<string> {\n if (!input || !input.trim()) {\n throw new Error('Empty input');\n }\n validateInputSize(input, 'junit');\n\n const { suites, name } = parseJUnitXML(input);\n const requirements = buildRequirements(suites);\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const baseline = createMinimalBaseline(name, requirements, {\n resultsChecksum,\n }) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'hdf-converters',\n converterVersion: CONVERTER_VERSION,\n toolName: 'JUnit XML',\n toolFormat: 'XML',\n baselines: [baseline],\n components: [{\n type: Copyright.Application,\n name,\n }],\n timestamp: new Date(),\n });\n}\n\nfunction parseJUnitXML(input: string): { suites: JUnitTestSuite[]; name: string } {\n const parsed = parseXmlWithArrays(input, ARRAY_TAGS) as JUnitTestSuites;\n\n // <testsuites> root\n if (parsed.testsuites) {\n const suites = parsed.testsuites.testsuite ?? [];\n const name = parsed.testsuites.name || 'JUnit Test Results';\n return { suites, name };\n }\n\n // <testsuite> root\n if (parsed.testsuite) {\n const suite = parsed.testsuite;\n // When testsuite is root, parseXmlWithArrays may return it directly\n // (not wrapped in an array since ARRAY_TAGS only forces arrays for child elements)\n const suites = Array.isArray(suite) ? (suite as JUnitTestSuite[]) : [suite];\n const name = suites[0]?.name || 'JUnit Test Results';\n return { suites, name };\n }\n\n throw new Error('Input is not a JUnit XML document: expected <testsuites> or <testsuite> root element');\n}\n\nfunction buildRequirements(suites: JUnitTestSuite[]): EvaluatedRequirement[] {\n const { items: limitedSuites, truncated: truncatedSuites } = limitArray(suites);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedSuites) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedSuites.length} test suite items (original: ${suites.length})`);\n }\n const requirements: EvaluatedRequirement[] = [];\n\n for (const suite of limitedSuites) {\n const testcases = suite.testcase ?? [];\n const { items: limitedTestCases, truncated: truncatedTC } = limitArray(testcases);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedTC) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedTestCases.length} test case items (original: ${testcases.length})`);\n }\n for (const tc of limitedTestCases) {\n requirements.push(testCaseToRequirement(tc, suite.timestamp));\n }\n }\n\n return requirements;\n}\n\nfunction testCaseToRequirement(\n tc: JUnitTestCase,\n suiteTimestamp?: string\n): EvaluatedRequirement {\n const id = buildID(tc);\n const { status, message } = resolveStatus(tc);\n const codeDesc = buildCodeDesc(tc);\n\n const resultOptions: Record<string, unknown> = { codeDesc };\n if (tc.time) {\n const parsed = parseFloat(tc.time);\n if (!isNaN(parsed)) {\n resultOptions.runTime = parsed;\n }\n }\n if (suiteTimestamp) {\n resultOptions.startTime = suiteTimestamp;\n }\n\n const result = createResult(status, message ?? '', resultOptions) as RequirementResult;\n\n const descriptions: Description[] = [\n {\n label: 'default',\n data: `JUnit test: ${tc.name} in ${tc.classname || 'unknown'}`,\n },\n ];\n\n return createRequirement(id, tc.name, descriptions, 0.5, [result], {\n tags: { nist: DEFAULT_NIST },\n }) as EvaluatedRequirement;\n}\n\nfunction buildID(tc: JUnitTestCase): string {\n if (tc.classname) {\n return `${tc.classname}.${tc.name}`;\n }\n return tc.name;\n}\n\nfunction resolveStatus(tc: JUnitTestCase): { status: ResultStatus; message?: string } {\n if (tc.failure) {\n const msg = buildFailureMessage(\n tc.failure.message ?? '',\n tc.failure.type ?? '',\n tc.failure['#text'] ?? ''\n );\n return { status: ResultStatus.Failed, message: msg };\n }\n if (tc.error) {\n const msg = buildFailureMessage(\n tc.error.message ?? '',\n tc.error.type ?? '',\n tc.error['#text'] ?? ''\n );\n return { status: ResultStatus.Error, message: msg };\n }\n if (tc.skipped !== undefined) {\n const skipped = typeof tc.skipped === 'object' ? tc.skipped : null;\n if (skipped?.message) {\n return { status: ResultStatus.NotReviewed, message: `Skipped: ${skipped.message}` };\n }\n return { status: ResultStatus.NotReviewed, message: 'Skipped' };\n }\n return { status: ResultStatus.Passed };\n}\n\nfunction buildFailureMessage(message: string, typeName: string, body: string): string {\n let result = '';\n if (typeName) {\n result = `${typeName}: `;\n }\n result += message;\n if (body) {\n result += '\\n' + body;\n }\n return result;\n}\n\nfunction buildCodeDesc(tc: JUnitTestCase): string {\n if (tc.classname) {\n return `${tc.classname} :: ${tc.name}`;\n }\n return tc.name;\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport { inputChecksum, inputIntegrity, limitArray, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n HdfBaseline,\n BaselineRequirement,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Description,\n RequirementGroup,\n Component,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n Severity,\n createMinimalBaseline,\n createRequirement,\n createResult,\n severityToImpact,\n} from '@mitre/hdf-schema';\nimport { getCCINistMappings } from '@mitre/hdf-mappings';\n\n// ---------------------------------------------------------------------------\n// Parsed XCCDF types (post-fast-xml-parser with removeNSPrefix)\n// ---------------------------------------------------------------------------\n\ninterface XccdfBenchmark {\n Benchmark?: BenchmarkElement;\n}\n\ninterface BenchmarkElement {\n id?: string;\n title?: string | TextElement;\n description?: string | TextElement;\n version?: string | VersionElement;\n Group?: GroupElement[];\n Rule?: RuleElement[];\n Profile?: ProfileElement[];\n TestResult?: TestResultElement;\n 'plain-text'?: PlainText | PlainText[];\n}\n\ninterface TextElement {\n '#text'?: string;\n}\n\ninterface VersionElement {\n '#text'?: string;\n update?: string;\n}\n\ninterface PlainText {\n '#text'?: string;\n id?: string;\n}\n\ninterface ProfileElement {\n id?: string;\n title?: string | TextElement;\n}\n\ninterface GroupElement {\n id?: string;\n title?: string | TextElement;\n Rule?: RuleElement[];\n}\n\ninterface RuleElement {\n id?: string;\n severity?: string;\n title?: string | TextElement;\n description?: string | TextElement;\n version?: string | VersionElement;\n fixtext?: string | FixtextElement;\n ident?: IdentElement[];\n check?: CheckElement;\n}\n\ninterface CheckElement {\n system?: string;\n 'check-content'?: string | TextElement;\n}\n\ninterface FixtextElement {\n '#text'?: string;\n fixref?: string;\n}\n\ninterface IdentElement {\n '#text'?: string;\n system?: string;\n}\n\ninterface TestResultElement {\n id?: string;\n 'start-time'?: string;\n 'end-time'?: string;\n title?: string | TextElement;\n target?: string;\n 'target-address'?: string[];\n 'rule-result'?: RuleResultElement[];\n}\n\ninterface RuleResultElement {\n idref?: string;\n time?: string;\n severity?: string;\n version?: string;\n result?: string;\n ident?: IdentElement[];\n}\n\n// ---------------------------------------------------------------------------\n// Parsed ARF types (post-fast-xml-parser with removeNSPrefix)\n// ---------------------------------------------------------------------------\n\ninterface ArfParsed {\n 'asset-report-collection'?: ArfCollectionElement;\n}\n\ninterface ArfCollectionElement {\n relationships?: {\n relationship?: ArfRelationshipElement[];\n };\n 'report-requests'?: {\n 'report-request'?: ArfReportRequestElement[];\n };\n assets?: {\n asset?: ArfAssetElement[];\n };\n reports?: {\n report?: ArfReportElement[];\n };\n}\n\ninterface ArfRelationshipElement {\n type?: string;\n subject?: string;\n ref?: string[];\n}\n\ninterface ArfReportRequestElement {\n id?: string;\n content?: {\n 'data-stream-collection'?: {\n component?: ArfComponentElement[];\n 'data-stream'?: unknown[];\n };\n };\n}\n\ninterface ArfComponentElement {\n id?: string;\n Benchmark?: BenchmarkElement;\n}\n\ninterface ArfAssetElement {\n id?: string;\n 'computing-device'?: {\n connections?: {\n connection?: ArfConnectionElement[];\n };\n fqdn?: string;\n hostname?: string;\n };\n}\n\ninterface ArfConnectionElement {\n 'ip-address'?: {\n 'ip-v4'?: string;\n 'ip-v6'?: string;\n };\n 'mac-address'?: string;\n}\n\ninterface ArfReportElement {\n id?: string;\n content?: {\n TestResult?: TestResultElement;\n };\n}\n\n// ---------------------------------------------------------------------------\n// Constants\n// ---------------------------------------------------------------------------\n\nconst CONVERTER_VERSION = '1.0.0';\n\nconst CCI_SYSTEM = 'http://cyber.mil/cci';\n\n/** Tags that must always be parsed as arrays even if only one element exists. */\nconst ARRAY_TAGS = [\n 'Group',\n 'Rule',\n 'Profile',\n 'rule-result',\n 'ident',\n 'select',\n 'set-value',\n 'target-address',\n 'platform',\n 'check-content',\n // ARF-specific array tags\n 'report',\n 'report-request',\n 'asset',\n 'connection',\n 'relationship',\n 'ref',\n 'component',\n 'data-stream',\n];\n\n/** Map XCCDF result values to HDF ResultStatus. */\nconst STATUS_MAP: Record<string, ResultStatus> = {\n pass: ResultStatus.Passed,\n fail: ResultStatus.Failed,\n error: ResultStatus.Error,\n unknown: ResultStatus.Error,\n notapplicable: ResultStatus.NotApplicable,\n notchecked: ResultStatus.NotReviewed,\n notselected: ResultStatus.NotReviewed,\n informational: ResultStatus.NotReviewed,\n fixed: ResultStatus.Passed,\n};\n\n// ---------------------------------------------------------------------------\n// Public API\n// ---------------------------------------------------------------------------\n\n/**\n * Converts an XCCDF results document (1.1 or 1.2) or ARF 1.1 XML to HDF Results JSON.\n * The input must contain TestResult elements.\n * For benchmark-only documents (no TestResult), use convertXccdfBenchmarkToHdf.\n *\n * @param input - Raw XML string (XCCDF Benchmark with TestResult, or ARF asset-report-collection)\n * @returns Stringified HDF Results JSON\n */\nexport async function convertXccdfResultsToHdf(input: string): Promise<string> {\n if (!input || !input.trim()) {\n throw new Error('Empty input');\n }\n validateInputSize(input, 'xccdf-results');\n\n const parsed = parseXmlWithArrays(input, ARRAY_TAGS);\n\n // Detect input format: ARF or raw XCCDF\n const arfParsed = parsed as ArfParsed;\n if (arfParsed['asset-report-collection']) {\n return convertArfCollection(arfParsed['asset-report-collection'], input);\n }\n\n const xccdfParsed = parsed as XccdfBenchmark;\n const benchmark = xccdfParsed.Benchmark;\n if (!benchmark) {\n throw new Error(\n 'Input is not an XCCDF document: expected <Benchmark> root element'\n );\n }\n\n if (!benchmark.TestResult) {\n throw new Error(\n \"Input has no TestResult elements — this is a benchmark. Use 'xccdf-benchmark' or 'xccdf' instead\"\n );\n }\n\n return convertBenchmarkResultsToHdf(benchmark, input);\n}\n\n/**\n * Converts an XCCDF benchmark document (no TestResult) to HDF Baseline JSON.\n * Supports both XCCDF 1.1 and 1.2 (namespace-agnostic via fast-xml-parser).\n *\n * @param input - Raw XML string (XCCDF Benchmark without TestResult)\n * @returns Stringified HDF Baseline JSON\n */\nexport async function convertXccdfBenchmarkToHdf(input: string): Promise<string> {\n if (!input || !input.trim()) {\n throw new Error('Empty input');\n }\n validateInputSize(input, 'xccdf-benchmark');\n\n const parsed = parseXmlWithArrays(input, ARRAY_TAGS);\n const xccdfParsed = parsed as XccdfBenchmark;\n const benchmark = xccdfParsed.Benchmark;\n\n if (!benchmark) {\n throw new Error(\n 'Input is not an XCCDF Benchmark document'\n );\n }\n\n if (benchmark.TestResult) {\n throw new Error(\n \"Input contains TestResult elements — this is a results document, not a benchmark. Use 'xccdf-results' or 'xccdf' instead\"\n );\n }\n\n return convertBenchmarkToBaselineJson(benchmark, input);\n}\n\n/**\n * Auto-detects whether the input is an XCCDF benchmark, results, or ARF\n * document and returns the appropriate JSON output.\n *\n * @param input - Raw XML string\n * @returns Object with json output and outputType ('baseline' or 'results')\n */\nexport async function convertXccdfToHdf(input: string): Promise<{ json: string; outputType: 'baseline' | 'results' }> {\n if (!input || !input.trim()) {\n throw new Error('Empty input');\n }\n validateInputSize(input, 'xccdf');\n\n const parsed = parseXmlWithArrays(input, ARRAY_TAGS);\n\n // Check ARF first\n const arfParsed = parsed as ArfParsed;\n if (arfParsed['asset-report-collection']) {\n const json = await convertArfCollection(arfParsed['asset-report-collection'], input);\n return { json, outputType: 'results' };\n }\n\n // Check XCCDF Benchmark\n const xccdfParsed = parsed as XccdfBenchmark;\n const benchmark = xccdfParsed.Benchmark;\n if (!benchmark) {\n throw new Error(\n 'Input is not an XCCDF or ARF document'\n );\n }\n\n if (benchmark.TestResult) {\n const json = await convertBenchmarkResultsToHdf(benchmark, input);\n return { json, outputType: 'results' };\n }\n\n const json = await convertBenchmarkToBaselineJson(benchmark, input);\n return { json, outputType: 'baseline' };\n}\n\n// ---------------------------------------------------------------------------\n// XCCDF Benchmark results conversion (existing path)\n// ---------------------------------------------------------------------------\n\nasync function convertBenchmarkResultsToHdf(\n benchmark: BenchmarkElement,\n rawInput: string\n): Promise<string> {\n const testResult = benchmark.TestResult!;\n\n const ruleIndex = buildRuleIndex(benchmark);\n\n const ruleResults = testResult['rule-result'] ?? [];\n const { items: limitedRuleResults, truncated: truncatedRR } = limitArray(ruleResults);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedRR) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedRuleResults.length} rule-result items (original: ${ruleResults.length})`);\n }\n const requirements = limitedRuleResults.map((rr) =>\n ruleResultToRequirement(rr, ruleIndex)\n );\n\n const resultsChecksum: Checksum = await inputChecksum(rawInput);\n\n const baselineName = extractText(benchmark.title) || 'XCCDF Benchmark';\n\n const baseline = createMinimalBaseline(\n baselineName,\n requirements,\n { resultsChecksum }\n ) as EvaluatedBaseline;\n\n const components = buildTargets(testResult);\n\n const timestamp = testResult['start-time']\n ? new Date(testResult['start-time'])\n : new Date();\n\n let durationSeconds: number | undefined;\n if (testResult['start-time'] && testResult['end-time']) {\n const start = new Date(testResult['start-time']).getTime();\n const end = new Date(testResult['end-time']).getTime();\n if (!isNaN(start) && !isNaN(end) && end >= start) {\n durationSeconds = (end - start) / 1000;\n }\n }\n\n const hdf: HdfResults = {\n baselines: [baseline],\n generator: { name: 'hdf-converters', version: CONVERTER_VERSION },\n tool: { name: 'XCCDF Results', format: 'XML' },\n components,\n timestamp,\n };\n\n if (durationSeconds !== undefined) {\n hdf.statistics = { duration: durationSeconds };\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n\n// ---------------------------------------------------------------------------\n// Benchmark-to-Baseline conversion\n// ---------------------------------------------------------------------------\n\nasync function convertBenchmarkToBaselineJson(\n benchmark: BenchmarkElement,\n rawInput: string\n): Promise<string> {\n const integrity = await inputIntegrity(rawInput);\n\n const requirements: BaselineRequirement[] = [];\n const groups: RequirementGroup[] = [];\n\n const benchmarkGroups = benchmark.Group ?? [];\n for (const group of benchmarkGroups) {\n const groupRules = group.Rule ?? [];\n for (const rule of groupRules) {\n if (!rule.id) {\n continue;\n }\n const req = ruleToBaselineRequirement(rule, group);\n requirements.push(req);\n groups.push({\n id: group.id ?? '',\n title: extractText(group.title),\n requirements: [req.id],\n });\n }\n }\n\n const topRules = benchmark.Rule ?? [];\n for (const rule of topRules) {\n if (!rule.id) {\n continue;\n }\n const req = ruleToBaselineRequirement(rule, undefined);\n requirements.push(req);\n }\n\n const baselineName = kebabCase(benchmark.id ?? 'xccdf-benchmark');\n\n const baseline: HdfBaseline = {\n name: baselineName,\n title: extractText(benchmark.title),\n version: extractVersion(benchmark.version),\n status: 'loaded',\n summary: extractText(benchmark.description),\n integrity,\n requirements,\n groups,\n generator: { name: 'hdf-converters', version: CONVERTER_VERSION },\n };\n\n return JSON.stringify(baseline, null, 2);\n}\n\n/**\n * Convert a single XCCDF Rule to an HDF BaselineRequirement.\n */\nfunction ruleToBaselineRequirement(\n rule: RuleElement,\n group: GroupElement | undefined\n): BaselineRequirement {\n const id = extractVersion(rule.version) || rule.id || '';\n const title = extractText(rule.title) || id;\n const severity = rule.severity ?? '';\n const impact = severity ? severityToImpact(severity) : 0.5;\n\n const descriptions: Description[] = [];\n const rawDesc = extractText(rule.description);\n if (rawDesc) {\n descriptions.push({\n label: 'default',\n data: extractVulnDiscussion(rawDesc),\n });\n } else {\n descriptions.push({ label: 'default', data: '' });\n }\n\n const checkContent = extractCheckContent(rule.check);\n if (checkContent) {\n descriptions.push({ label: 'check', data: checkContent });\n }\n\n const fixtext = extractFixtext(rule.fixtext);\n if (fixtext) {\n descriptions.push({ label: 'fix', data: fixtext });\n }\n\n const tags: Record<string, unknown> = {};\n const cciIds = extractCCIs(rule.ident ?? []);\n if (cciIds.length > 0) {\n tags['cci'] = cciIds;\n const nistTags = cciIds.flatMap(\n (cci) => getCCINistMappings(cci) ?? []\n );\n if (nistTags.length > 0) {\n tags['nist'] = [...new Set(nistTags)];\n }\n }\n\n // STIG-specific tags\n tags['rid'] = rule.id;\n tags['stig_id'] = extractVersion(rule.version);\n if (severity) {\n tags['severity'] = severity.toLowerCase();\n }\n if (rule.check?.system) {\n tags['check_id'] = rule.check.system;\n }\n const fixtextObj = rule.fixtext;\n if (fixtextObj && typeof fixtextObj !== 'string' && fixtextObj.fixref) {\n tags['fix_id'] = fixtextObj.fixref;\n }\n if (group) {\n tags['gid'] = group.id;\n tags['gtitle'] = extractText(group.title);\n }\n\n const req: BaselineRequirement = {\n id,\n title,\n impact,\n descriptions,\n tags,\n };\n\n if (severity) {\n req.severity = severity.toLowerCase() as Severity;\n }\n\n return req;\n}\n\n// ---------------------------------------------------------------------------\n// ARF conversion\n// ---------------------------------------------------------------------------\n\nasync function convertArfCollection(\n arc: ArfCollectionElement,\n rawInput: string\n): Promise<string> {\n const resultsChecksum: Checksum = await inputChecksum(rawInput);\n\n // Find the Benchmark from data-stream-collection components\n const benchmark = findBenchmarkInArf(arc);\n\n // Build rule index from Benchmark\n const ruleIndex = benchmark\n ? buildRuleIndex(benchmark)\n : new Map<string, RuleElement>();\n\n // Build asset metadata map: asset ID -> asset element\n const assetMap = new Map<string, ArfAssetElement>();\n for (const asset of arc.assets?.asset ?? []) {\n if (asset.id) {\n assetMap.set(asset.id, asset);\n }\n }\n\n // Build relationship map: report ID -> asset IDs (isAbout)\n const reportToAssets = new Map<string, string[]>();\n for (const rel of arc.relationships?.relationship ?? []) {\n if (rel.type?.includes('isAbout') && rel.subject) {\n reportToAssets.set(rel.subject, rel.ref ?? []);\n }\n }\n\n // Process each report\n const baselines: EvaluatedBaseline[] = [];\n const components: Component[] = [];\n let firstTimestamp: Date | undefined;\n let totalDuration = 0;\n\n for (const report of arc.reports?.report ?? []) {\n const testResult = report.content?.TestResult;\n // Skip non-XCCDF reports (e.g. OVAL)\n if (!testResult?.id) {\n continue;\n }\n\n // Timing\n if (testResult['start-time'] && !firstTimestamp) {\n firstTimestamp = new Date(testResult['start-time']);\n }\n if (testResult['start-time'] && testResult['end-time']) {\n const start = new Date(testResult['start-time']).getTime();\n const end = new Date(testResult['end-time']).getTime();\n if (!isNaN(start) && !isNaN(end) && end >= start) {\n totalDuration += (end - start) / 1000;\n }\n }\n\n // Convert rule-results\n const ruleResults = testResult['rule-result'] ?? [];\n const { items: limitedARFRuleResults, truncated: truncatedARFRR } = limitArray(ruleResults);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedARFRR) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedARFRuleResults.length} rule-result items (original: ${ruleResults.length})`);\n }\n const requirements = limitedARFRuleResults.map((rr) =>\n ruleResultToRequirement(rr, ruleIndex)\n );\n\n // Baseline name from Benchmark title\n let baselineName = '';\n if (benchmark) {\n baselineName = extractText(benchmark.title) || '';\n }\n if (!baselineName) {\n baselineName = extractText(testResult.title) || testResult.id || 'ARF Report';\n }\n\n const baseline = createMinimalBaseline(\n baselineName,\n requirements,\n { resultsChecksum }\n ) as EvaluatedBaseline;\n baselines.push(baseline);\n\n // Build target from TestResult, then enrich with ARF asset metadata\n const reportTargets = buildTargets(testResult);\n const target = reportTargets[0];\n if (target && report.id) {\n const assetIds = reportToAssets.get(report.id) ?? [];\n for (const assetId of assetIds) {\n const asset = assetMap.get(assetId);\n if (asset) {\n enrichTargetWithAsset(target, asset);\n }\n }\n }\n components.push(...reportTargets);\n }\n\n if (baselines.length === 0) {\n throw new Error('ARF document contains no XCCDF TestResult reports');\n }\n\n const hdf: HdfResults = {\n baselines,\n generator: { name: 'hdf-converters', version: CONVERTER_VERSION },\n tool: { name: 'ARF', format: 'ARF' },\n components,\n timestamp: firstTimestamp ?? new Date(),\n };\n\n if (totalDuration > 0) {\n hdf.statistics = { duration: totalDuration };\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n\n/**\n * Find the XCCDF Benchmark embedded in an ARF data-stream-collection.\n */\nfunction findBenchmarkInArf(\n arc: ArfCollectionElement\n): BenchmarkElement | undefined {\n for (const req of arc['report-requests']?.['report-request'] ?? []) {\n const components =\n req.content?.['data-stream-collection']?.component ?? [];\n for (const comp of components) {\n if (comp.Benchmark?.id) {\n return comp.Benchmark;\n }\n }\n }\n return undefined;\n}\n\n/**\n * Enrich an HDF Component with metadata from an ARF asset element.\n */\nfunction enrichTargetWithAsset(\n target: Component,\n asset: ArfAssetElement\n): void {\n const cd = asset['computing-device'];\n if (!cd) {\n return;\n }\n\n if (cd.fqdn) {\n target.fqdn = cd.fqdn;\n }\n\n // Extract first non-loopback MAC address\n const connections = cd.connections?.connection ?? [];\n for (const conn of connections) {\n const mac = conn['mac-address'];\n if (mac && mac !== '00:00:00:00:00:00') {\n target.macAddress = mac;\n break;\n }\n }\n\n // If target has no IP yet, try ARF asset connections\n if (!target.ipAddress) {\n for (const conn of connections) {\n const ip = conn['ip-address'];\n if (ip?.['ip-v4']) {\n target.ipAddress = ip['ip-v4'];\n break;\n }\n if (ip?.['ip-v6']) {\n target.ipAddress = ip['ip-v6'];\n break;\n }\n }\n }\n}\n\n// ---------------------------------------------------------------------------\n// Shared helpers\n// ---------------------------------------------------------------------------\n\n/**\n * Builds an index of Rule elements keyed by their @id attribute.\n * Rules can appear directly under Benchmark or nested inside Group elements.\n */\nfunction buildRuleIndex(benchmark: BenchmarkElement): Map<string, RuleElement> {\n const index = new Map<string, RuleElement>();\n\n const topRules = benchmark.Rule ?? [];\n for (const rule of topRules) {\n if (rule.id) {\n index.set(rule.id, rule);\n }\n }\n\n const groups = benchmark.Group ?? [];\n for (const group of groups) {\n const rules = group.Rule ?? [];\n for (const rule of rules) {\n if (rule.id) {\n index.set(rule.id, rule);\n }\n }\n }\n\n return index;\n}\n\n/**\n * Convert a single <rule-result> into an EvaluatedRequirement.\n */\nfunction ruleResultToRequirement(\n rr: RuleResultElement,\n ruleIndex: Map<string, RuleElement>\n): EvaluatedRequirement {\n const ruleId = rr.idref ?? '';\n const ruleDef = ruleIndex.get(ruleId);\n\n const id = extractVersion(ruleDef?.version) || ruleId;\n const title = extractText(ruleDef?.title) || id;\n\n const severity = rr.severity ?? ruleDef?.severity ?? '';\n const impact = severity ? severityToImpact(severity) : 0.5;\n\n const descriptions: Description[] = [];\n const rawDesc = extractText(ruleDef?.description);\n if (rawDesc) {\n descriptions.push({\n label: 'default',\n data: extractVulnDiscussion(rawDesc),\n });\n }\n const fixtext = extractFixtext(ruleDef?.fixtext);\n if (fixtext) {\n descriptions.push({ label: 'fix', data: fixtext });\n }\n\n const xccdfResult = (rr.result ?? '').toLowerCase();\n const status = STATUS_MAP[xccdfResult] ?? ResultStatus.NotReviewed;\n\n const result = createResult(status, '', {\n codeDesc: `XCCDF rule ${id}`,\n }) as RequirementResult;\n\n const tags: Record<string, unknown> = {};\n const cciIds = extractCCIs(rr.ident ?? ruleDef?.ident ?? []);\n if (cciIds.length > 0) {\n tags['cci'] = cciIds;\n const nistTags = cciIds.flatMap(\n (cci) => getCCINistMappings(cci) ?? []\n );\n if (nistTags.length > 0) {\n tags['nist'] = [...new Set(nistTags)];\n }\n }\n\n return createRequirement(\n id,\n title,\n descriptions,\n impact,\n [result],\n { tags }\n ) as EvaluatedRequirement;\n}\n\n/**\n * Build Component array from TestResult metadata.\n */\nfunction buildTargets(testResult: TestResultElement): Component[] {\n const targetName = testResult.target;\n if (!targetName) {\n return [];\n }\n\n const addresses = testResult['target-address'] ?? [];\n const target: Component = {\n name: targetName,\n type: Copyright.Host,\n labels: {},\n };\n\n if (addresses.length > 0) {\n target.ipAddress = addresses[0];\n }\n\n return [target];\n}\n\n/**\n * Extract plain text from a field that may be a string or {#text: string}.\n */\nfunction extractText(\n field: string | TextElement | VersionElement | undefined\n): string {\n if (field === undefined || field === null) {\n return '';\n }\n if (typeof field === 'string') {\n return field;\n }\n return (field as TextElement)['#text'] ?? '';\n}\n\n/**\n * Extract version string from a version field.\n */\nfunction extractVersion(\n field: string | VersionElement | undefined\n): string {\n if (field === undefined || field === null) {\n return '';\n }\n if (typeof field === 'string') {\n return field;\n }\n return (field as VersionElement)['#text'] ?? '';\n}\n\n/**\n * Extract fixtext content from fixtext field.\n */\nfunction extractFixtext(\n field: string | FixtextElement | undefined\n): string {\n if (field === undefined || field === null) {\n return '';\n }\n if (typeof field === 'string') {\n return field;\n }\n return (field as FixtextElement)['#text'] ?? '';\n}\n\n/**\n * Extract check-content text from a check element.\n */\nfunction extractCheckContent(\n check: CheckElement | undefined\n): string {\n if (!check) {\n return '';\n }\n const cc = check['check-content'];\n if (!cc) {\n return '';\n }\n if (typeof cc === 'string') {\n return cc;\n }\n // check-content is forced into an array by ARRAY_TAGS — handle both cases\n if (Array.isArray(cc)) {\n const first = (cc as unknown[])[0];\n if (typeof first === 'string') {\n return first;\n }\n if (first && typeof first === 'object' && '#text' in first) {\n return (first as TextElement)['#text'] ?? '';\n }\n return '';\n }\n return (cc as TextElement)['#text'] ?? '';\n}\n\n/**\n * Extract the VulnDiscussion text from an XCCDF description that contains\n * embedded XML like `<VulnDiscussion>...</VulnDiscussion>`. If no\n * VulnDiscussion tag is found, returns the original text.\n */\nfunction extractVulnDiscussion(description: string): string {\n const match = description.match(\n /<VulnDiscussion>([\\s\\S]*?)<\\/VulnDiscussion>/\n );\n if (match) {\n return match[1]!.trim();\n }\n // Also handle HTML-entity-encoded tags from the XML parser\n const entityMatch = description.match(\n /<VulnDiscussion>([\\s\\S]*?)<\\/VulnDiscussion>/\n );\n if (entityMatch) {\n return entityMatch[1]!.trim();\n }\n return description;\n}\n\n/**\n * Extract CCI identifiers from ident elements (system=\"http://cyber.mil/cci\").\n */\nfunction extractCCIs(idents: IdentElement[]): string[] {\n return idents\n .filter((i) => i.system === CCI_SYSTEM)\n .map((i) => i['#text'] ?? '')\n .filter((v) => v.length > 0);\n}\n\n/**\n * Convert a string to kebab-case (e.g., \"MS_Windows_Server_2022_STIG\" -> \"ms-windows-server-2022-stig\").\n */\nfunction kebabCase(s: string): string {\n return s.toLowerCase().replace(/_/g, '-');\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { detectConverter } from '../../../shared/typescript/fingerprint.js';\nimport { registerAllFingerprints } from '../../../shared/typescript/register-all.js';\nimport { convertSarifToHdf } from '../../sarif-to-hdf/typescript/converter.js';\nimport { inputChecksum, limitArray, mapCWEToNIST, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n severityToImpact,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Snyk JSON output structures\n * See https://docs.snyk.io/snyk-cli/commands/test for the full schema.\n */\ninterface SnykReport {\n ok: boolean;\n vulnerabilities: SnykVuln[];\n dependencyCount?: number;\n org?: string;\n packageManager?: string;\n summary?: string;\n projectName?: string;\n path?: string;\n}\n\ninterface SnykVuln {\n id: string;\n title: string;\n description: string;\n severity: string;\n cvssScore?: number;\n CVSSv3?: string;\n identifiers: SnykIdentifiers;\n language?: string;\n packageName?: string;\n moduleName?: string;\n version?: string;\n from: string[];\n upgradePath?: unknown[];\n fixedIn?: string[];\n exploit?: string;\n}\n\ninterface SnykIdentifiers {\n CVE?: string[];\n CWE?: string[];\n GHSA?: string[];\n}\n\n/**\n * Formats the \"from\" array as a human-readable dependency path.\n */\nfunction formatDependencyPath(from: string[]): string {\n if (!from || from.length === 0) {\n return 'Unknown dependency path';\n }\n return `From: [ ${from.join(', ')} ]`;\n}\n\n/**\n * Builds a single EvaluatedRequirement from a group of vulnerabilities sharing an ID.\n */\nfunction buildRequirement(vulnID: string, vulns: SnykVuln[]): EvaluatedRequirement {\n const rep = vulns[0]!;\n const cweIDs = rep.identifiers.CWE ?? [];\n const nist = mapCWEToNIST(cweIDs, DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n const tags: Record<string, unknown> = {\n nist,\n cci: cciTags,\n };\n\n if (cweIDs.length > 0) {\n tags['cweid'] = cweIDs;\n }\n if (rep.identifiers.CVE && rep.identifiers.CVE.length > 0) {\n tags['cveid'] = rep.identifiers.CVE;\n }\n if (rep.identifiers.GHSA && rep.identifiers.GHSA.length > 0) {\n tags['ghsaid'] = rep.identifiers.GHSA;\n }\n\n const descriptions: Description[] = [\n { label: 'default', data: rep.description },\n ];\n\n const results = vulns.map(vuln =>\n createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatDependencyPath(vuln.from),\n })\n );\n\n return createRequirement(\n vulnID,\n rep.title,\n descriptions,\n severityToImpact(rep.severity),\n results,\n { tags }\n );\n}\n\n/**\n * Converts a single Snyk project report to an HDF baseline.\n */\nfunction convertSingleProject(\n report: SnykReport,\n resultsChecksum: Checksum\n): EvaluatedBaseline {\n // Group vulnerabilities by ID, preserving insertion order\n const { items: limitedVulns, truncated: truncatedVulns } = limitArray(report.vulnerabilities);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedVulns) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${report.vulnerabilities.length})`);\n }\n const groups = new Map<string, SnykVuln[]>();\n for (const vuln of limitedVulns) {\n const existing = groups.get(vuln.id);\n if (existing) {\n existing.push(vuln);\n } else {\n groups.set(vuln.id, [vuln]);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [vulnID, vulns] of groups) {\n requirements.push(buildRequirement(vulnID, vulns));\n }\n\n const title = `Snyk Project: ${report.projectName ?? ''} Snyk Path: ${report.path ?? ''}`;\n\n return createMinimalBaseline(\n 'Snyk Scan',\n requirements,\n {\n resultsChecksum,\n title,\n summary: report.summary,\n }\n ) as EvaluatedBaseline;\n}\n\n/**\n * Converts Snyk output to HDF format.\n * Accepts both native Snyk JSON and SARIF format — SARIF input is detected\n * automatically and delegated to the shared SARIF converter.\n * Handles both single-project (object) and multi-project (array) input.\n *\n * @param input - Snyk JSON or SARIF string\n * @returns HDF JSON string\n */\nexport async function convertSnykToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('snyk: empty input');\n }\n validateInputSize(input, 'snyk');\n\n // Detect format: if SARIF, delegate to the shared SARIF converter\n registerAllFingerprints();\n const detected = detectConverter(input);\n if (detected && detected.fingerprint.id === 'sarif-to-hdf') {\n return convertSarifToHdf(input);\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const parsed = parseJSON<SnykReport | SnykReport[]>(input);\n\n if (!parsed || typeof parsed !== 'object') {\n throw new Error('snyk: invalid JSON');\n }\n\n let baselines: EvaluatedBaseline[];\n let targetName: string;\n\n if (Array.isArray(parsed)) {\n // Multi-project output\n const { items: limitedProjects, truncated: truncatedProjects } = limitArray(parsed);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedProjects) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedProjects.length} project items (original: ${parsed.length})`);\n }\n baselines = limitedProjects.map(report => convertSingleProject(report, resultsChecksum));\n targetName = limitedProjects[0]?.projectName ?? limitedProjects[0]?.path ?? '';\n } else {\n // Single project\n baselines = [convertSingleProject(parsed, resultsChecksum)];\n targetName = parsed.projectName ?? parsed.path ?? '';\n }\n\n return buildHdfResults({\n generatorName: 'snyk-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Snyk',\n toolFormat: 'JSON',\n baselines,\n components: [{ name: targetName, type: Copyright.Application }],\n timestamp: new Date(),\n });\n}\n","import {\n type Checksum,\n Copyright,\n createMinimalBaseline,\n type EvaluatedBaseline,\n type EvaluatedRequirement,\n type RequirementResult,\n ResultStatus,\n} from '@mitre/hdf-schema';\nimport {nistToCci, DEFAULT_STATIC_ANALYSIS_NIST_TAGS} from '@mitre/hdf-mappings';\nimport {parseJSON} from '@mitre/hdf-utilities';\nimport {inputChecksum, buildNistCciTags, limitArray, validateInputSize, buildHdfResults} from '../../../shared/typescript/converterutil.js';\n\n// Input types for Grype JSON\n\ninterface GrypeReport {\n descriptor: GrypeDescriptor;\n source: GrypeSource;\n distro?: GrypeDistro;\n matches: GrypeMatch[];\n ignoredMatches?: GrypeMatch[];\n}\n\ninterface GrypeDescriptor {\n name: string;\n version: string;\n timestamp?: string;\n configuration?: unknown;\n}\n\ninterface GrypeSource {\n target: {\n userInput: string;\n };\n}\n\ninterface GrypeDistro {\n name?: string;\n version?: string;\n idLike?: string[];\n}\n\ninterface GrypeMatch {\n vulnerability: GrypeVulnerability;\n relatedVulnerabilities?: GrypeRelatedVulnerability[];\n matchDetails: GrypeMatchDetail[];\n artifact: GrypeArtifact;\n}\n\ninterface GrypeVulnerability {\n id: string;\n dataSource?: string;\n namespace?: string;\n severity?: string;\n urls?: string[];\n description?: string;\n cvss?: GrypeCVSS[];\n fix?: GrypeFix;\n advisories?: unknown[];\n}\n\ninterface GrypeRelatedVulnerability {\n id: string;\n dataSource?: string;\n namespace?: string;\n severity?: string;\n urls?: string[];\n description?: string;\n cvss?: GrypeCVSS[];\n}\n\ninterface GrypeCVSS {\n version?: string;\n vector?: string;\n metrics?: {\n baseScore?: number;\n exploitabilityScore?: number;\n impactScore?: number;\n };\n vendorMetadata?: unknown;\n}\n\ninterface GrypeFix {\n versions?: string[];\n state?: string; // \"fixed\", \"unknown\", \"wontfix\", \"not-fixed\"\n}\n\ninterface GrypeMatchDetail {\n type?: string; // \"exact-direct-match\", \"exact-indirect-match\", \"cpe-match\"\n matcher?: string;\n searchedBy?: Record<string, unknown>;\n found?: Record<string, unknown>;\n}\n\ninterface GrypeArtifact {\n id?: string;\n name: string;\n version: string;\n type?: string; // \"apk\", \"rpm\", \"deb\", \"npm\", \"python\", etc.\n locations?: GrypeLocation[];\n licenses?: string[];\n language?: string;\n cpes?: string[];\n purl?: string;\n upstreams?: unknown[];\n metadata?: unknown;\n}\n\ninterface GrypeLocation {\n path?: string;\n layerID?: string;\n}\n\n// Severity to impact mapping\nconst IMPACT_MAPPING: Map<string, number> = new Map([\n ['critical', 0.9],\n ['high', 0.7],\n ['medium', 0.5],\n ['low', 0.3],\n ['negligible', 0.0],\n ['unknown', 0.5],\n]);\n\n\nfunction getImpact(severity?: string): number {\n if (!severity) {\n return 0.5; // default for unknown\n }\n return IMPACT_MAPPING.get(severity.toLowerCase()) ?? 0.5;\n}\n\nfunction isNegligibleOrUnknown(severity?: string): boolean {\n if (!severity) {\n return true;\n }\n const lower = severity.toLowerCase();\n return lower === 'negligible' || lower === 'unknown';\n}\n\nfunction getDescription(vuln: GrypeVulnerability, relatedVulns?: GrypeRelatedVulnerability[]): string {\n // Use primary vulnerability description if available\n if (vuln.description) {\n return vuln.description;\n }\n\n // Fall back to related vulnerability with matching ID\n if (relatedVulns) {\n for (const related of relatedVulns) {\n if (related.id === vuln.id && related.description) {\n return related.description;\n }\n }\n }\n\n return `Vulnerability ${vuln.id}`;\n}\n\nfunction getFixInfo(fix?: GrypeFix): string {\n if (!fix || !fix.state) {\n return 'vulnerability is not known to be fixed in any versions';\n }\n\n if (fix.state === 'fixed' && fix.versions && fix.versions.length > 0) {\n return `vulnerability is ${fix.state} for versions ${fix.versions.join(', ')}`;\n }\n\n return `vulnerability is ${fix.state}`;\n}\n\nfunction getCVSSInfo(vuln: GrypeVulnerability, relatedVulns?: GrypeRelatedVulnerability[]): string {\n const cvssData: Record<string, unknown> = {};\n\n // Collect CVSS from primary vulnerability\n if (vuln.cvss && vuln.cvss.length > 0) {\n cvssData.primary = vuln.cvss;\n }\n\n // Collect CVSS from related vulnerabilities\n if (relatedVulns && relatedVulns.length > 0) {\n cvssData.related = relatedVulns\n .filter(r => r.cvss && r.cvss.length > 0)\n .map(r => ({\n id: r.id,\n dataSource: r.dataSource,\n cvss: r.cvss,\n }));\n }\n\n return JSON.stringify(cvssData);\n}\n\nfunction getReferences(vuln: GrypeVulnerability, relatedVulns?: GrypeRelatedVulnerability[]): string[] {\n const refs = new Set<string>();\n\n // Add URLs from primary vulnerability\n if (vuln.urls) {\n for (const url of vuln.urls) {\n refs.add(url);\n }\n }\n\n // Add URLs from related vulnerabilities\n if (relatedVulns) {\n for (const related of relatedVulns) {\n if (related.urls) {\n for (const url of related.urls) {\n refs.add(url);\n }\n }\n }\n }\n\n return Array.from(refs);\n}\n\nfunction buildCodeDesc(match: GrypeMatch): string {\n const parts: string[] = [];\n\n // Package info\n parts.push(`Package: ${match.artifact.name}@${match.artifact.version}`);\n\n // Package type if available\n if (match.artifact.type) {\n parts.push(`Type: ${match.artifact.type}`);\n }\n\n // Location if available\n if (match.artifact.locations && match.artifact.locations.length > 0) {\n const location = match.artifact.locations[0]!;\n if (location.path) {\n parts.push(`Location: ${location.path}`);\n }\n }\n\n // Match type if available\n if (match.matchDetails && match.matchDetails.length > 0) {\n const matchType = match.matchDetails[0]!.type;\n if (matchType) {\n parts.push(`Match Type: ${matchType}`);\n }\n }\n\n return parts.join(' | ');\n}\n\nfunction convertMatchToRequirement(match: GrypeMatch, isIgnored: boolean): EvaluatedRequirement {\n const vuln = match.vulnerability;\n const cveId = vuln.id;\n const severity = vuln.severity;\n const impact = getImpact(severity);\n const description = getDescription(vuln, match.relatedVulnerabilities);\n const fixInfo = getFixInfo(vuln.fix);\n const cvssInfo = getCVSSInfo(vuln, match.relatedVulnerabilities);\n const refs = getReferences(vuln, match.relatedVulnerabilities);\n\n // Determine status\n let status: ResultStatus;\n if (isIgnored) {\n status = ResultStatus.NotReviewed; // Ignored by configured rules\n } else if (isNegligibleOrUnknown(severity)) {\n status = ResultStatus.NotApplicable;\n } else {\n status = ResultStatus.Failed;\n }\n\n // Build result message\n const messageParts: string[] = [];\n if (isIgnored) {\n messageParts.push('This vulnerability was ignored by configured rules.');\n }\n if (isNegligibleOrUnknown(severity) && !isIgnored) {\n messageParts.push(\n 'Manual review required because a Grype rating severity is set to `negligible` or `unknown`.'\n );\n }\n messageParts.push(`Severity: ${severity || 'unknown'}`);\n messageParts.push(fixInfo);\n const message = messageParts.join(' ');\n\n // Build execution result\n const result: RequirementResult = {\n status,\n codeDesc: buildCodeDesc(match),\n message,\n startTime: new Date('0001-01-01T00:00:00Z'), // Go zero time format\n };\n\n // Get CCI mappings for NIST controls using curated mapping table\n const cciTags = nistToCci(DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n\n // Build tags object - only include cci if not empty\n const tags = buildNistCciTags(DEFAULT_STATIC_ANALYSIS_NIST_TAGS, cciTags);\n\n // Build requirement\n const requirement: EvaluatedRequirement = {\n id: isIgnored ? `Grype-Ignored-Match/${cveId}` : `Grype/${cveId}`,\n impact,\n results: [result],\n tags,\n descriptions: [\n {label: 'default', data: description},\n {label: 'fix', data: fixInfo},\n {label: 'check', data: cvssInfo},\n ],\n refs: refs.length > 0 ? refs.map(url => ({url})) : undefined,\n };\n\n return requirement;\n}\n\nexport async function convertGrypeToHdf(input: string): Promise<string> {\n validateInputSize(input, 'grype');\n // Calculate checksum of input data\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Parse Grype JSON\n const grypeData = parseJSON<GrypeReport>(input);\n\n // Build requirements from matches\n const requirements: EvaluatedRequirement[] = [];\n\n // Process regular matches\n if (grypeData.matches && grypeData.matches.length > 0) {\n const { items: limitedMatches, truncated: truncatedMatches } = limitArray(grypeData.matches);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedMatches) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedMatches.length} match items (original: ${grypeData.matches.length})`);\n }\n for (const match of limitedMatches) {\n requirements.push(convertMatchToRequirement(match, false));\n }\n }\n\n // Process ignored matches\n if (grypeData.ignoredMatches && grypeData.ignoredMatches.length > 0) {\n const { items: limitedIgnored, truncated: truncatedIgnored } = limitArray(grypeData.ignoredMatches);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedIgnored) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedIgnored.length} ignoredMatch items (original: ${grypeData.ignoredMatches.length})`);\n }\n for (const match of limitedIgnored) {\n requirements.push(convertMatchToRequirement(match, true));\n }\n }\n\n // Build baseline name from source\n const targetName = grypeData.source?.target?.userInput || 'Grype Scan';\n\n // Create baseline\n const baseline: EvaluatedBaseline = createMinimalBaseline(targetName, requirements, {\n resultsChecksum,\n }) as EvaluatedBaseline;\n\n // Build HDF results\n return buildHdfResults({\n generatorName: grypeData.descriptor?.name || 'grype',\n converterVersion: grypeData.descriptor?.version || 'unknown',\n toolName: 'Grype',\n toolVersion: grypeData.descriptor?.version,\n baselines: [baseline],\n components: [{\n type: Copyright.Artifact,\n name: targetName,\n }],\n timestamp: grypeData.descriptor?.timestamp ? new Date(grypeData.descriptor.timestamp) : new Date(),\n });\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport { getNessusNistControl, getCCINistMappings } from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Component,\n Description,\n Reference,\n Checksum,\n Tool,\n} from '@mitre/hdf-schema';\nimport { ResultStatus, Copyright as TargetType, createMinimalBaseline } from '@mitre/hdf-schema';\n// Per-converter version (matches the pattern used by the other 32 converters).\n// Bumped manually when the nessus converter's output format changes in a way\n// consumers might notice. Distinct from the package's npm version.\nconst converterVersion = '1.0.0';\n\ninterface NessusXml {\n NessusClientData_v2: {\n Policy: {\n policyName: string;\n Preferences?: {\n ServerPreferences?: {\n preference?: Array<{ name: string; value: string }>;\n };\n };\n };\n Report: {\n '@name'?: string;\n ReportHost: ReportHost[];\n };\n };\n}\n\ninterface ReportHost {\n name: string;\n HostProperties?: {\n tag?: HostPropertyTag[];\n };\n ReportItem?: ReportItem[];\n}\n\ninterface HostPropertyTag {\n name: string;\n '#text'?: string;\n}\n\ninterface ReportItem {\n port: string;\n svc_name: string;\n protocol: string;\n severity: string;\n pluginID: string;\n pluginName: string;\n pluginFamily: string;\n description?: string;\n fname?: string;\n plugin_modification_date?: string;\n plugin_name?: string;\n plugin_publication_date?: string;\n plugin_type?: string;\n risk_factor?: string;\n script_version?: string;\n see_also?: string;\n solution?: string;\n synopsis?: string;\n plugin_output?: string;\n cvss_base_score?: string;\n cvss3_base_score?: string;\n cve?: string;\n // Compliance fields\n 'compliance-reference'?: string;\n 'compliance-check-name'?: string;\n 'compliance-info'?: string;\n 'compliance-solution'?: string;\n 'compliance-result'?: string;\n 'compliance-actual-value'?: string;\n}\n\n// Severity to impact mapping from heimdall2\nconst IMPACT_MAPPING: Record<string, number> = {\n '4': 0.9, // Critical\n '3': 0.7, // High\n 'i': 0.7,\n '2': 0.5, // Medium\n 'ii': 0.5,\n '1': 0.3, // Low\n 'iii': 0.3,\n '0': 0.0, // Info\n};\n\n/**\n * Strip HTML tags from a string\n */\nfunction parseHtml(html: string): string {\n return html.replace(/<[^>]*>/g, '').trim();\n}\n\n/**\n * Convert Nessus XML scan results to HDF format\n */\nexport async function convertNessusToHdf(nessusXml: string): Promise<HdfResults> {\n validateInputSize(nessusXml, 'nessus');\n // Calculate checksum of source scan data for integrity verification\n const resultsChecksum: Checksum = await inputChecksum(nessusXml);\n\n const parsed = parseXmlWithArrays(nessusXml, ['preference', 'tag', 'ReportItem', 'ReportHost']) as unknown as NessusXml;\n\n const policyName = parsed.NessusClientData_v2.Policy.policyName;\n const version = extractVersion(parsed);\n // parseXmlWithArrays ensures ReportHost is always an array\n const reportHosts = parsed.NessusClientData_v2.Report.ReportHost as ReportHost[];\n\n const { items: limitedHosts, truncated: truncatedHosts } = limitArray(reportHosts);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedHosts) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedHosts.length} ReportHost items (original: ${reportHosts.length})`);\n }\n\n // Calculate start and end times from first and last host\n const { startTime, duration } = calculateTiming(limitedHosts);\n\n const baselines: EvaluatedBaseline[] = [];\n const components: Component[] = [];\n\n // Process each ReportHost\n limitedHosts.forEach(host => {\n const baseline = convertReportHostToBaseline(host, policyName, version, resultsChecksum);\n baselines.push(baseline);\n\n const target = convertReportHostToTarget(host);\n components.push(target);\n });\n\n const tool: Tool = { name: 'Nessus' };\n\n const result: HdfResults = {\n baselines,\n components,\n statistics: {\n duration,\n },\n generator: {\n name: 'hdf-converters',\n version: converterVersion,\n },\n tool,\n timestamp: startTime,\n };\n\n return result;\n}\n\nfunction extractVersion(parsed: NessusXml): string {\n const prefs = parsed.NessusClientData_v2.Policy.Preferences?.ServerPreferences?.preference;\n if (!prefs) return '';\n\n // parseXmlWithArrays ensures preference is always an array\n const scVersion = (prefs as Array<{ name: string; value: string }>).find(p => p.name === 'sc_version');\n return scVersion?.value || '';\n}\n\nfunction calculateTiming(hosts: ReportHost[]): { startTime: Date; endTime: Date; duration: number } {\n if (hosts.length === 0) {\n const now = new Date();\n return { startTime: now, endTime: now, duration: 0 };\n }\n\n const firstHost = hosts[0]!;\n const lastHost = hosts[hosts.length - 1]!;\n\n const startTimeStr = getHostPropertyValue(firstHost, 'HOST_START');\n const endTimeStr = getHostPropertyValue(lastHost, 'HOST_END') || getHostPropertyValue(lastHost, 'HOST_START');\n\n const startTime = startTimeStr ? new Date(startTimeStr) : new Date();\n const endTime = endTimeStr ? new Date(endTimeStr) : startTime;\n\n const duration = (endTime.getTime() - startTime.getTime()) / 1000; // seconds\n\n return { startTime, endTime, duration };\n}\n\nfunction getHostPropertyValue(host: ReportHost, name: string): string | undefined {\n const tags = host.HostProperties?.tag;\n if (!tags) return undefined;\n\n // parseXmlWithArrays ensures tag is always an array\n const tag = (tags as HostPropertyTag[]).find(t => t['name'] === name);\n return tag?.['#text'];\n}\n\nfunction convertReportHostToBaseline(\n host: ReportHost,\n policyName: string,\n version: string,\n resultsChecksum: Checksum\n): EvaluatedBaseline {\n const items = host.ReportItem;\n // parseXmlWithArrays ensures ReportItem is always an array\n let requirements: EvaluatedRequirement[];\n if (items) {\n const { items: limitedItems, truncated: truncatedItems } = limitArray(items as ReportItem[]);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedItems) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedItems.length} ReportItem items (original: ${(items as ReportItem[]).length})`);\n }\n requirements = limitedItems.map(item => convertReportItemToRequirement(item, host));\n } else {\n requirements = [];\n }\n\n return createMinimalBaseline(`Nessus ${policyName}`, requirements, {\n title: `Nessus ${policyName}`,\n version,\n resultsChecksum,\n status: 'loaded',\n summary: `Nessus ${policyName}`,\n });\n}\n\nfunction convertReportItemToRequirement(item: ReportItem, host: ReportHost): EvaluatedRequirement {\n const isCompliance = !!item['compliance-reference'];\n const id = isCompliance\n ? parseComplianceRef(item['compliance-reference']!, 'Vuln-ID')[0] || item['pluginID']\n : item['pluginID'];\n\n const title = isCompliance\n ? (item['compliance-check-name'] || item['pluginName'])\n : item['pluginName'];\n\n const descriptions = buildDescriptions(item, isCompliance);\n const impact = calculateImpact(item, isCompliance);\n const tags = buildTags(item, isCompliance);\n const refs = buildRefs(item);\n const results = [buildResult(item, host, isCompliance)];\n const code = JSON.stringify(item, null, 2);\n\n return {\n id,\n title,\n descriptions,\n impact,\n tags,\n refs,\n results,\n code,\n };\n}\n\nfunction buildDescriptions(item: ReportItem, isCompliance: boolean): Description[] {\n const descriptions: Description[] = [];\n\n // Default description\n if (isCompliance && item['compliance-info']) {\n descriptions.push({\n label: 'default',\n data: parseHtml(item['compliance-info']),\n });\n } else {\n // Non-compliance: create description from metadata\n const parts = [\n `Plugin Family: ${item['pluginFamily']}`,\n `Port: ${item['port']}`,\n `Protocol: ${item['protocol']}`,\n ];\n descriptions.push({\n label: 'default',\n data: parts.join('; ') + ';',\n });\n }\n\n // Fix/solution description\n const solution = isCompliance ? item['compliance-solution'] : item.solution;\n if (solution && solution !== 'n/a') {\n descriptions.push({\n label: 'fix',\n data: parseHtml(solution),\n });\n } else if (solution === 'n/a') {\n descriptions.push({\n label: 'fix',\n data: 'n/a',\n });\n }\n\n return descriptions;\n}\n\nfunction calculateImpact(item: ReportItem, isCompliance: boolean): number {\n if (isCompliance && item['compliance-reference']) {\n const cat = parseComplianceRef(item['compliance-reference'], 'CAT')[0];\n const catKey = cat?.toLowerCase();\n return catKey ? (IMPACT_MAPPING[catKey] ?? 0.5) : 0.5;\n }\n\n return IMPACT_MAPPING[item['severity']] ?? 0.0;\n}\n\nfunction buildTags(item: ReportItem, isCompliance: boolean): Record<string, unknown> {\n const tags: Record<string, unknown> = {\n rid: isCompliance\n ? parseComplianceRef(item['compliance-reference']!, 'Rule-ID').join(',')\n : item['pluginID'],\n };\n\n // NIST tags\n if (isCompliance && item['compliance-reference']) {\n const cciTags = parseComplianceRef(item['compliance-reference'], 'CCI');\n tags.cci = cciTags;\n // Map CCI IDs to NIST controls using hdf-mappings\n // Pattern: Extract source IDs → Map each ID → Flatten results → Deduplicate\n const mappedControls = cciTags.flatMap(cci => getCCINistMappings(cci) ?? []);\n tags.nist = [...new Set(mappedControls)];\n } else {\n const nistControls = getNessusNistControl(item['pluginFamily'], item['pluginID']);\n tags.nist = nistControls ? nistControls.split('|') : [];\n }\n\n // STIG ID for compliance\n if (isCompliance && item['compliance-reference']) {\n const stigId = parseComplianceRef(item['compliance-reference'], 'STIG-ID').join(',');\n if (stigId) {\n tags.stig_id = stigId;\n }\n }\n\n // Additional Nessus metadata tags\n if (item.risk_factor) tags.risk_factor = item.risk_factor;\n if (item.plugin_type) tags.plugin_type = item.plugin_type;\n if (item.plugin_publication_date) tags.plugin_publication_date = item.plugin_publication_date;\n if (item.fname) tags.fname = item.fname;\n if (item.cvss3_base_score) tags.cvss3_base_score = item.cvss3_base_score;\n if (item.cvss_base_score) tags.cvss_base_score = item.cvss_base_score;\n\n return tags;\n}\n\nfunction buildRefs(item: ReportItem): Reference[] | undefined {\n const refs: Reference[] = [];\n\n if (item.see_also) {\n refs.push({ url: item.see_also });\n }\n\n return refs.length > 0 ? refs : undefined;\n}\n\nfunction buildResult(item: ReportItem, host: ReportHost, isCompliance: boolean): RequirementResult {\n const status = getStatus(item, isCompliance);\n const codeDesc = getCodeDesc(item);\n const message = item.plugin_output || item['compliance-actual-value'];\n const startTimeStr = getHostPropertyValue(host, 'HOST_START');\n const startTime = startTimeStr ? new Date(startTimeStr) : new Date();\n\n return {\n status,\n codeDesc,\n message: message || undefined,\n startTime,\n };\n}\n\nfunction getStatus(item: ReportItem, isCompliance: boolean): ResultStatus {\n if (isCompliance && item['compliance-result']) {\n const result = item['compliance-result'];\n switch (result) {\n case 'PASSED':\n return ResultStatus.Passed;\n case 'WARNING':\n return ResultStatus.NotApplicable; // Heimdall2 maps WARNING to skipped\n case 'ERROR':\n return ResultStatus.Error;\n default:\n return ResultStatus.Failed;\n }\n }\n\n // Non-compliance items are always failed (informational findings)\n return ResultStatus.Failed;\n}\n\nfunction getCodeDesc(item: ReportItem): string {\n const desc = item.description || item.plugin_output || 'This Nessus Plugin does not provide output message.';\n return parseHtml(desc);\n}\n\nfunction parseComplianceRef(ref: string, key: string): string[] {\n const matches = ref.split(',').filter(element => element.startsWith(key));\n return matches.map(element => element.split('|')[1] || '');\n}\n\nfunction convertReportHostToTarget(host: ReportHost): Component {\n const hostName = host['name'];\n\n // Extract host properties into a lookup map\n const hostProps: Record<string, string> = {};\n const tags = host.HostProperties?.tag;\n if (tags) {\n // parseXmlWithArrays ensures tag is always an array\n (tags as HostPropertyTag[]).forEach(tag => {\n const name = tag['name'];\n const value = tag['#text'];\n if (name && value) {\n hostProps[name] = value;\n }\n });\n }\n\n const target: Component = {\n name: hostName,\n type: TargetType.Host,\n };\n\n // Map host properties to typed Component fields\n if (isFQDN(hostName)) {\n target.fqdn = hostName;\n }\n\n const hostIp = hostProps['host-ip'];\n if (hostIp) {\n target.ipAddress = hostIp;\n } else if (isIPAddress(hostName)) {\n target.ipAddress = hostName;\n }\n\n if (hostProps['operating-system']) {\n target.osName = hostProps['operating-system'];\n }\n\n if (hostProps['os']) {\n target.osVersion = hostProps['os'];\n }\n\n if (hostProps['mac-address']) {\n target.macAddress = hostProps['mac-address'].split('\\n')[0];\n }\n\n if (hostProps['host-fqdn']) {\n target.fqdn = hostProps['host-fqdn'];\n }\n\n target.labels = {};\n\n return target;\n}\n\nfunction isFQDN(s: string): boolean {\n return s.includes('.') && !/^\\d+\\.\\d+\\.\\d+\\.\\d+$/.test(s);\n}\n\nfunction isIPAddress(s: string): boolean {\n return /^\\d+\\.\\d+\\.\\d+\\.\\d+$/.test(s) || s.includes(':');\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, mapCWEToNIST, extractCWEIDs, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n Copyright,\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createDescription,\n createResult,\n} from '@mitre/hdf-schema';\n\n/**\n * SonarQube /api/issues/search response structure\n */\ninterface SonarQubeIssuesResponse {\n total: number;\n p: number;\n ps: number;\n paging: {\n pageIndex: number;\n pageSize: number;\n total: number;\n };\n issues: SonarQubeIssue[];\n components?: SonarQubeComponent[];\n rules?: SonarQubeRule[];\n}\n\ninterface SonarQubeIssue {\n key: string;\n rule: string;\n severity: 'BLOCKER' | 'CRITICAL' | 'MAJOR' | 'MINOR' | 'INFO';\n component: string;\n project: string;\n line?: number;\n hash?: string;\n textRange?: {\n startLine: number;\n endLine: number;\n startOffset: number;\n endOffset: number;\n };\n flows?: SonarQubeFlow[];\n status: 'OPEN' | 'CONFIRMED' | 'REOPENED' | 'RESOLVED' | 'CLOSED';\n message: string;\n effort?: string;\n debt?: string;\n author?: string;\n tags?: string[];\n creationDate: string;\n updateDate: string;\n type: 'CODE_SMELL' | 'BUG' | 'VULNERABILITY' | 'SECURITY_HOTSPOT';\n}\n\ninterface SonarQubeFlow {\n locations: SonarQubeLocation[];\n}\n\ninterface SonarQubeLocation {\n component: string;\n textRange?: {\n startLine: number;\n endLine: number;\n };\n msg?: string;\n}\n\ninterface SonarQubeComponent {\n key: string;\n enabled?: boolean;\n qualifier?: string;\n name?: string;\n longName?: string;\n path?: string;\n}\n\n/**\n * A section of a SonarQube rule description.\n * SonarQube 26+ returns rule descriptions as structured sections\n * instead of monolithic htmlDesc/mdDesc fields.\n */\ninterface SonarQubeDescriptionSection {\n key: string;\n content: string;\n}\n\ninterface SonarQubeRule {\n key: string;\n name: string;\n status?: string;\n lang?: string;\n langName?: string;\n htmlDesc?: string;\n mdDesc?: string;\n severity?: string;\n type?: string;\n tags?: string[];\n sysTags?: string[];\n scope?: string;\n descriptionSections?: SonarQubeDescriptionSection[];\n}\n\n/**\n * Severity to impact mapping.\n * Canonical reference: heimdall2 sonarqube-mapper.ts IMPACT_MAPPING.\n */\nconst SEVERITY_IMPACT_MAPPING: Record<string, number> = {\n BLOCKER: 1.0,\n CRITICAL: 0.7,\n MAJOR: 0.5,\n MINOR: 0.3,\n INFO: 0.0,\n};\n\n/**\n * Default NIST tag for SonarQube findings without CWE mappings.\n * SA-11 (Developer Security Testing and Evaluation) applies to all issue types —\n * SonarQube is fundamentally a static analysis tool. Matches heimdall2.\n */\nconst DEFAULT_NIST_TAGS = ['SA-11'];\n\n/**\n * Convert SonarQube issues JSON to HDF format\n *\n * @param input - JSON string from SonarQube /api/issues/search endpoint\n * @returns HDF JSON string\n */\nexport async function convertSonarqubeToHdf(input: string): Promise<string> {\n validateInputSize(input, 'sonarqube');\n // Calculate checksum of source scan data\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Parse SonarQube JSON\n const sonarData = parseJSON<SonarQubeIssuesResponse>(input);\n\n if (!sonarData || typeof sonarData !== 'object') {\n throw new Error('Invalid SonarQube structure: not a valid JSON object');\n }\n\n if (!Array.isArray(sonarData.issues)) {\n throw new Error('Invalid SonarQube structure: missing or invalid issues field');\n }\n\n // Create lookup maps for components and rules\n const componentMap = new Map<string, SonarQubeComponent>();\n if (sonarData.components) {\n for (const component of sonarData.components) {\n componentMap.set(component.key, component);\n }\n }\n\n const ruleMap = new Map<string, SonarQubeRule>();\n if (sonarData.rules) {\n for (const rule of sonarData.rules) {\n ruleMap.set(rule.key, rule);\n }\n }\n\n // Group issues by project (each project becomes a baseline)\n const { items: limitedIssues, truncated: truncatedIssues } = limitArray(sonarData.issues);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedIssues) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedIssues.length} issue items (original: ${sonarData.issues.length})`);\n }\n const issuesByProject = new Map<string, SonarQubeIssue[]>();\n for (const issue of limitedIssues) {\n const projectKey = issue.project;\n if (!issuesByProject.has(projectKey)) {\n issuesByProject.set(projectKey, []);\n }\n issuesByProject.get(projectKey)!.push(issue);\n }\n\n // Convert each project to a baseline\n const baselines: EvaluatedBaseline[] = [];\n for (const [projectKey, issues] of issuesByProject) {\n const baseline = convertProjectToBaseline(\n projectKey,\n issues,\n componentMap,\n ruleMap,\n resultsChecksum\n );\n baselines.push(baseline);\n }\n\n // Build components from project keys\n const components = Array.from(issuesByProject.keys()).map(projectKey => ({\n type: Copyright.Application,\n name: projectKey,\n }));\n\n // Build HDF\n return buildHdfResults({\n generatorName: 'sonarqube-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'SonarQube',\n baselines,\n components,\n timestamp: new Date(),\n });\n}\n\nfunction convertProjectToBaseline(\n projectKey: string,\n issues: SonarQubeIssue[],\n componentMap: Map<string, SonarQubeComponent>,\n ruleMap: Map<string, SonarQubeRule>,\n resultsChecksum: Checksum\n): EvaluatedBaseline {\n // Group issues by rule (each rule becomes a requirement)\n const issuesByRule = new Map<string, SonarQubeIssue[]>();\n for (const issue of issues) {\n const ruleKey = issue.rule;\n if (!issuesByRule.has(ruleKey)) {\n issuesByRule.set(ruleKey, []);\n }\n issuesByRule.get(ruleKey)!.push(issue);\n }\n\n // Convert each rule to a requirement\n const requirements: EvaluatedRequirement[] = [];\n for (const [ruleKey, ruleIssues] of issuesByRule) {\n const requirement = convertRuleToRequirement(\n ruleKey,\n ruleIssues,\n componentMap,\n ruleMap\n );\n requirements.push(requirement);\n }\n\n return createMinimalBaseline(projectKey, requirements, {\n title: `SonarQube Analysis for ${projectKey}`,\n resultsChecksum,\n });\n}\n\nfunction convertRuleToRequirement(\n ruleKey: string,\n issues: SonarQubeIssue[],\n componentMap: Map<string, SonarQubeComponent>,\n ruleMap: Map<string, SonarQubeRule>\n): EvaluatedRequirement {\n const rule = ruleMap.get(ruleKey);\n\n // Extract rule name and description\n const title = rule?.name || ruleKey;\n const description = extractDescription(rule);\n\n // Get impact from first issue (all issues of same rule have same severity)\n const firstIssue = issues[0]!;\n const impact = SEVERITY_IMPACT_MAPPING[firstIssue.severity] || 0.5;\n\n // Extract tags and mappings\n const { cweIds, owaspTags, allTags } = extractTags(rule, issues);\n const nistControls = mapCWEToNIST(cweIds, DEFAULT_NIST_TAGS);\n const cciControls = nistToCci(nistControls);\n\n // Create results for each issue\n const results: RequirementResult[] = issues.map(issue =>\n createResultFromIssue(issue, componentMap)\n );\n\n // Get source location from first issue with a line number\n const issueWithLocation = issues.find(i => i.line !== undefined);\n const sourceLocation = issueWithLocation\n ? extractSourceLocation(issueWithLocation, componentMap)\n : undefined;\n\n const options: {\n sourceLocation?: { ref: string; line: number };\n tags: Record<string, unknown>;\n } = {\n tags: {\n severity: firstIssue.severity.toLowerCase(),\n type: firstIssue.type.toLowerCase(),\n cwe: cweIds,\n owasp: owaspTags,\n nist: nistControls,\n cci: cciControls,\n ...allTags,\n },\n };\n\n if (sourceLocation) {\n options.sourceLocation = sourceLocation;\n }\n\n return createRequirement(\n ruleKey,\n title,\n [createDescription('default', description)],\n impact,\n results,\n options\n );\n}\n\nfunction extractDescription(rule: SonarQubeRule | undefined): string {\n if (!rule) {\n return '';\n }\n\n // Prefer markdown description, fall back to HTML (stripped), then name\n if (rule.mdDesc) {\n return rule.mdDesc;\n }\n\n if (rule.htmlDesc) {\n // Strip HTML tags for plain text description\n return rule.htmlDesc.replace(/<[^>]*>/g, ' ').replace(/\\s+/g, ' ').trim();\n }\n\n // Fall back to descriptionSections (SonarQube 26+ format)\n if (rule.descriptionSections && rule.descriptionSections.length > 0) {\n // Prefer root_cause section (closest to the old monolithic description)\n const rootCause = rule.descriptionSections.find(s => s.key === 'root_cause');\n if (rootCause) {\n return rootCause.content.replace(/<[^>]*>/g, ' ').replace(/\\s+/g, ' ').trim();\n }\n // If no root_cause, concatenate all sections\n const parts = rule.descriptionSections\n .map(s => s.content.replace(/<[^>]*>/g, ' ').replace(/\\s+/g, ' ').trim())\n .filter(s => s.length > 0);\n if (parts.length > 0) {\n return parts.join('\\n\\n');\n }\n }\n\n return rule.name || '';\n}\n\nfunction extractTags(\n rule: SonarQubeRule | undefined,\n issues: SonarQubeIssue[]\n): {\n cweIds: string[];\n owaspTags: string[];\n allTags: Record<string, string[]>;\n} {\n const cweSet = new Set<string>();\n const owaspSet = new Set<string>();\n const allTagsMap = new Map<string, Set<string>>();\n\n // Extract from rule tags\n if (rule) {\n const ruleTags = [...(rule.tags || []), ...(rule.sysTags || [])];\n\n for (const tag of ruleTags) {\n const lowerTag = tag.toLowerCase();\n\n // Check for CWE tags\n if (lowerTag.startsWith('cwe-') || lowerTag.includes('cwe')) {\n for (const id of extractCWEIDs(tag)) {\n cweSet.add(`CWE-${id}`);\n }\n }\n\n // Check for OWASP tags\n if (lowerTag.includes('owasp')) {\n owaspSet.add(tag);\n }\n\n // Collect other tags by category\n const parts = tag.split(':');\n if (parts.length === 2) {\n const [category, value] = parts;\n if (!allTagsMap.has(category!)) {\n allTagsMap.set(category!, new Set());\n }\n allTagsMap.get(category!)!.add(value!);\n }\n }\n }\n\n // Extract from issue tags\n for (const issue of issues) {\n if (issue.tags) {\n for (const tag of issue.tags) {\n const lowerTag = tag.toLowerCase();\n\n if (lowerTag.startsWith('cwe-')) {\n for (const id of extractCWEIDs(tag)) {\n cweSet.add(`CWE-${id}`);\n }\n }\n\n if (lowerTag.includes('owasp')) {\n owaspSet.add(tag);\n }\n }\n }\n }\n\n // Also parse CWE from rule description\n if (rule?.htmlDesc || rule?.mdDesc) {\n const desc = (rule.htmlDesc || '') + (rule.mdDesc || '');\n for (const id of extractCWEIDs(desc)) {\n cweSet.add(`CWE-${id}`);\n }\n }\n\n // Parse CWE from descriptionSections (SonarQube 26+ format)\n if (rule?.descriptionSections) {\n for (const section of rule.descriptionSections) {\n for (const id of extractCWEIDs(section.content)) {\n cweSet.add(`CWE-${id}`);\n }\n }\n }\n\n const allTags: Record<string, string[]> = {};\n for (const [category, values] of allTagsMap) {\n allTags[category] = Array.from(values);\n }\n\n return {\n cweIds: Array.from(cweSet),\n owaspTags: Array.from(owaspSet),\n allTags,\n };\n}\n\nfunction createResultFromIssue(\n issue: SonarQubeIssue,\n componentMap: Map<string, SonarQubeComponent>\n): RequirementResult {\n const status = issue.status === 'RESOLVED' || issue.status === 'CLOSED'\n ? ResultStatus.Passed\n : ResultStatus.Failed;\n\n const component = componentMap.get(issue.component);\n const componentPath = component?.path || component?.longName || issue.component;\n\n const lineInfo = issue.line ? ` LINE : ${issue.line}` : '';\n const codeDesc = `${componentPath}${lineInfo}`;\n\n return createResult(status, issue.message, {\n codeDesc,\n startTime: new Date(issue.creationDate),\n });\n}\n\nfunction extractSourceLocation(\n issue: SonarQubeIssue,\n componentMap: Map<string, SonarQubeComponent>\n): { ref: string; line: number } | undefined {\n if (!issue.line) {\n return undefined;\n }\n\n const component = componentMap.get(issue.component);\n const ref = component?.path || component?.key || issue.component;\n\n return { ref, line: issue.line };\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n getAwsConfigNistControlByIdentifier,\n getAwsConfigNistControlByName,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport {\n Copyright,\n type EvaluatedBaseline,\n type EvaluatedRequirement,\n type RequirementResult,\n type Checksum,\n type Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n/**\n * AWS Config static export structures.\n * Produced by combining `aws configservice describe-config-rules` with\n * `aws configservice get-compliance-details-by-config-rule`.\n */\ninterface ConfigRulesFile {\n ConfigRules: ConfigRule[];\n}\n\ninterface ConfigRule {\n ConfigRuleId: string;\n ConfigRuleName: string;\n ConfigRuleArn: string;\n Description: string;\n Source: ConfigRuleSource;\n InputParameters: string;\n EvaluationResults: EvaluationResult[];\n}\n\ninterface ConfigRuleSource {\n Owner: string;\n SourceIdentifier: string;\n}\n\ninterface EvaluationResult {\n EvaluationResultIdentifier: EvaluationResultIdentifier;\n ComplianceType: string;\n Annotation?: string;\n ConfigRuleInvokedTime: string;\n ResultRecordedTime: string;\n}\n\ninterface EvaluationResultIdentifier {\n EvaluationResultQualifier: EvaluationResultQualifier;\n}\n\ninterface EvaluationResultQualifier {\n ConfigRuleName: string;\n ResourceType: string;\n ResourceId: string;\n}\n\nconst ARN_RE = /arn:aws[^:]*:config:([^:]+):(\\d{12}):config-rule/;\n\nfunction getAccountId(arn: string): string {\n const m = ARN_RE.exec(arn);\n return m ? m[2]! : 'no-account-id';\n}\n\nfunction getRegion(arn: string): string {\n const m = ARN_RE.exec(arn);\n return m ? m[1]! : 'unknown';\n}\n\nfunction mapComplianceStatus(complianceType: string): ResultStatus {\n switch (complianceType) {\n case 'COMPLIANT': return ResultStatus.Passed;\n case 'NON_COMPLIANT': return ResultStatus.Failed;\n case 'NOT_APPLICABLE': return ResultStatus.NotApplicable;\n default: return ResultStatus.NotReviewed; // INSUFFICIENT_DATA etc.\n }\n}\n\nfunction buildNistTags(sourceIdentifier: string, ruleName: string): string[] {\n const byIdentifier = getAwsConfigNistControlByIdentifier(sourceIdentifier);\n if (byIdentifier) return [byIdentifier];\n const byName = getAwsConfigNistControlByName(ruleName);\n if (byName) return [byName];\n return [];\n}\n\nfunction buildCheckText(rule: ConfigRule): string {\n const parts: string[] = [\n `ARN: ${rule.ConfigRuleArn || 'N/A'}`,\n `Source Identifier: ${rule.Source.SourceIdentifier || 'N/A'}`,\n ];\n if (rule.InputParameters && rule.InputParameters !== '{}') {\n const params = rule.InputParameters\n .replace(/[{}\"]/g, '')\n .split(',')\n .map(p => p.trim())\n .filter(Boolean);\n parts.push(...params);\n }\n return parts.join('<br/>');\n}\n\nfunction buildCodeDesc(q: EvaluationResultQualifier): string {\n return `config_rule_name: ${q.ConfigRuleName}, resource_type: ${q.ResourceType}, resource_id: ${q.ResourceId}`;\n}\n\nfunction buildResultMessage(codeDesc: string, annotation: string | undefined, status: ResultStatus): string | undefined {\n if (status !== ResultStatus.Failed) return undefined;\n const text = annotation || 'Rule does not pass rule compliance';\n return `(${codeDesc}): ${text}`;\n}\n\nfunction buildResult(r: EvaluationResult): RequirementResult {\n const q = r.EvaluationResultIdentifier.EvaluationResultQualifier;\n const status = mapComplianceStatus(r.ComplianceType);\n const codeDesc = buildCodeDesc(q);\n const message = buildResultMessage(codeDesc, r.Annotation, status);\n const startTime = r.ConfigRuleInvokedTime ? new Date(r.ConfigRuleInvokedTime) : undefined;\n\n return createResult(status, message ?? codeDesc, {\n codeDesc,\n ...(startTime ? { startTime } : {}),\n });\n}\n\nfunction buildRequirement(rule: ConfigRule): EvaluatedRequirement {\n const nist = buildNistTags(rule.Source.SourceIdentifier, rule.ConfigRuleName);\n const tags: Record<string, unknown> = nist.length > 0 ? { nist } : {};\n\n const descriptions: Description[] = [\n { label: 'default', data: rule.Description },\n { label: 'check', data: buildCheckText(rule) },\n ];\n\n const title = `${getAccountId(rule.ConfigRuleArn)} - ${rule.ConfigRuleName}`;\n const results = rule.EvaluationResults.map(buildResult);\n\n return createRequirement(\n rule.ConfigRuleId,\n title,\n descriptions,\n 0.5,\n results,\n {\n tags,\n sourceLocation: { ref: rule.ConfigRuleArn, line: 1 },\n }\n );\n}\n\n/**\n * Converts an AWS Config static export (ConfigRulesFile JSON) to HDF format.\n *\n * @param input - JSON string produced by combining aws configservice describe-config-rules\n * with get-compliance-details-by-config-rule\n * @returns HDF JSON string\n */\nexport async function convertAwsConfigToHdf(input: string): Promise<string> {\n validateInputSize(input, 'aws-config');\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const data = parseJSON<ConfigRulesFile>(input);\n\n if (!data || typeof data !== 'object') {\n throw new Error('Invalid AWS Config export: not a valid JSON object');\n }\n if (!Array.isArray(data.ConfigRules)) {\n throw new Error('Invalid AWS Config export: ConfigRules field is required');\n }\n\n const { items: limitedRules, truncated: truncatedRules } = limitArray(data.ConfigRules);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedRules) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedRules.length} ConfigRule items (original: ${data.ConfigRules.length})`);\n }\n const requirements = limitedRules.map(buildRequirement);\n\n const baseline: EvaluatedBaseline = {\n ...createMinimalBaseline('AWS Config', requirements, { resultsChecksum }),\n title: 'AWS Config Compliance Results',\n version: '1.0.0',\n maintainer: 'Amazon Web Services',\n } as EvaluatedBaseline;\n\n // Extract account/region from the first rule's ARN for target labels\n const firstArn = limitedRules[0]?.ConfigRuleArn ?? '';\n const accountId = getAccountId(firstArn);\n const region = getRegion(firstArn);\n\n return buildHdfResults({\n generatorName: 'aws-config-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'AWS Config',\n baselines: [baseline],\n components: [{\n type: Copyright.CloudAccount,\n name: `AWS Account ${accountId}`,\n labels: {\n account: accountId,\n region,\n provider: 'aws',\n },\n }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { detectConverter } from '../../../shared/typescript/fingerprint.js';\nimport { registerAllFingerprints } from '../../../shared/typescript/register-all.js';\nimport { convertSarifToHdf } from '../../sarif-to-hdf/typescript/converter.js';\nimport { inputChecksum, limitArray, validateInputSize, mapCWEToNIST, DEFAULT_REMEDIATION_NIST_TAGS, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * gosec JSON output structures\n * See https://github.com/securego/gosec for the full schema.\n */\ninterface GosecReport {\n 'Golang errors': unknown;\n Issues: GosecIssue[];\n Stats: GosecStats;\n GosecVersion: string;\n}\n\ninterface GosecStats {\n files: number;\n lines: number;\n nosec: number;\n found: number;\n}\n\ninterface GosecCWE {\n id: string;\n url: string;\n}\n\ninterface GosecSuppression {\n kind: string;\n justification: string;\n}\n\ninterface GosecIssue {\n severity: string;\n confidence: string;\n cwe: GosecCWE;\n rule_id: string;\n details: string;\n file: string;\n code: string;\n line: string;\n column: string;\n nosec: boolean;\n suppressions: GosecSuppression[] | null;\n}\n\n/**\n * Severity to HDF impact mapping for gosec.\n */\nconst IMPACT_MAPPING: Record<string, number> = {\n HIGH: 0.7,\n MEDIUM: 0.5,\n LOW: 0.3,\n};\n\n\n/**\n * Returns true if the issue is suppressed (via nosec flag or suppressions list).\n */\nfunction isSuppressed(issue: GosecIssue): boolean {\n return issue.nosec || issue.suppressions !== null;\n}\n\n/**\n * Builds a skip message from a suppressions list.\n * Returns undefined when suppressions is null (issue not suppressed via list).\n */\nfunction formatSkipMessage(suppressions: GosecSuppression[] | null): string | undefined {\n if (suppressions === null) {\n return undefined;\n }\n if (suppressions.length === 0) {\n return 'No justification provided';\n }\n return suppressions\n .map(s => `${s.justification || 'No justification provided'} (${s.kind})`)\n .join('\\n');\n}\n\n/**\n * Converts a single GosecIssue to an HDF RequirementResult.\n */\nfunction issueToResult(issue: GosecIssue): RequirementResult {\n const suppressed = isSuppressed(issue);\n const status = suppressed ? ResultStatus.NotReviewed : ResultStatus.Failed;\n\n let message: string;\n if (suppressed) {\n const skipMsg = formatSkipMessage(issue.suppressions);\n message = skipMsg ?? 'No justification provided';\n } else {\n message = `${issue.confidence} confidence of rule violation at:\\n${issue.code}`;\n }\n\n const codeDesc = `Rule ${issue.rule_id} violation detected at:\\nFile: ${issue.file}\\nLine: ${issue.line}\\nColumn: ${issue.column}`;\n\n return createResult(status, message, { codeDesc });\n}\n\n/**\n * Converts a group of issues sharing a rule_id into one EvaluatedRequirement.\n */\nfunction buildRequirement(ruleId: string, issues: GosecIssue[]): EvaluatedRequirement {\n const rep = issues[0]!;\n const impact = IMPACT_MAPPING[rep.severity.toUpperCase()] ?? 0.5;\n const nist = mapCWEToNIST([rep.cwe.id], DEFAULT_REMEDIATION_NIST_TAGS);\n\n const tags: Record<string, unknown> = {\n nist,\n cwe: { id: rep.cwe.id, url: rep.cwe.url },\n };\n\n const results = issues.map(issueToResult);\n\n const descriptions: Description[] = [\n { label: 'default', data: rep.details },\n { label: 'check', data: `CWE-${rep.cwe.id}: ${rep.cwe.url}` },\n ];\n\n return createRequirement(ruleId, rep.details, descriptions, impact, results, { tags });\n}\n\n/**\n * Converts gosec output to HDF format.\n * Accepts both native gosec JSON and SARIF format — SARIF input is detected\n * automatically and delegated to the shared SARIF converter.\n *\n * @param input - gosec JSON or SARIF string\n * @returns HDF JSON string\n */\nexport async function convertGosecToHdf(input: string): Promise<string> {\n validateInputSize(input, 'gosec');\n // Detect format: if SARIF, delegate to the shared SARIF converter\n registerAllFingerprints();\n const detected = detectConverter(input);\n if (detected && detected.fingerprint.id === 'sarif-to-hdf') {\n return convertSarifToHdf(input);\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const report = parseJSON<GosecReport>(input);\n\n if (!report || typeof report !== 'object') {\n throw new Error('Invalid gosec structure: not a valid JSON object');\n }\n\n if (!Array.isArray(report.Issues)) {\n throw new Error('Invalid gosec structure: missing or invalid Issues field');\n }\n\n // Group issues by rule_id, preserving insertion order.\n const { items: limitedIssues, truncated: truncatedIssues } = limitArray(report.Issues);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedIssues) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedIssues.length} issue items (original: ${report.Issues.length})`);\n }\n const groups = new Map<string, GosecIssue[]>();\n for (const issue of limitedIssues) {\n const existing = groups.get(issue.rule_id);\n if (existing) {\n existing.push(issue);\n } else {\n groups.set(issue.rule_id, [issue]);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [ruleId, issues] of groups) {\n requirements.push(buildRequirement(ruleId, issues));\n }\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'gosec Scan',\n requirements,\n { resultsChecksum }\n ) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'gosec-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'gosec',\n toolVersion: report.GosecVersion || undefined,\n baselines: [baseline],\n timestamp: new Date(),\n });\n}\n","import {\n type Checksum,\n Copyright,\n createMinimalBaseline,\n type EvaluatedBaseline,\n type EvaluatedRequirement,\n type RequirementResult,\n ResultStatus,\n} from '@mitre/hdf-schema';\nimport {\n getNiktoNistControl,\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport {parseJSON} from '@mitre/hdf-utilities';\nimport {inputChecksum, buildNistCciTags, limitArray, validateInputSize, buildHdfResults} from '../../../shared/typescript/converterutil.js';\n\n// Nikto JSON input types\n\ninterface NiktoReport {\n banner?: string;\n host?: string;\n ip?: string;\n port?: string;\n vulnerabilities: NiktoVulnerability[];\n}\n\ninterface NiktoVulnerability {\n OSVDB?: string;\n id: string;\n method?: string;\n msg: string;\n url?: string;\n}\n\nfunction buildNistTags(niktoId: string): string[] {\n const control = getNiktoNistControl(niktoId);\n if (control) {\n return [control];\n }\n return [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n}\n\nfunction buildCodeDesc(vuln: NiktoVulnerability): string {\n const parts: string[] = [];\n if (vuln.url) {\n parts.push(`URL: ${vuln.url}`);\n }\n if (vuln.method) {\n parts.push(`Method: ${vuln.method}`);\n }\n return parts.join(' ');\n}\n\nfunction convertVulnToRequirement(vuln: NiktoVulnerability): EvaluatedRequirement {\n const nistTags = buildNistTags(vuln.id);\n const cciTags = nistToCci(nistTags);\n\n const result: RequirementResult = {\n status: ResultStatus.Failed,\n codeDesc: buildCodeDesc(vuln),\n startTime: new Date('0001-01-01T00:00:00Z'),\n };\n\n const extras: Record<string, unknown> = {};\n if (vuln.OSVDB && vuln.OSVDB !== '0') {\n extras.osvdb = vuln.OSVDB;\n }\n const tags = buildNistCciTags(nistTags, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n return {\n id: vuln.id,\n title: vuln.msg,\n impact: 0.5,\n results: [result],\n tags,\n descriptions: [\n {label: 'default', data: vuln.msg},\n ],\n };\n}\n\nexport async function convertNiktoToHdf(input: string): Promise<string> {\n validateInputSize(input, 'nikto');\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const niktoData = parseJSON<NiktoReport>(input);\n\n // Group vulnerabilities by ID to handle duplicates\n const vulnGroups = new Map<string, NiktoVulnerability[]>();\n if (niktoData.vulnerabilities) {\n const { items: limitedVulns, truncated: truncatedVulns } = limitArray(niktoData.vulnerabilities);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedVulns) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${niktoData.vulnerabilities.length})`);\n }\n for (const vuln of limitedVulns) {\n const existing = vulnGroups.get(vuln.id);\n if (existing) {\n existing.push(vuln);\n } else {\n vulnGroups.set(vuln.id, [vuln]);\n }\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [, vulns] of vulnGroups) {\n // Use first vuln for the requirement definition\n const primary = vulns[0]!;\n const req = convertVulnToRequirement(primary);\n\n // Add results from duplicate IDs\n if (vulns.length > 1) {\n for (let i = 1; i < vulns.length; i++) {\n req.results.push({\n status: ResultStatus.Failed,\n codeDesc: buildCodeDesc(vulns[i]!),\n startTime: new Date('0001-01-01T00:00:00Z'),\n });\n }\n }\n\n requirements.push(req);\n }\n\n const targetParts: string[] = [];\n if (niktoData.host) {\n targetParts.push(`Host: ${niktoData.host}`);\n }\n if (niktoData.port) {\n targetParts.push(`Port: ${niktoData.port}`);\n }\n const targetName = targetParts.length > 0 ? targetParts.join(' ') : 'Nikto Scan';\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(targetName, requirements, {\n resultsChecksum,\n title: `Nikto Target: ${targetName}`,\n summary: niktoData.banner || '',\n }) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'nikto-to-hdf',\n converterVersion: 'unknown',\n toolName: 'Nikto',\n toolFormat: 'JSON',\n baselines: [baseline],\n components: [{\n type: Copyright.Application,\n name: targetName,\n }],\n });\n}\n","import {\n type Checksum,\n createMinimalBaseline,\n Copyright,\n type Tool,\n type EvaluatedBaseline,\n type EvaluatedRequirement,\n type RequirementResult,\n type HdfResults,\n ResultStatus,\n} from '@mitre/hdf-schema';\nimport {\n getCweNistControl,\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport {parseJSON} from '@mitre/hdf-utilities';\nimport {detectConverter} from '../../../shared/typescript/fingerprint.js';\nimport {registerAllFingerprints} from '../../../shared/typescript/register-all.js';\nimport {convertSarifToHdf} from '../../sarif-to-hdf/typescript/converter.js';\nimport {inputChecksum, buildNistCciTags, limitArray, stripHTML, validateInputSize} from '../../../shared/typescript/converterutil.js';\n\n// --- ZAP JSON input types ---\n\ninterface ZapReport {\n '@generated'?: string;\n '@version'?: string;\n site?: ZapSite[];\n}\n\ninterface ZapSite {\n '@host'?: string;\n '@name'?: string;\n '@port'?: string;\n '@ssl'?: string;\n alerts?: ZapAlert[];\n}\n\ninterface ZapAlert {\n pluginid: string;\n name: string;\n alert?: string;\n cweid?: string;\n wascid?: string;\n riskcode?: string;\n riskdesc?: string;\n confidence?: string;\n count?: string;\n desc?: string;\n solution?: string;\n otherinfo?: string;\n reference?: string;\n sourceid?: string;\n instances?: ZapInstance[];\n}\n\ninterface ZapInstance {\n uri?: string;\n method?: string;\n param?: string;\n evidence?: string;\n attack?: string;\n}\n\n// --- Risk code to impact ---\n\nfunction riskCodeToImpact(riskCode: string): number {\n switch (riskCode) {\n case '0':\n case '1':\n return 0.3;\n case '2':\n return 0.5;\n case '3':\n return 0.7;\n default:\n return 0.5;\n }\n}\n\n// --- NIST tag building ---\n\nfunction buildNistTags(cweid: string): string[] {\n if (cweid && cweid !== '0') {\n const cweNum = parseInt(cweid, 10);\n if (!isNaN(cweNum)) {\n const control = getCweNistControl(cweNum);\n if (control) {\n return [control];\n }\n }\n }\n return [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n}\n\n// --- Instance to code desc ---\n\nfunction buildCodeDesc(instance: ZapInstance): string {\n const parts: string[] = [];\n if (instance.uri) {\n parts.push(`URI: ${instance.uri}`);\n }\n if (instance.method) {\n parts.push(`Method: ${instance.method}`);\n }\n if (instance.param) {\n parts.push(`Param: ${instance.param}`);\n }\n if (instance.evidence) {\n parts.push(`Evidence: ${instance.evidence}`);\n }\n return parts.join(' | ');\n}\n\n// --- Build check description ---\n\nfunction buildCheckDescription(alert: ZapAlert): string {\n const parts: string[] = [];\n if (alert.solution) {\n const stripped = stripHTML(alert.solution);\n if (stripped) {\n parts.push(stripped);\n }\n }\n if (alert.otherinfo) {\n const stripped = stripHTML(alert.otherinfo);\n if (stripped) {\n parts.push(stripped);\n }\n }\n return parts.join('\\n');\n}\n\n// --- Select site with most alerts ---\n\nfunction selectSite(sites: ZapSite[]): ZapSite | undefined {\n if (sites.length === 0) return undefined;\n let best = sites[0]!;\n for (let i = 1; i < sites.length; i++) {\n const site = sites[i]!;\n if ((site.alerts?.length ?? 0) > (best.alerts?.length ?? 0)) {\n best = site;\n }\n }\n return best;\n}\n\n// --- Main converter ---\n\nexport async function convertZapToHdf(input: string): Promise<string> {\n validateInputSize(input, 'zap');\n // SARIF routing — delegate to the shared SARIF converter\n registerAllFingerprints();\n const detected = detectConverter(input);\n if (detected && detected.fingerprint.id === 'sarif-to-hdf') {\n return convertSarifToHdf(input);\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const zapData = parseJSON<ZapReport>(input);\n\n // Validate basic structure\n if (!zapData.site || !Array.isArray(zapData.site)) {\n // Empty report — produce empty HDF\n const baseline: EvaluatedBaseline = createMinimalBaseline('OWASP ZAP Scan', [], {\n resultsChecksum,\n title: 'OWASP ZAP Scan',\n summary: '',\n }) as EvaluatedBaseline;\n\n const hdf: HdfResults = {\n baselines: [baseline],\n generator: {name: 'zap-to-hdf', version: 'unknown'},\n tool: {name: 'OWASP ZAP', format: 'JSON'},\n };\n return JSON.stringify(hdf, null, 2);\n }\n\n // Select site with most alerts\n const site = selectSite(zapData.site);\n if (!site) {\n // Empty site array — produce empty HDF\n const baseline: EvaluatedBaseline = createMinimalBaseline('OWASP ZAP Scan', [], {\n resultsChecksum,\n title: 'OWASP ZAP Scan',\n summary: `ZAP Version ${zapData['@version'] ?? 'unknown'}`,\n }) as EvaluatedBaseline;\n\n const hdf: HdfResults = {\n baselines: [baseline],\n generator: {name: 'zap-to-hdf', version: 'unknown'},\n tool: {name: 'OWASP ZAP', format: 'JSON'},\n };\n if (zapData['@generated']) {\n hdf.timestamp = new Date(zapData['@generated']);\n }\n return JSON.stringify(hdf, null, 2);\n }\n\n const alerts = site.alerts ?? [];\n\n // Deduplicate by pluginid — append .1, .2 for duplicates\n const pluginIdCount = new Map<string, number>();\n const {items: limitedAlerts, truncated} = limitArray(alerts);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedAlerts.length} alert items (original: ${alerts.length})`);\n }\n\n const requirements: EvaluatedRequirement[] = [];\n\n for (const alert of limitedAlerts) {\n // Deduplicate pluginid\n const count = pluginIdCount.get(alert.pluginid) ?? 0;\n pluginIdCount.set(alert.pluginid, count + 1);\n const reqId = count === 0 ? alert.pluginid : `${alert.pluginid}.${count}`;\n\n // Build NIST tags\n const nistTags = buildNistTags(alert.cweid ?? '');\n const cciTags = nistToCci(nistTags);\n\n // Build extra tags\n const extras: Record<string, unknown> = {};\n if (alert.cweid) {\n extras.cweid = alert.cweid;\n }\n if (alert.wascid) {\n extras.wascid = alert.wascid;\n }\n if (alert.riskdesc) {\n extras.riskdesc = alert.riskdesc;\n }\n if (alert.confidence) {\n extras.confidence = alert.confidence;\n }\n const tags = buildNistCciTags(nistTags, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n // Build results from instances\n const results: RequirementResult[] = [];\n if (alert.instances && alert.instances.length > 0) {\n const {items: limitedInstances, truncated: instTruncated} = limitArray(alert.instances);\n if (instTruncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Instances truncated at ${limitedInstances.length} for alert ${alert.pluginid}`);\n }\n for (const instance of limitedInstances) {\n const result: RequirementResult = {\n status: ResultStatus.Failed,\n codeDesc: buildCodeDesc(instance),\n startTime: new Date('0001-01-01T00:00:00Z'),\n };\n if (instance.attack) {\n result.message = instance.attack;\n }\n results.push(result);\n }\n }\n\n // Build descriptions\n const descriptions: Array<{label: string; data: string}> = [];\n if (alert.desc) {\n descriptions.push({label: 'default', data: stripHTML(alert.desc)});\n }\n const checkDesc = buildCheckDescription(alert);\n if (checkDesc) {\n descriptions.push({label: 'check', data: checkDesc});\n }\n\n const impact = riskCodeToImpact(alert.riskcode ?? '');\n\n const req: EvaluatedRequirement = {\n id: reqId,\n title: alert.name,\n impact,\n results,\n tags,\n descriptions,\n };\n\n requirements.push(req);\n }\n\n const targetName = site['@host'] ?? 'Unknown Host';\n const siteName = site['@name'] ?? targetName;\n const baselineName = `OWASP ZAP Scan of ${siteName}`;\n\n const baseline: EvaluatedBaseline = createMinimalBaseline('OWASP ZAP Scan', requirements, {\n resultsChecksum,\n title: baselineName,\n summary: `ZAP Version ${zapData['@version'] ?? 'unknown'}`,\n }) as EvaluatedBaseline;\n\n const tool: Tool = {\n name: 'OWASP ZAP',\n format: 'JSON',\n };\n if (zapData['@version']) {\n tool.version = zapData['@version'];\n }\n\n // Build components — ZAP is a DAST tool scanning web applications\n const components: Array<{name: string; type: Copyright; url?: string; labels?: Record<string, string>}> = [];\n if (site['@name']) {\n components.push({name: targetName, type: Copyright.Application, url: site['@name']});\n } else if (targetName !== 'Unknown Host') {\n components.push({name: targetName, type: Copyright.Application});\n }\n\n const hdf: HdfResults = {\n baselines: [baseline],\n components,\n generator: {\n name: 'zap-to-hdf',\n version: 'unknown',\n },\n tool,\n };\n\n if (zapData['@generated']) {\n hdf.timestamp = new Date(zapData['@generated']);\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, mapCWEToNIST, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n severityToImpact,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * CycloneDX JSON structures (subset relevant to vulnerability mapping)\n */\ninterface CycloneDXBom {\n bomFormat: string;\n specVersion: string;\n metadata?: CycloneDXMetadata;\n components?: CycloneDXComponent[];\n vulnerabilities?: CycloneDXVulnerability[];\n}\n\ninterface CycloneDXMetadata {\n timestamp?: string;\n component?: CycloneDXMetadataComponent;\n}\n\ninterface CycloneDXMetadataComponent {\n type?: string;\n name?: string;\n version?: string;\n 'bom-ref'?: string;\n}\n\ninterface CycloneDXComponent {\n type: string;\n name: string;\n version?: string;\n group?: string;\n 'bom-ref'?: string;\n components?: CycloneDXComponent[];\n}\n\ninterface CycloneDXVulnerability {\n id: string;\n source?: CycloneDXSource;\n ratings?: CycloneDXRating[];\n cwes?: number[];\n description?: string;\n detail?: string;\n recommendation?: string;\n affects?: CycloneDXAffect[];\n analysis?: CycloneDXAnalysis;\n}\n\ninterface CycloneDXSource {\n name?: string;\n url?: string;\n}\n\ninterface CycloneDXRating {\n source?: CycloneDXSource;\n score?: number;\n severity?: string;\n method?: string;\n vector?: string;\n}\n\ninterface CycloneDXAffect {\n ref: string;\n}\n\ninterface CycloneDXAnalysis {\n state?: string;\n justification?: string;\n response?: string[];\n detail?: string;\n}\n\nconst CVSS_METHODS = new Set([\n 'CVSSv2',\n 'CVSSv3',\n 'CVSSv31',\n 'CVSSv4',\n]);\n\n// NOTE: heimdall2 mapped info/unknown severity to NotReviewed status.\n// We intentionally do NOT replicate that — a vulnerability is a finding\n// regardless of severity confidence. Info/unknown severity vulns are Failed\n// with impact from the severity mapping (info→0.1, unknown→0.5).\n\n/**\n * Computes the maximum impact across all ratings for a vulnerability.\n * Prefers CVSS score/10 when available, falls back to severityToImpact().\n */\nfunction maxImpact(ratings: CycloneDXRating[]): number {\n if (ratings.length === 0) {\n return 0.5;\n }\n\n let max = 0;\n for (const rating of ratings) {\n let impact: number;\n if (\n rating.method &&\n CVSS_METHODS.has(rating.method) &&\n rating.score !== undefined &&\n rating.score !== null\n ) {\n impact = rating.score / 10;\n } else {\n impact = severityToImpact(rating.severity ?? 'medium');\n }\n if (impact > max) {\n max = impact;\n }\n }\n return max;\n}\n\n\n/**\n * Formats the ratings as a human-readable tag string.\n */\nfunction formatRatingsTag(ratings: CycloneDXRating[]): string {\n return ratings\n .map((r) => `${r.source?.name ?? 'Unknown'} - ${r.severity ?? 'unrated'}`)\n .join(', ');\n}\n\n/**\n * Formats a component reference as a code_desc string.\n */\nfunction formatCodeDesc(\n componentLookup: Map<string, CycloneDXComponent>,\n ref: string\n): string {\n const comp = componentLookup.get(ref);\n if (!comp) {\n // VEX case: no matching component, use the ref directly\n return `Component ${ref} is vulnerable`;\n }\n\n let name = '';\n if (comp.group) {\n name += comp.group + '/';\n }\n name += comp.name;\n if (comp.version) {\n name += '@' + comp.version;\n }\n return `Component ${name} is vulnerable`;\n}\n\n/**\n * Flattens nested CycloneDX components into a single array.\n */\nfunction flattenComponents(components: CycloneDXComponent[]): CycloneDXComponent[] {\n const result: CycloneDXComponent[] = [];\n for (const comp of components) {\n result.push(comp);\n if (comp.components) {\n result.push(...flattenComponents(comp.components));\n }\n }\n return result;\n}\n\n/**\n * Converts CycloneDX SBOM/VEX JSON to HDF format.\n *\n * @param input - CycloneDX JSON string\n * @returns HDF JSON string\n */\nexport async function convertCyclonedxToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('cyclonedx: empty input');\n }\n validateInputSize(input, 'cyclonedx');\n\n const bom = parseJSON<CycloneDXBom>(input);\n\n if (!bom || typeof bom !== 'object') {\n throw new Error('cyclonedx: invalid JSON');\n }\n\n if (bom.bomFormat !== 'CycloneDX') {\n throw new Error(\n `cyclonedx: missing or invalid bomFormat (expected \"CycloneDX\", got \"${bom.bomFormat ?? 'undefined'}\")`\n );\n }\n\n if (\n (!bom.components || bom.components.length === 0) &&\n (!bom.vulnerabilities || bom.vulnerabilities.length === 0)\n ) {\n throw new Error(\n 'cyclonedx: input has neither components nor vulnerabilities'\n );\n }\n\n if (!bom.vulnerabilities || bom.vulnerabilities.length === 0) {\n throw new Error(\n 'cyclonedx: this file is an SBOM inventory with no vulnerabilities; ' +\n 'to import SBOM data into a system document, use:\\n' +\n ' hdf system create --from <sbom-file> --component-name <name>'\n );\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Flatten nested components and build lookup by bom-ref\n const allComponents = flattenComponents(bom.components ?? []);\n const componentLookup = new Map<string, CycloneDXComponent>();\n for (const comp of allComponents) {\n if (comp['bom-ref']) {\n componentLookup.set(comp['bom-ref'], comp);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n\n const { items: limitedVulns, truncated: truncatedVulns } = limitArray(bom.vulnerabilities ?? []);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedVulns) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${(bom.vulnerabilities ?? []).length})`);\n }\n for (const vuln of limitedVulns) {\n const ratings = vuln.ratings ?? [];\n const impact = maxImpact(ratings);\n const cwes = vuln.cwes ?? [];\n const nist = mapCWEToNIST(cwes.map(c => `${c}`), DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n const tags: Record<string, unknown> = {\n nist,\n cci: cciTags,\n };\n\n if (cwes.length > 0) {\n tags['cweid'] = cwes.map((c) => `CWE-${c}`);\n }\n\n if (ratings.length > 0) {\n tags['ratings'] = formatRatingsTag(ratings);\n }\n\n // Build descriptions (must always include a 'default' label per HDF schema)\n const descriptions: Description[] = [];\n\n // Default description: description + detail\n const defaultParts: string[] = [];\n if (vuln.description) {\n defaultParts.push(`Description: ${vuln.description}`);\n }\n if (vuln.detail) {\n defaultParts.push(`Detail: ${vuln.detail}`);\n }\n if (defaultParts.length > 0) {\n descriptions.push({ label: 'default', data: defaultParts.join('\\n\\n') });\n } else {\n descriptions.push({ label: 'default', data: vuln.id });\n }\n\n // Fix description: recommendation + workaround from analysis\n const fixParts: string[] = [];\n if (vuln.recommendation) {\n fixParts.push(vuln.recommendation);\n }\n if (vuln.analysis?.detail) {\n fixParts.push(`Workaround: ${vuln.analysis.detail}`);\n }\n if (fixParts.length > 0) {\n descriptions.push({ label: 'fix', data: fixParts.join('\\n\\n') });\n }\n\n // Build results: one per affected component.\n // All vulnerabilities are Failed — info/unknown severity affects impact\n // score but not status.\n const affects = vuln.affects ?? [];\n const results =\n affects.length > 0\n ? affects.map((affect) =>\n createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatCodeDesc(componentLookup, affect.ref),\n })\n )\n : [\n createResult(ResultStatus.Failed, undefined, {\n codeDesc: `Vulnerability ${vuln.id}`,\n }),\n ];\n\n const title = vuln.source?.name\n ? `${vuln.id} (${vuln.source.name})`\n : vuln.id;\n\n requirements.push(\n createRequirement(vuln.id, title, descriptions, impact, results, { tags })\n );\n }\n\n const baseline = createMinimalBaseline('CycloneDX Scan', requirements, {\n resultsChecksum,\n }) as EvaluatedBaseline;\n\n const targetName = bom.metadata?.component?.name ?? '';\n\n return buildHdfResults({\n generatorName: 'cyclonedx-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'CycloneDX',\n toolFormat: 'JSON',\n baselines: [baseline],\n components: [{ name: targetName, type: Copyright.Application }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { buildCsv } from '@mitre/hdf-utilities';\nimport type { HdfResults, EvaluatedBaseline, EvaluatedRequirement, Component, Description } from '@mitre/hdf-schema';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\n\n/**\n * Row structure for CSV export\n */\ninterface CsvRow {\n 'Baseline ID': string;\n 'Baseline Version': string;\n 'Baseline Title': string;\n 'Target ID': string;\n 'Target Type': string;\n 'Requirement ID': string;\n 'Requirement Title': string;\n 'Description': string;\n 'Severity': string;\n 'Impact': number;\n 'Status': string;\n 'NIST Controls': string;\n 'CCI Controls': string;\n 'Result Message': string;\n}\n\n/**\n * Convert HDF JSON to CSV format\n * @param input HDF JSON string\n * @returns CSV string with sanitized output\n */\nexport function convertHdfToCsv(input: string): string {\n validateInputSize(input, 'hdf-to-csv');\n const hdf = parseJSON<HdfResults>(input);\n\n if (!hdf || typeof hdf !== 'object' || !('baselines' in hdf)) {\n throw new Error('Invalid HDF structure: missing baselines field');\n }\n\n if (!Array.isArray(hdf.baselines)) {\n throw new Error('Invalid HDF structure: baselines must be an array');\n }\n\n const rows: CsvRow[] = [];\n\n // Get components array (may be empty or undefined)\n const components = hdf.components || [];\n\n // If no components, create a single default target entry\n const targetList: Array<{ name: string; type: string }> = components.length > 0\n ? components.map((t: Component) => ({ name: t.name, type: t.type }))\n : [{ name: '', type: '' }];\n\n // Iterate through each baseline\n for (const baseline of hdf.baselines) {\n // Iterate through each requirement in the baseline\n for (const requirement of baseline.requirements) {\n // Create a row for each target\n for (const target of targetList) {\n rows.push(createRow(baseline, requirement, target));\n }\n }\n }\n\n // Convert to CSV with sanitization enabled\n return buildCsv(rows, { sanitize: true });\n}\n\n/**\n * Create a CSV row from baseline, requirement, and target data\n */\nfunction createRow(\n baseline: EvaluatedBaseline,\n requirement: EvaluatedRequirement,\n target: { name: string; type: string }\n): CsvRow {\n // Get default description (required to be present per schema)\n const defaultDesc = requirement.descriptions.find((d: Description) => d.label === 'default');\n const description = defaultDesc?.data || '';\n\n // Get severity from tags or derive from impact\n const severity = getSeverity(requirement);\n\n // Get status from first result (results is required, minItems: 1 per schema)\n const firstResult = requirement.results[0];\n const status = firstResult?.status || '';\n const message = firstResult?.message || '';\n\n // Extract NIST and CCI controls from tags\n const nistControls = extractArrayFromTags(requirement.tags, 'nist');\n const cciControls = extractArrayFromTags(requirement.tags, 'cci');\n\n return {\n 'Baseline ID': baseline.name,\n 'Baseline Version': baseline.version || '',\n 'Baseline Title': baseline.title || '',\n 'Target ID': target.name,\n 'Target Type': target.type,\n 'Requirement ID': requirement.id,\n 'Requirement Title': requirement.title || '',\n 'Description': description,\n 'Severity': severity,\n 'Impact': requirement.impact,\n 'Status': String(status),\n 'NIST Controls': nistControls,\n 'CCI Controls': cciControls,\n 'Result Message': message\n };\n}\n\n/**\n * Get severity from requirement tags or derive from impact\n */\nfunction getSeverity(requirement: EvaluatedRequirement): string {\n // Check if severity is explicitly provided in tags\n if (requirement.tags && typeof requirement.tags === 'object') {\n if ('severity' in requirement.tags) {\n const sev = requirement.tags.severity;\n if (typeof sev === 'string') {\n return sev;\n }\n if (Array.isArray(sev) && sev.length > 0) {\n return String(sev[0]);\n }\n }\n }\n\n // Derive from impact if not provided\n const impact = requirement.impact;\n if (impact >= 0.7) return 'high';\n if (impact >= 0.4) return 'medium';\n return 'low';\n}\n\n/**\n * Extract array values from tags object and join with semicolons\n */\nfunction extractArrayFromTags(\n tags: Record<string, unknown>,\n key: string\n): string {\n if (!tags || typeof tags !== 'object') {\n return '';\n }\n\n const value = tags[key];\n if (Array.isArray(value)) {\n return value.map(v => String(v)).join('; ');\n }\n\n return '';\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { inputChecksum, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Description,\n RequirementGroup,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createDescription,\n createResult,\n} from '@mitre/hdf-schema';\n\n/**\n * Splunk event metadata. Each event emitted by the HDF-to-Splunk pipeline\n * carries a `meta` object that describes the event's role.\n */\ninterface SplunkMeta {\n guid: string;\n subtype: 'header' | 'profile' | 'control';\n hdf_splunk_schema: string;\n filetype: string;\n filename: string;\n profile_sha256?: string;\n status?: string;\n is_baseline?: boolean;\n is_waived?: boolean;\n overlay_depth?: number;\n}\n\ninterface SplunkEvent {\n meta: SplunkMeta;\n [key: string]: unknown;\n}\n\ninterface SplunkHeader extends SplunkEvent {\n profiles: unknown[];\n platform: { name: string; release: string };\n statistics: Record<string, unknown>;\n version: string;\n}\n\ninterface SplunkProfile extends SplunkEvent {\n name: string;\n title: string;\n sha256: string;\n version: string;\n summary?: string;\n copyright?: string;\n maintainer?: string;\n license?: string;\n supports: unknown[];\n groups: Array<{ id: string; controls: string[] }>;\n attributes: unknown[];\n controls: unknown[];\n}\n\ninterface SplunkControl extends SplunkEvent {\n id: string;\n title: string;\n desc: string;\n descriptions: Record<string, string>;\n impact: number;\n code: string;\n tags: Record<string, unknown>;\n results: SplunkResult[];\n refs: unknown[];\n source_location?: { ref: string; line: number };\n}\n\ninterface SplunkResult {\n status: string;\n code_desc: string;\n message?: string;\n start_time: string;\n run_time?: number;\n skip_message?: string;\n exception?: string;\n backtrace?: string[];\n resource?: string;\n}\n\n/**\n * Map a Splunk result status string to the HDF ResultStatus enum.\n */\nfunction mapStatus(status: string): ResultStatus {\n switch (status.toLowerCase()) {\n case 'passed':\n return ResultStatus.Passed;\n case 'failed':\n return ResultStatus.Failed;\n case 'skipped':\n return ResultStatus.NotReviewed;\n case 'error':\n return ResultStatus.Error;\n default:\n return ResultStatus.NotReviewed;\n }\n}\n\n/**\n * Convert a Splunk descriptions object (`{ key: value }`) to an array of\n * HDF Description objects.\n */\nfunction convertDescriptions(\n descriptions: Record<string, string> | undefined,\n): Description[] {\n if (!descriptions || typeof descriptions !== 'object') {\n return [];\n }\n return Object.entries(descriptions).map(([label, data]) =>\n createDescription(label, data),\n );\n}\n\n/**\n * Convert Splunk profile groups (which use `controls`) to HDF\n * RequirementGroups (which use `requirements`).\n */\nfunction convertGroups(\n groups: Array<{ id: string; controls: string[] }> | undefined,\n): RequirementGroup[] {\n if (!groups || !Array.isArray(groups)) {\n return [];\n }\n return groups.map((g) => ({\n id: g.id,\n requirements: g.controls,\n }));\n}\n\n/**\n * Convert a Splunk JSON event array back into an HDF Results document.\n *\n * Input is a JSON string containing an array of Splunk events previously\n * produced by the HDF-to-Splunk pipeline. Each event carries a `meta.subtype`\n * of \"header\", \"profile\", or \"control\" and a shared `meta.guid` that ties\n * them together.\n *\n * @param input - JSON string of a SplunkEvent array\n * @returns HDF Results JSON string\n */\nexport async function convertSplunkToHdf(input: string): Promise<string> {\n validateInputSize(input, 'splunk');\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const events = parseJSON<SplunkEvent[]>(input);\n\n if (!Array.isArray(events) || events.length === 0) {\n throw new Error('No Splunk events found in input');\n }\n\n // Group events by GUID (each GUID represents one original HDF execution)\n const eventsByGuid = new Map<string, SplunkEvent[]>();\n for (const event of events) {\n const guid = event.meta.guid;\n if (!eventsByGuid.has(guid)) {\n eventsByGuid.set(guid, []);\n }\n eventsByGuid.get(guid)!.push(event);\n }\n\n // Process each GUID group into baselines + components\n const allBaselines: EvaluatedBaseline[] = [];\n let targetName = 'unknown';\n let targetRelease = '';\n\n for (const [, guidEvents] of eventsByGuid) {\n const headers: SplunkHeader[] = [];\n const profiles: SplunkProfile[] = [];\n const controls: SplunkControl[] = [];\n\n for (const event of guidEvents) {\n switch (event.meta.subtype) {\n case 'header':\n headers.push(event as SplunkHeader);\n break;\n case 'profile':\n profiles.push(event as SplunkProfile);\n break;\n case 'control':\n controls.push(event as SplunkControl);\n break;\n }\n }\n\n if (headers.length !== 1) {\n throw new Error(\n `Expected 1 header event, got ${headers.length}`,\n );\n }\n\n const header = headers[0]!;\n targetName = header.platform.name;\n targetRelease = header.platform.release;\n\n // Group controls by their profile_sha256\n const controlsByProfile = new Map<string, SplunkControl[]>();\n for (const control of controls) {\n const sha = control.meta.profile_sha256 ?? '';\n if (!controlsByProfile.has(sha)) {\n controlsByProfile.set(sha, []);\n }\n controlsByProfile.get(sha)!.push(control);\n }\n\n // Build a baseline for each profile event\n for (const profile of profiles) {\n const profileControls = controlsByProfile.get(profile.sha256) ?? [];\n\n const requirements: EvaluatedRequirement[] = profileControls.map(\n (control) => {\n const descriptions = convertDescriptions(control.descriptions);\n\n const results: RequirementResult[] = Array.isArray(control.results)\n ? control.results.map((result) =>\n createResult(mapStatus(result.status), result.message, {\n codeDesc: result.code_desc,\n startTime: new Date(result.start_time),\n runTime: result.run_time,\n exception: result.exception,\n backtrace: result.backtrace,\n }),\n )\n : [];\n\n const options: {\n tags: Record<string, unknown>;\n sourceLocation?: { ref: string; line: number };\n } = {\n tags: control.tags ?? {},\n };\n\n if (control.source_location) {\n options.sourceLocation = control.source_location;\n }\n\n return createRequirement(\n control.id,\n control.title,\n descriptions,\n control.impact,\n results,\n options,\n );\n },\n );\n\n const groups = convertGroups(profile.groups);\n\n const baselineOptions: {\n title?: string;\n version?: string;\n summary?: string;\n groups?: RequirementGroup[];\n resultsChecksum: Checksum;\n } = {\n resultsChecksum,\n };\n\n if (profile.title) {\n baselineOptions.title = profile.title;\n }\n if (profile.version) {\n baselineOptions.version = profile.version;\n }\n if (profile.summary) {\n baselineOptions.summary = profile.summary;\n }\n if (groups.length > 0) {\n baselineOptions.groups = groups;\n }\n\n allBaselines.push(\n createMinimalBaseline(profile.name, requirements, baselineOptions),\n );\n }\n }\n\n const hdf: HdfResults = {\n baselines: allBaselines,\n components: [\n {\n name: targetName,\n type: Copyright.Host,\n osName: targetRelease || undefined,\n labels: {},\n },\n ],\n generator: {\n name: 'splunk-to-hdf',\n version: '1.0.0',\n },\n };\n\n return JSON.stringify(hdf, null, 2);\n}\n","import { parseJSON, buildXml } from '@mitre/hdf-utilities';\nimport type { HdfResults, EvaluatedRequirement, Description, RequirementResult } from '@mitre/hdf-schema';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\n\n/**\n * Convert HDF JSON to XML format\n * @param input HDF JSON string\n * @returns XML string with proper HDF structure\n */\nexport function convertHdfToXml(input: string): string {\n validateInputSize(input, 'hdf-to-xml');\n const hdf = parseJSON<HdfResults>(input);\n\n if (!hdf || typeof hdf !== 'object' || !('baselines' in hdf)) {\n throw new Error('Invalid HDF structure: missing baselines field');\n }\n\n if (!Array.isArray(hdf.baselines)) {\n throw new Error('Invalid HDF structure: baselines must be an array');\n }\n\n // Transform HDF structure to XML-friendly format\n const xmlObj = {\n HdfResults: transformHdfToXmlObject(hdf)\n };\n\n return buildXml(xmlObj);\n}\n\n/**\n * Wrap primitive values to force them as nested elements instead of attributes\n */\nfunction wrap(value: string | number | boolean): { '#text': string | number | boolean } {\n return { '#text': value };\n}\n\n/**\n * Transform HDF object to XML-compatible structure\n * Converts arrays to repeated singular elements\n */\nfunction transformHdfToXmlObject(hdf: HdfResults): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n\n // Transform baselines array\n if (hdf.baselines && hdf.baselines.length > 0) {\n result.baselines = {\n baseline: hdf.baselines.map(baseline => ({\n name: wrap(baseline.name),\n ...(baseline.version && { version: wrap(baseline.version) }),\n ...(baseline.title && { title: wrap(baseline.title) }),\n ...(baseline.integrity && {\n integrity: {\n ...(baseline.integrity.algorithm && { algorithm: wrap(baseline.integrity.algorithm) }),\n ...(baseline.integrity.checksum && { checksum: wrap(baseline.integrity.checksum) })\n }\n }),\n ...(baseline.requirements && baseline.requirements.length > 0 && {\n requirements: {\n requirement: baseline.requirements.map(req => transformRequirement(req))\n }\n }),\n ...(baseline.requirements && baseline.requirements.length === 0 && {\n requirements: {}\n })\n }))\n };\n } else {\n result.baselines = {};\n }\n\n // Transform components array\n if (hdf.components && hdf.components.length > 0) {\n result.components = {\n target: hdf.components.map(target => ({\n name: wrap(target.name),\n type: wrap(target.type),\n ...(target.fqdn && { fqdn: wrap(target.fqdn) }),\n ...(target.ipAddress && { ipAddress: wrap(target.ipAddress) }),\n ...(target.hostname && { hostname: wrap(target.hostname) })\n }))\n };\n }\n\n // Transform statistics\n if (hdf.statistics) {\n result.statistics = {};\n if (hdf.statistics.duration !== undefined) {\n (result.statistics as Record<string, unknown>).duration = wrap(hdf.statistics.duration);\n }\n if (hdf.statistics.requirements) {\n (result.statistics as Record<string, unknown>).requirements = hdf.statistics.requirements;\n }\n }\n\n // Add other optional fields\n if (hdf.timestamp) {\n result.timestamp = wrap(typeof hdf.timestamp === 'string' ? hdf.timestamp : hdf.timestamp.toISOString());\n }\n if (hdf.generator) {\n result.generator = hdf.generator;\n }\n\n return result;\n}\n\n/**\n * Transform a requirement object for XML output\n */\nfunction transformRequirement(req: EvaluatedRequirement): Record<string, unknown> {\n const result: Record<string, unknown> = {\n id: wrap(req.id),\n ...(req.title && { title: wrap(req.title) }),\n ...(req.descriptions && req.descriptions.length > 0 && {\n descriptions: {\n description: req.descriptions.map((d: Description) => ({\n label: wrap(d.label),\n data: wrap(d.data)\n }))\n }\n }),\n impact: wrap(req.impact)\n };\n\n // Transform tags (handle arrays within tags object)\n if (req.tags && Object.keys(req.tags).length > 0) {\n const transformedTags: Record<string, unknown> = {};\n for (const [key, value] of Object.entries(req.tags)) {\n if (Array.isArray(value) && value.length > 0) {\n // Repeat the tag name for each array element (wrapped)\n transformedTags[key] = value.map((v: string | number | boolean) => wrap(v));\n } else if (!Array.isArray(value)) {\n transformedTags[key] = wrap(value);\n }\n }\n if (Object.keys(transformedTags).length > 0) {\n result.tags = transformedTags;\n }\n }\n\n // Transform results array\n if (req.results && req.results.length > 0) {\n result.results = {\n result: req.results.map((r: RequirementResult) => ({\n status: wrap(r.status),\n codeDesc: wrap(r.codeDesc),\n startTime: wrap(typeof r.startTime === 'string' ? r.startTime : r.startTime.toISOString()),\n ...(r.message && { message: wrap(r.message) }),\n ...(r.runTime !== undefined && { runTime: wrap(r.runTime) })\n }))\n };\n }\n\n return result;\n}\n","import {\n type Checksum,\n createMinimalBaseline,\n Copyright,\n type Tool,\n type EvaluatedBaseline,\n type EvaluatedRequirement,\n type RequirementResult,\n type HdfResults,\n type Component,\n ResultStatus,\n severityToImpact,\n} from '@mitre/hdf-schema';\nimport {\n getCweNistControl,\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport {parseJSON} from '@mitre/hdf-utilities';\nimport {inputChecksum, buildNistCciTags, limitArray, validateInputSize} from '../../../shared/typescript/converterutil.js';\n\n// --- GitLab Security Report input types ---\n\ninterface GitLabReport {\n version?: string;\n scan?: GitLabScan;\n vulnerabilities?: GitLabVulnerability[];\n remediations?: GitLabRemediation[];\n}\n\ninterface GitLabScan {\n analyzer?: GitLabTool;\n scanner?: GitLabTool;\n start_time?: string;\n end_time?: string;\n status?: string;\n type?: string;\n}\n\ninterface GitLabTool {\n id?: string;\n name?: string;\n version?: string;\n}\n\ninterface GitLabVulnerability {\n id: string;\n name?: string;\n description?: string;\n severity?: string;\n solution?: string;\n identifiers?: GitLabIdentifier[];\n location?: GitLabLocation;\n links?: Array<{url?: string}>;\n}\n\ninterface GitLabIdentifier {\n type?: string;\n name?: string;\n value?: string;\n url?: string;\n}\n\ninterface GitLabLocation {\n file?: string;\n start_line?: number;\n end_line?: number;\n class?: string;\n method?: string;\n hostname?: string;\n path?: string;\n param?: string;\n image?: string;\n operating_system?: string;\n dependency?: {\n package?: {name?: string};\n version?: string;\n };\n}\n\ninterface GitLabRemediation {\n fixes?: Array<{id?: string}>;\n summary?: string;\n diff?: string;\n}\n\n// --- Severity to impact ---\n\nfunction gitlabSeverityToImpact(severity: string): number {\n return severityToImpact(severity.toLowerCase());\n}\n\n// --- Scan type to target type ---\n\nfunction scanTypeToTargetType(scanType: string): Copyright {\n switch (scanType) {\n case 'dast':\n return Copyright.Application;\n case 'container_scanning':\n return Copyright.ContainerImage;\n default:\n return Copyright.Repository;\n }\n}\n\n// --- Scan type label ---\n\nfunction scanTypeLabel(scanType: string): string {\n const labels: Record<string, string> = {\n sast: 'SAST',\n dast: 'DAST',\n dependency_scanning: 'Dependency Scanning',\n container_scanning: 'Container Scanning',\n secret_detection: 'Secret Detection',\n api_fuzzing: 'API Fuzzing',\n };\n return labels[scanType] ?? scanType.toUpperCase();\n}\n\n// --- NIST tag building ---\n\nfunction buildNistTags(identifiers: GitLabIdentifier[]): string[] {\n const seen = new Set<string>();\n const controls: string[] = [];\n for (const id of identifiers) {\n if (id.type === 'cwe' && id.value) {\n const cweNum = parseInt(id.value, 10);\n if (!isNaN(cweNum)) {\n const control = getCweNistControl(cweNum);\n if (control && !seen.has(control)) {\n seen.add(control);\n controls.push(control);\n }\n }\n }\n }\n if (controls.length > 0) {\n return controls;\n }\n return [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n}\n\n// --- Collect identifier tags ---\n\nfunction collectIdentifierTags(identifiers: GitLabIdentifier[]): Record<string, string[]> {\n const result: Record<string, string[]> = {};\n for (const id of identifiers) {\n if (id.type && id.value) {\n const key = id.type.toLowerCase();\n if (!result[key]) {\n result[key] = [];\n }\n result[key].push(id.value);\n }\n }\n return result;\n}\n\n// --- Build code description by scan type ---\n\nfunction buildCodeDesc(scanType: string, location?: GitLabLocation): string {\n if (!location) return '';\n\n switch (scanType) {\n case 'sast':\n case 'secret_detection': {\n const parts: string[] = [];\n if (location.file) {\n parts.push(`File: ${location.file}`);\n }\n if (location.start_line != null) {\n const line = location.end_line != null && location.end_line !== location.start_line\n ? `${location.start_line}-${location.end_line}`\n : `${location.start_line}`;\n parts.push(`Line: ${line}`);\n }\n if (location.class) {\n parts.push(`Class: ${location.class}`);\n }\n if (location.method) {\n parts.push(`Method: ${location.method}`);\n }\n return parts.join(' | ');\n }\n case 'dast': {\n const parts: string[] = [];\n if (location.hostname) {\n const url = location.path ? `${location.hostname}${location.path}` : location.hostname;\n parts.push(`URL: ${url}`);\n }\n if (location.method) {\n parts.push(`Method: ${location.method}`);\n }\n if (location.param) {\n parts.push(`Param: ${location.param}`);\n }\n return parts.join(' | ');\n }\n case 'dependency_scanning': {\n const parts: string[] = [];\n if (location.file) {\n parts.push(`File: ${location.file}`);\n }\n if (location.dependency?.package?.name) {\n const pkg = location.dependency.version\n ? `${location.dependency.package.name}@${location.dependency.version}`\n : location.dependency.package.name;\n parts.push(`Package: ${pkg}`);\n }\n return parts.join(' | ');\n }\n case 'container_scanning': {\n const parts: string[] = [];\n if (location.image) {\n parts.push(`Image: ${location.image}`);\n }\n if (location.dependency?.package?.name) {\n const pkg = location.dependency.version\n ? `${location.dependency.package.name}@${location.dependency.version}`\n : location.dependency.package.name;\n parts.push(`Package: ${pkg}`);\n }\n return parts.join(' | ');\n }\n default:\n return `Location: ${JSON.stringify(location)}`;\n }\n}\n\n// --- Main converter ---\n\nexport async function convertGitlabToHdf(input: string): Promise<string> {\n validateInputSize(input, 'gitlab');\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const report = parseJSON<GitLabReport>(input);\n\n const scanType = report.scan?.type ?? 'sast';\n const scannerName = report.scan?.scanner?.name ?? 'GitLab Security Scanner';\n const scannerVersion = report.scan?.scanner?.version;\n const startTime = report.scan?.start_time;\n\n const vulns = report.vulnerabilities ?? [];\n const {items: limitedVulns, truncated} = limitArray(vulns);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerabilities (original: ${vulns.length})`);\n }\n\n const requirements: EvaluatedRequirement[] = [];\n\n for (const vuln of limitedVulns) {\n const identifiers = vuln.identifiers ?? [];\n\n // Build NIST tags\n const nistTags = buildNistTags(identifiers);\n const cciTags = nistToCci(nistTags);\n\n // Build extra tags from identifiers\n const idTags = collectIdentifierTags(identifiers);\n const extras: Record<string, unknown> = {};\n for (const [key, values] of Object.entries(idTags)) {\n extras[key] = values;\n }\n const tags = buildNistCciTags(nistTags, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n // Build descriptions\n const descriptions: Array<{label: string; data: string}> = [];\n if (vuln.description) {\n descriptions.push({label: 'default', data: vuln.description});\n }\n if (vuln.solution) {\n descriptions.push({label: 'check', data: vuln.solution});\n }\n\n // Build result\n const result: RequirementResult = {\n status: ResultStatus.Failed,\n codeDesc: buildCodeDesc(scanType, vuln.location),\n startTime: startTime ? new Date(startTime) : new Date('0001-01-01T00:00:00Z'),\n };\n\n const impact = gitlabSeverityToImpact(vuln.severity ?? 'Unknown');\n\n const req: EvaluatedRequirement = {\n id: vuln.id,\n title: vuln.name ?? vuln.id,\n impact,\n results: [result],\n tags,\n descriptions,\n };\n\n requirements.push(req);\n }\n\n const label = scanTypeLabel(scanType);\n const baselineTitle = `GitLab ${label} Security Scan`;\n\n const baseline: EvaluatedBaseline = createMinimalBaseline('GitLab Security Scan', requirements, {\n resultsChecksum,\n title: baselineTitle,\n summary: `Scanner: ${scannerName}${scannerVersion ? ` v${scannerVersion}` : ''}`,\n }) as EvaluatedBaseline;\n\n const tool: Tool = {\n name: scannerName,\n format: 'JSON',\n };\n if (scannerVersion) {\n tool.version = scannerVersion;\n }\n\n // Build components based on scan type\n const components: Component[] = [];\n const targetType = scanTypeToTargetType(scanType);\n components.push({name: scannerName, type: targetType});\n\n const hdf: HdfResults = {\n baselines: [baseline],\n components,\n generator: {\n name: 'gitlab-to-hdf',\n version: 'unknown',\n },\n tool,\n };\n\n if (report.scan?.end_time) {\n hdf.timestamp = new Date(report.scan.end_time);\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { inputChecksum, buildNistCciTags, limitArrayWithWarning, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n Tool,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n/**\n * TruffleHog finding structure.\n */\ninterface TrufflehogFinding {\n SourceMetadata?: SourceMetadata;\n SourceID?: number;\n SourceType?: number;\n SourceName?: string;\n DetectorType: number;\n DetectorName: string;\n DetectorDescription?: string;\n DecoderName: string;\n Verified: boolean;\n VerificationError?: string;\n Raw: string;\n RawV2?: string;\n Redacted: string;\n ExtraData?: Record<string, unknown> | null;\n StructuredData?: unknown;\n}\n\ninterface SourceMetadata {\n Data: SourceData;\n}\n\ninterface SourceData {\n Git?: GitSource;\n Filesystem?: FilesystemSource;\n Docker?: DockerSource;\n}\n\ninterface GitSource {\n commit: string;\n file: string;\n email: string;\n repository: string;\n timestamp: string;\n line: number;\n}\n\ninterface FilesystemSource {\n file: string;\n line: number;\n}\n\ninterface DockerSource {\n image: string;\n file: string;\n line: number;\n}\n\n/** Hardcoded NIST/CCI constants for credential exposure findings. */\nconst TRUFFLEHOG_NIST = ['IA-5 (7)'];\nconst TRUFFLEHOG_CCI = ['CCI-000202', 'CCI-000203', 'CCI-002367'];\n\n/**\n * Parse TruffleHog input as JSON array, single object, or NDJSON.\n */\nfunction parseFindings(input: string): TrufflehogFinding[] {\n const trimmed = input.trim();\n\n // Try JSON array first\n try {\n const parsed = parseJSON<unknown>(trimmed);\n if (Array.isArray(parsed)) {\n return parsed as TrufflehogFinding[];\n }\n // Single JSON object\n if (typeof parsed === 'object' && parsed !== null && 'DetectorName' in parsed) {\n return [parsed as TrufflehogFinding];\n }\n } catch {\n // Not valid JSON — try NDJSON\n }\n\n // Try NDJSON: split on newlines, parse each line\n const lines = trimmed.split('\\n').filter(line => line.trim().length > 0);\n const findings: TrufflehogFinding[] = [];\n for (const line of lines) {\n try {\n findings.push(parseJSON<TrufflehogFinding>(line.trim()));\n } catch {\n throw new Error(`trufflehog: failed to parse NDJSON line: ${line.substring(0, 80)}`);\n }\n }\n if (findings.length > 0) {\n return findings;\n }\n\n throw new Error('trufflehog: unable to parse input as JSON array, single object, or NDJSON');\n}\n\n/**\n * Group findings by DetectorName + DecoderName, preserving insertion order.\n */\nfunction groupFindings(findings: TrufflehogFinding[]): Map<string, TrufflehogFinding[]> {\n const groups = new Map<string, TrufflehogFinding[]>();\n for (const f of findings) {\n const key = `${f.DetectorName} ${f.DecoderName}`;\n const existing = groups.get(key);\n if (existing) {\n existing.push(f);\n } else {\n groups.set(key, [f]);\n }\n }\n return groups;\n}\n\n/**\n * Build the Result.Message JSON from selected finding fields.\n */\nfunction buildMessage(f: TrufflehogFinding): string {\n const msg: Record<string, unknown> = {\n Verified: f.Verified,\n Redacted: f.Redacted,\n };\n if (f.VerificationError) {\n msg.VerificationError = f.VerificationError;\n }\n if (f.ExtraData && Object.keys(f.ExtraData).length > 0) {\n msg.ExtraData = f.ExtraData;\n }\n return JSON.stringify(msg);\n}\n\n/**\n * Build the Result.CodeDesc as JSON of SourceMetadata.\n */\nfunction buildCodeDesc(f: TrufflehogFinding): string {\n return JSON.stringify(f.SourceMetadata ?? {});\n}\n\n/**\n * Extract a timestamp from a finding's Git source metadata.\n */\nfunction getTimestamp(f: TrufflehogFinding): Date {\n if (f.SourceMetadata?.Data?.Git?.timestamp) {\n const ts = new Date(f.SourceMetadata.Data.Git.timestamp);\n if (!isNaN(ts.getTime())) {\n return ts;\n }\n }\n return new Date();\n}\n\n/**\n * Get the source file path from any source type.\n */\nfunction getSourceFile(f: TrufflehogFinding): string | undefined {\n return f.SourceMetadata?.Data?.Git?.file\n ?? f.SourceMetadata?.Data?.Filesystem?.file\n ?? f.SourceMetadata?.Data?.Docker?.file;\n}\n\n/**\n * Get the source line number from any source type.\n */\nfunction getSourceLine(f: TrufflehogFinding): number | undefined {\n return f.SourceMetadata?.Data?.Git?.line\n ?? f.SourceMetadata?.Data?.Filesystem?.line\n ?? f.SourceMetadata?.Data?.Docker?.line;\n}\n\n/**\n * Find the first Git repository URL from findings.\n */\nfunction findGitRepoURL(findings: TrufflehogFinding[]): string | undefined {\n for (const f of findings) {\n if (f.SourceMetadata?.Data?.Git?.repository) {\n return f.SourceMetadata.Data.Git.repository;\n }\n }\n return undefined;\n}\n\n/**\n * Build an EvaluatedRequirement from a group of findings sharing a detector.\n */\nfunction buildRequirement(reqID: string, findings: TrufflehogFinding[]): EvaluatedRequirement {\n const rep = findings[0]!;\n const tags = buildNistCciTags(TRUFFLEHOG_NIST, TRUFFLEHOG_CCI);\n\n const title = `Found ${rep.DetectorName} secret using ${rep.DecoderName} decoder`;\n\n const descData = rep.DetectorDescription\n ?? `${rep.DetectorName} secret detected by ${rep.DecoderName} decoder`;\n const descriptions: Description[] = [\n { label: 'default', data: descData },\n ];\n\n const results = findings.map(f =>\n createResult(ResultStatus.Failed, buildMessage(f), {\n codeDesc: buildCodeDesc(f),\n startTime: getTimestamp(f),\n })\n );\n\n const sourceFile = getSourceFile(rep);\n const sourceLine = getSourceLine(rep);\n\n return createRequirement(\n reqID,\n title,\n descriptions,\n 0.5,\n results,\n {\n tags,\n sourceLocation: sourceFile ? { ref: sourceFile, line: sourceLine } : undefined,\n }\n );\n}\n\n/**\n * Converts TruffleHog output to HDF format.\n * Accepts JSON array, single JSON object, or NDJSON input.\n *\n * @param input - TruffleHog JSON/NDJSON string\n * @returns HDF JSON string\n */\nexport async function convertTrufflehogToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('trufflehog: empty input');\n }\n validateInputSize(input, 'trufflehog');\n\n const findings = parseFindings(input);\n if (findings.length === 0) {\n throw new Error('trufflehog: no findings in input');\n }\n\n const resultsChecksum = await inputChecksum(input);\n const limitedFindings = limitArrayWithWarning(findings, 'finding');\n\n const groups = groupFindings(limitedFindings);\n const requirements: EvaluatedRequirement[] = [];\n for (const [reqID, group] of groups) {\n requirements.push(buildRequirement(reqID, group));\n }\n\n const sourceName = limitedFindings[0]?.SourceName ?? 'trufflehog';\n const baselineTitle = `TruffleHog Scan (${sourceName})`;\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'TruffleHog Scan',\n requirements,\n {\n resultsChecksum,\n title: baselineTitle,\n }\n ) as EvaluatedBaseline;\n\n const tool: Tool = { name: 'TruffleHog', format: 'JSON' };\n\n const hdf: HdfResults = {\n baselines: [baseline],\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n tool,\n timestamp: new Date(),\n };\n\n // Add target only if a Git repository URL is available\n const repoURL = findGitRepoURL(limitedFindings);\n if (repoURL) {\n hdf.components = [{ name: repoURL, type: Copyright.Repository }];\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport {\n inputChecksum,\n buildNistCciTags,\n limitArray,\n stripHTML,\n mapCWEToNIST,\n extractCWEIDs,\n validateInputSize,\n} from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Tool,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n} from '@mitre/hdf-schema';\n\n// --- BurpSuite XML input types ---\n\ninterface BurpIssuesXml {\n issues: {\n burpVersion?: string;\n exportTime?: string;\n issue?: BurpIssueXml[];\n };\n}\n\ninterface BurpIssueXml {\n serialNumber?: string;\n type?: string;\n name?: string;\n host?: BurpHostXml;\n path?: string;\n location?: string;\n severity?: string;\n confidence?: string;\n issueBackground?: string;\n remediationBackground?: string;\n references?: string;\n vulnerabilityClassifications?: string;\n issueDetail?: string;\n}\n\ninterface BurpHostXml {\n ip?: string;\n '#text'?: string;\n}\n\n// --- Impact mapping ---\n\nconst IMPACT_MAPPING: Record<string, number> = {\n 'high': 0.7,\n 'medium': 0.5,\n 'low': 0.3,\n 'information': 0.3,\n};\n\nfunction getImpact(severity: string): number {\n return IMPACT_MAPPING[severity.toLowerCase()] ?? 0.3;\n}\n\n// --- CWE parsing ---\n\n/**\n * Extract CWE identifiers from HTML text.\n * Returns CWE-prefixed IDs (e.g., [\"CWE-79\"]) for use in tags and mapCWEToNIST.\n */\nfunction parseCWEIDs(html: string): string[] {\n if (!html) return [];\n return extractCWEIDs(html).map(id => `CWE-${id}`);\n}\n\n// --- Format code desc ---\n\nfunction formatCodeDesc(\n hostIP: string,\n hostURL: string,\n location: string,\n issueDetail: string,\n confidence: string,\n): string {\n const parts: string[] = [];\n parts.push(`Host: ip: ${hostIP}, url: ${hostURL}`);\n parts.push(`Location: ${stripHTML(location)}`);\n if (issueDetail) {\n parts.push(`issueDetail: ${stripHTML(issueDetail)}`);\n }\n parts.push(`confidence: ${confidence}`);\n return parts.join('\\n') + '\\n';\n}\n\n// --- Main converter ---\n\n/**\n * Converts BurpSuite Pro XML export to HDF format.\n *\n * Issues are grouped by `<type>` — each unique type becomes one requirement,\n * with one result per individual issue instance.\n *\n * @param input - BurpSuite XML string\n * @returns HDF JSON string\n */\nexport async function convertBurpsuiteToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('burpsuite: empty input');\n }\n validateInputSize(input, 'burpsuite');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Parse XML — ensure issue is always treated as array\n const parsed = parseXmlWithArrays(input, ['issue']) as unknown as BurpIssuesXml;\n\n if (!parsed.issues) {\n throw new Error('burpsuite: invalid XML — missing <issues> root element');\n }\n\n const issues = parsed.issues.issue ?? [];\n const burpVersion = parsed.issues.burpVersion ?? '';\n const exportTime = parsed.issues.exportTime ?? '';\n\n const { items: limitedIssues, truncated } = limitArray(issues);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedIssues.length} issue items (original: ${issues.length})`);\n }\n\n // Group issues by type (preserving insertion order)\n const groups = new Map<string, BurpIssueXml[]>();\n for (const issue of limitedIssues) {\n const issueType = issue.type ?? 'unknown';\n const existing = groups.get(issueType);\n if (existing) {\n existing.push(issue);\n } else {\n groups.set(issueType, [issue]);\n }\n }\n\n // Build requirements from grouped issues\n const requirements: EvaluatedRequirement[] = [];\n for (const [issueType, groupIssues] of groups) {\n requirements.push(buildRequirement(issueType, groupIssues));\n }\n\n // Determine target from the first issue's host\n const targetName = limitedIssues.length > 0\n ? (limitedIssues[0]!.host?.['#text'] ?? 'Unknown').trim()\n : 'Unknown';\n\n const title = `BurpSuite Scan: ${targetName}`;\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'BurpSuite Scan',\n requirements,\n {\n resultsChecksum,\n title,\n },\n ) as EvaluatedBaseline;\n\n const tool: Tool = {\n name: 'BurpSuite',\n format: 'XML',\n };\n if (burpVersion) {\n tool.version = burpVersion;\n }\n\n const hdf: HdfResults = {\n baselines: [baseline],\n components: [\n {\n name: targetName,\n type: Copyright.Application,\n },\n ],\n generator: {\n name: 'burpsuite-to-hdf',\n version: '1.0.0',\n },\n tool,\n };\n\n if (exportTime) {\n hdf.timestamp = new Date(exportTime);\n }\n\n return JSON.stringify(hdf, null, 2);\n}\n\n// --- Build requirement ---\n\nfunction buildRequirement(\n issueType: string,\n issues: BurpIssueXml[],\n): EvaluatedRequirement {\n const rep = issues[0]!;\n\n // Parse CWE IDs from vulnerabilityClassifications HTML\n const cweIDs = parseCWEIDs(rep.vulnerabilityClassifications ?? '');\n\n // Map CWE to NIST\n const nist = mapCWEToNIST(cweIDs, [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS]);\n const cciTags = nistToCci(nist);\n\n // Build extra tags\n const extras: Record<string, unknown> = {};\n if (cweIDs.length > 0) {\n extras.cweid = cweIDs.join(', ');\n }\n if (rep.confidence) {\n extras.confidence = rep.confidence;\n }\n const tags = buildNistCciTags(nist, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n // Build descriptions\n const descriptions: Description[] = [];\n\n // Default description (required minimum 1 with \"default\" label)\n const defaultData = rep.issueBackground\n ? stripHTML(rep.issueBackground)\n : (rep.name ?? issueType);\n descriptions.push({ label: 'default', data: defaultData });\n\n // Check description from issueBackground\n if (rep.issueBackground) {\n descriptions.push({ label: 'check', data: stripHTML(rep.issueBackground) });\n }\n\n // Fix description from remediationBackground\n if (rep.remediationBackground) {\n descriptions.push({ label: 'fix', data: stripHTML(rep.remediationBackground) });\n }\n\n // Build results — one per issue in the group\n const results: RequirementResult[] = issues.map(issue => {\n const codeDesc = formatCodeDesc(\n issue.host?.ip ?? '',\n (issue.host?.['#text'] ?? '').trim(),\n issue.location ?? '',\n issue.issueDetail ?? '',\n issue.confidence ?? '',\n );\n return {\n status: ResultStatus.Failed,\n codeDesc,\n startTime: new Date('0001-01-01T00:00:00Z'),\n };\n });\n\n const impact = getImpact(rep.severity ?? 'information');\n\n return {\n id: issueType,\n title: rep.name ?? undefined,\n impact,\n tags,\n descriptions,\n results,\n };\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport {\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n nistToCci,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, buildNistCciTags, limitArray, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n/** Impact mapping from heimdall2 DBProtect mapper */\nconst IMPACT_MAPPING: Record<string, number> = {\n high: 0.7,\n medium: 0.5,\n low: 0.3,\n informational: 0.0,\n};\n\n/** Parsed DBProtect XML dataset structure */\ninterface DatasetXml {\n dataset: {\n metadata: {\n item: MetadataItem[];\n };\n data: {\n row: DataRow[];\n };\n };\n}\n\ninterface MetadataItem {\n name: string;\n type: string;\n}\n\ninterface DataRow {\n value: Array<string | { nil: string } | null>;\n}\n\n/** A single compiled finding, mapping column names to string values */\ntype Finding = Record<string, string>;\n\n/**\n * Maps metadata column names to row values by position index.\n * Mirrors the heimdall2 compileFindings function.\n */\nfunction compileFindings(parsed: DatasetXml): Finding[] {\n const items = parsed.dataset.metadata.item;\n const rows = parsed.dataset.data.row;\n\n const colNames = items.map((item: MetadataItem) => item['name']);\n\n return rows.map((row: DataRow) => {\n const finding: Finding = {};\n const values = row.value;\n colNames.forEach((name: string, i: number) => {\n const val = values[i];\n if (val === null || val === undefined || typeof val === 'object') {\n finding[name] = '';\n } else {\n finding[name] = String(val);\n }\n });\n return finding;\n });\n}\n\n/** Check if the dataset has a \"Result Status\" column */\nfunction hasResultStatusColumn(parsed: DatasetXml): boolean {\n return parsed.dataset.metadata.item.some(\n (item: MetadataItem) => item['name'] === 'Result Status',\n );\n}\n\n/** Maps DBProtect result status strings to HDF ResultStatus */\nfunction getStatus(status: string): ResultStatus {\n switch (status) {\n case 'Fact':\n return ResultStatus.NotReviewed;\n case 'Failed':\n return ResultStatus.Failed;\n case 'Finding':\n return ResultStatus.Failed;\n case 'Not A Finding':\n return ResultStatus.Passed;\n default:\n // Includes \"Skipped\" and any unknown status\n return ResultStatus.NotReviewed;\n }\n}\n\n/** Maps DBProtect risk level to HDF impact value */\nfunction getImpact(riskDV: string): number {\n const impact = IMPACT_MAPPING[riskDV.toLowerCase()];\n return impact !== undefined ? impact : 0.5;\n}\n\n/** Creates a description string from a finding's task and check category */\nfunction formatDesc(f: Finding): string {\n return `Task : ${f['Task'] ?? ''}; Check Category : ${f['Check Category'] ?? ''}`;\n}\n\n/** Creates a summary string from a finding's metadata */\nfunction formatSummary(f: Finding): string {\n return [\n `Organization : ${f['Organization'] ?? ''}`,\n `Asset : ${f['Asset'] ?? ''}`,\n `Asset Type : ${f['Asset Type'] ?? ''}`,\n `IP Address, Port, Instance : ${f['IP Address, Port, Instance'] ?? ''}`,\n ].join('\\n');\n}\n\n/**\n * Parses DBProtect date format \"Feb 18 2021 15:57\"\n */\nfunction parseDate(dateStr: string): Date {\n const trimmed = dateStr.trim();\n if (!trimmed) {\n return new Date();\n }\n const parsed = new Date(trimmed);\n if (!isNaN(parsed.getTime())) {\n return parsed;\n }\n return new Date();\n}\n\n/**\n * Builds a single EvaluatedRequirement from a group of findings sharing a Check ID.\n */\nfunction buildRequirement(\n checkID: string,\n findings: Finding[],\n hasStatus: boolean,\n): EvaluatedRequirement {\n const rep = findings[0]!;\n\n const nist = DEFAULT_STATIC_ANALYSIS_NIST_TAGS;\n const cciTags = nistToCci(nist);\n const tags = buildNistCciTags(nist, cciTags);\n\n const descriptions: Description[] = [\n { label: 'default', data: formatDesc(rep) },\n ];\n\n const results = findings.map((f) => {\n const status = hasStatus\n ? getStatus(f['Result Status'] ?? '')\n : ResultStatus.Failed;\n\n return createResult(status, undefined, {\n codeDesc: f['Details'] ?? '',\n startTime: parseDate(f['Date'] ?? ''),\n });\n });\n\n return createRequirement(\n checkID,\n rep['Check'] ?? '',\n descriptions,\n getImpact(rep['Risk DV'] ?? ''),\n results,\n { tags },\n );\n}\n\n/**\n * Converts DBProtect Cognos XML output to HDF format.\n * Supports both \"Check Results Details\" (has Result Status) and \"Findings Detail\"\n * (no Result Status; all rows are findings) report formats.\n *\n * @param input - DBProtect XML string\n * @returns HDF JSON string\n */\nexport async function convertDbprotectToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('dbprotect: empty input');\n }\n validateInputSize(input, 'dbprotect');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const parsed = parseXmlWithArrays(input, ['item', 'row', 'value']) as unknown as DatasetXml;\n\n if (!parsed?.dataset?.data?.row || parsed.dataset.data.row.length === 0) {\n throw new Error('dbprotect: no data rows found');\n }\n\n const findings = compileFindings(parsed);\n const { items: limitedFindings, truncated } = limitArray(findings);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(\n `WARNING: Input truncated at ${limitedFindings.length} finding items (original: ${findings.length})`,\n );\n }\n\n const hasStatus = hasResultStatusColumn(parsed);\n\n // Group findings by Check ID, preserving insertion order\n const groups = new Map<string, Finding[]>();\n for (const f of limitedFindings) {\n const checkID = (f['Check ID'] ?? '').trim();\n const existing = groups.get(checkID);\n if (existing) {\n existing.push(f);\n } else {\n groups.set(checkID, [f]);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [checkID, findingGroup] of groups) {\n requirements.push(buildRequirement(checkID, findingGroup, hasStatus));\n }\n\n // Use first finding for metadata\n const firstFinding = limitedFindings[0]!;\n const title = firstFinding['Job Name'] ?? '';\n const summary = formatSummary(firstFinding);\n const targetName = firstFinding['Asset'] ?? '';\n\n const baseline = createMinimalBaseline('DBProtect Scan', requirements, {\n resultsChecksum,\n title,\n summary,\n }) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'dbprotect-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'DBProtect',\n toolFormat: 'XML',\n baselines: [baseline],\n components: [{ name: targetName, type: Copyright.Host }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_REMEDIATION_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, buildNistCciTags, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Twistlock/Prisma Cloud scan output structures.\n *\n * Container image scans produce a top-level \"results\" array.\n * Code repository scans omit the wrapper and return a single result object.\n */\ninterface TwistlockReport {\n results?: TwistlockResult[];\n consoleURL?: string;\n}\n\ninterface TwistlockResult {\n id?: string;\n name?: string;\n repository?: string;\n distro?: string;\n collections?: string[];\n vulnerabilities?: TwistlockVuln[] | null;\n vulnerabilityDistribution?: TwistlockDistribution;\n complianceDistribution?: TwistlockDistribution;\n}\n\ninterface TwistlockVuln {\n id: string;\n status?: string;\n cvss?: number;\n vector?: string;\n description: string;\n severity: string;\n packageName?: string;\n packageVersion?: string;\n link?: string;\n riskFactors?: string[];\n impactedVersions?: string[];\n publishedDate?: string;\n discoveredDate?: string;\n fixDate?: string;\n layerTime?: string;\n}\n\ninterface TwistlockDistribution {\n critical: number;\n high: number;\n medium: number;\n low: number;\n total: number;\n}\n\n/**\n * Maps Twistlock severity strings to HDF impact values.\n * Includes \"important\" (alias for critical) and \"moderate\" (alias for medium)\n * which appear in some Twistlock outputs.\n */\nfunction twistlockSeverityToImpact(severity: string): number {\n switch (severity.toLowerCase()) {\n case 'critical':\n case 'important':\n return 0.9;\n case 'high':\n return 0.7;\n case 'medium':\n case 'moderate':\n return 0.5;\n case 'low':\n return 0.3;\n default:\n return 0.5;\n }\n}\n\n/**\n * Builds the baseline title from scan result data.\n */\nfunction buildTitle(result: TwistlockResult): string {\n let projectName: string;\n if (result.repository) {\n projectName = result.repository;\n } else if (result.collections && result.collections.length > 0) {\n projectName = result.collections.join(' / ');\n } else {\n projectName = 'N/A';\n }\n return `Twistlock Project: ${projectName}`;\n}\n\n/**\n * Builds the baseline summary from distribution data.\n */\nfunction buildSummary(result: TwistlockResult): string {\n const vulnTotal = result.vulnerabilityDistribution\n ? String(result.vulnerabilityDistribution.total)\n : 'N/A';\n const complianceTotal = result.complianceDistribution\n ? String(result.complianceDistribution.total)\n : 'N/A';\n return `Package Vulnerability Summary: ${vulnTotal} Application Compliance Issue Total: ${complianceTotal}`;\n}\n\n/**\n * Builds the code_desc string for a vulnerability result.\n */\nfunction formatCodeDesc(vuln: TwistlockVuln): string {\n const packageName = vuln.packageName ?? 'N/A';\n const impactedVersions = vuln.impactedVersions && vuln.impactedVersions.length > 0\n ? JSON.stringify(vuln.impactedVersions)\n : 'N/A';\n return `Package ${JSON.stringify(packageName)} should be updated to latest version above impacted versions ${impactedVersions}`;\n}\n\n/**\n * Converts a single vulnerability into an EvaluatedRequirement.\n */\nfunction buildRequirement(vuln: TwistlockVuln): EvaluatedRequirement {\n const nist = DEFAULT_REMEDIATION_NIST_TAGS;\n const cciTags = nistToCci(nist);\n\n const tags = buildNistCciTags(nist, cciTags, {\n cveid: [vuln.id],\n });\n\n const descriptions: Description[] = [\n { label: 'default', data: vuln.description },\n ];\n\n const startTime = vuln.discoveredDate ? new Date(vuln.discoveredDate) : undefined;\n\n const results = [\n createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatCodeDesc(vuln),\n startTime,\n }),\n ];\n\n return createRequirement(\n vuln.id,\n vuln.id,\n descriptions,\n twistlockSeverityToImpact(vuln.severity),\n results,\n { tags }\n );\n}\n\n/**\n * Converts a single TwistlockResult to an EvaluatedBaseline.\n */\nfunction convertSingleResult(\n result: TwistlockResult,\n resultsChecksum: Checksum\n): EvaluatedBaseline {\n const vulns = result.vulnerabilities ?? [];\n const { items: limitedVulns, truncated } = limitArray(vulns);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${vulns.length})`);\n }\n\n const requirements: EvaluatedRequirement[] = limitedVulns.map(vuln =>\n buildRequirement(vuln)\n );\n\n const title = buildTitle(result);\n const summary = buildSummary(result);\n\n return createMinimalBaseline(\n 'Twistlock Scan',\n requirements,\n {\n resultsChecksum,\n title,\n summary,\n }\n ) as EvaluatedBaseline;\n}\n\n/**\n * Converts Twistlock/Prisma Cloud scan output to HDF format.\n *\n * Handles both container image scans (with \"results\" wrapper) and code\n * repository scans (single result object without wrapper).\n *\n * @param input - Twistlock JSON string\n * @returns HDF JSON string\n */\nexport async function convertTwistlockToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('twistlock: empty input');\n }\n validateInputSize(input, 'twistlock');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const parsed = parseJSON<TwistlockReport & TwistlockResult>(input);\n\n if (!parsed || typeof parsed !== 'object') {\n throw new Error('twistlock: invalid JSON');\n }\n\n let results: TwistlockResult[];\n\n if (Array.isArray((parsed as TwistlockReport).results)) {\n // Container scan with \"results\" wrapper\n results = (parsed as TwistlockReport).results!;\n } else {\n // Code repo scan — single result object, wrap it\n results = [parsed as TwistlockResult];\n }\n\n if (results.length === 0) {\n throw new Error('twistlock: no scan results found');\n }\n\n const baselines = results.map(result =>\n convertSingleResult(result, resultsChecksum)\n );\n\n // Use the first result's name or repository as target name\n const targetName = results[0]!.name ?? results[0]!.repository ?? '';\n\n return buildHdfResults({\n generatorName: 'twistlock-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Twistlock',\n toolFormat: 'JSON',\n baselines,\n components: [{\n name: targetName,\n type: Copyright.ContainerImage,\n labels: { image: results[0]?.id ?? targetName },\n }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, mapCWEToNIST, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Dependency-Track Finding Packaging Format (FPF) structures.\n */\ninterface DeptrackReport {\n version?: string;\n meta: DeptrackMeta;\n project: DeptrackProject;\n findings: DeptrackFinding[];\n}\n\ninterface DeptrackMeta {\n application?: string;\n version?: string;\n timestamp?: string;\n baseUrl?: string;\n}\n\ninterface DeptrackProject {\n uuid: string;\n name: string;\n version?: string;\n description?: string;\n}\n\ninterface DeptrackFinding {\n component: DeptrackComponent;\n vulnerability: DeptrackVulnerability;\n analysis?: DeptrackAnalysis;\n attribution?: DeptrackAttribution;\n matrix: string;\n}\n\ninterface DeptrackComponent {\n uuid?: string;\n name: string;\n version?: string;\n purl?: string;\n latestVersion?: string;\n group?: string;\n project?: string;\n cpe?: string;\n}\n\ninterface DeptrackVulnerability {\n uuid?: string;\n source?: string;\n vulnId?: string;\n title?: string;\n subtitle?: string;\n severity: string;\n severityRank?: number;\n cweId?: number;\n cweName?: string;\n cwes?: DeptrackCwe[];\n description?: string;\n recommendation?: string;\n aliases?: unknown[];\n cvssV2BaseScore?: number;\n cvssV3BaseScore?: number;\n epssScore?: number;\n epssPercentile?: number;\n}\n\ninterface DeptrackCwe {\n cweId: number;\n name: string;\n}\n\ninterface DeptrackAnalysis {\n state?: string;\n isSuppressed?: boolean;\n}\n\ninterface DeptrackAttribution {\n analyzerIdentity?: string;\n attributedOn?: string;\n alternateIdentifier?: string;\n referenceUrl?: string;\n}\n\n/**\n * Maps Dependency-Track severity strings to HDF impact values.\n * Uses the same mapping as the heimdall2 dependency-track-mapper:\n * critical=0.9, high=0.7, medium=0.5, low=0.3, info=0, unassigned=0.5\n */\nfunction getImpact(severity: string): number {\n switch (severity.toLowerCase()) {\n case 'critical':\n return 0.9;\n case 'high':\n return 0.7;\n case 'medium':\n return 0.5;\n case 'low':\n return 0.3;\n case 'info':\n return 0.0;\n default:\n return 0.5;\n }\n}\n\n/**\n * Builds the requirement title from component purl and vulnerability title.\n * Matches the heimdall2 pattern: \"{purl} - {title}\" or just \"{purl}\".\n */\nfunction getTitle(finding: DeptrackFinding): string {\n const purl = finding.component.purl ?? finding.component.name;\n const title = finding.vulnerability.title;\n if (title) {\n return `${purl} - ${title}`;\n }\n return purl;\n}\n\n/**\n * Extracts CWE IDs as \"CWE-NNN\" strings from the cwes array.\n */\nfunction getCweIDs(cwes: DeptrackCwe[] | undefined): string[] {\n if (!cwes || cwes.length === 0) {\n return [];\n }\n return cwes.map(cwe => `CWE-${cwe.cweId}`);\n}\n\n/**\n * Builds a single EvaluatedRequirement from a Dependency-Track finding.\n */\nfunction buildRequirement(finding: DeptrackFinding, timestamp: string | undefined): EvaluatedRequirement {\n const cweIDs = getCweIDs(finding.vulnerability.cwes);\n const nist = mapCWEToNIST(cweIDs, DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n const tags: Record<string, unknown> = {\n nist,\n cci: cciTags,\n };\n\n if (cweIDs.length > 0) {\n tags['cweIds'] = cweIDs;\n }\n\n // Build descriptions: default, check, fix\n const descriptions: Description[] = [\n { label: 'default', data: finding.vulnerability.description ?? '' },\n ];\n\n if (finding.vulnerability.description) {\n descriptions.push({ label: 'check', data: finding.vulnerability.description });\n }\n if (finding.vulnerability.recommendation) {\n descriptions.push({ label: 'fix', data: finding.vulnerability.recommendation });\n }\n\n // Build result: all findings are Failed\n const codeDesc = finding.vulnerability.recommendation ?? 'No recommendation available';\n\n const results = [\n createResult(ResultStatus.Failed, undefined, {\n codeDesc,\n startTime: timestamp ? new Date(timestamp) : undefined,\n }),\n ];\n\n return createRequirement(\n finding.matrix,\n getTitle(finding),\n descriptions,\n getImpact(finding.vulnerability.severity),\n results,\n { tags },\n );\n}\n\n/**\n * Converts Dependency-Track FPF JSON output to HDF format.\n *\n * @param input - Dependency-Track FPF JSON string\n * @returns HDF JSON string\n */\nexport async function convertDeptrackToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('deptrack: empty input');\n }\n validateInputSize(input, 'deptrack');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const parsed = parseJSON<DeptrackReport>(input);\n\n if (!parsed || typeof parsed !== 'object') {\n throw new Error('deptrack: invalid JSON');\n }\n\n // Validate it looks like a Dependency-Track report\n if (!parsed.findings && !parsed.project && !parsed.meta) {\n throw new Error('deptrack: input does not appear to be a Dependency-Track report');\n }\n\n const findings = parsed.findings ?? [];\n const requirements: EvaluatedRequirement[] = findings.map(\n finding => buildRequirement(finding, parsed.meta?.timestamp),\n );\n\n const title = `Dependency-Track: ${parsed.project?.name ?? ''} ${parsed.project?.version ?? ''}`;\n\n const baseline = createMinimalBaseline(\n 'Dependency-Track Scan',\n requirements,\n {\n resultsChecksum,\n title,\n summary: parsed.project?.description,\n },\n ) as EvaluatedBaseline;\n\n const targetName = parsed.project?.name ?? parsed.project?.uuid ?? '';\n\n return buildHdfResults({\n generatorName: 'deptrack-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Dependency-Track',\n toolFormat: 'JSON',\n baselines: [baseline],\n components: [{ name: targetName, type: Copyright.Application }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON, sha256 } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, mapCWEToNIST, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n severityToImpact,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * JFrog Xray JSON output structures.\n */\ninterface XrayReport {\n total_count: number;\n data: XrayEntry[];\n}\n\ninterface XrayEntry {\n id: string;\n severity: string;\n summary: string;\n issue_type?: string;\n provider?: string;\n component?: string;\n source_id?: string;\n source_comp_id?: string;\n component_versions?: ComponentVersions;\n edited?: string;\n}\n\ninterface ComponentVersions {\n id?: string;\n vulnerable_versions?: string[];\n fixed_versions?: string[];\n more_details?: MoreDetails;\n}\n\ninterface MoreDetails {\n cves?: CVEEntry[];\n description?: string;\n provider?: string;\n}\n\ninterface CVEEntry {\n cve?: string;\n cwe?: string[];\n cvss_v2?: string;\n cvss_v3?: string;\n}\n\n/**\n * Generate a truncated SHA-256 hash of a string for use as an ID.\n * Truncated to 32 hex chars for compatibility with original hash length.\n */\nasync function hashID(summary: string): Promise<string> {\n const full = await sha256(summary);\n return full.substring(0, 32);\n}\n\n/**\n * Extract CWE identifiers from the first CVE entry.\n */\nfunction extractCWEs(entry: XrayEntry): string[] {\n const cves = entry.component_versions?.more_details?.cves;\n if (!cves || cves.length === 0) {\n return [];\n }\n return cves[0]?.cwe ?? [];\n}\n\n/**\n * Build description from more_details, including CVE data.\n * Matches heimdall2 formatDesc behavior.\n */\nfunction formatDescription(entry: XrayEntry): string {\n const parts: string[] = [];\n const desc = entry.component_versions?.more_details?.description;\n if (desc) {\n parts.push(desc);\n }\n const cves = entry.component_versions?.more_details?.cves;\n if (cves && cves.length > 0) {\n let cveStr = JSON.stringify(cves);\n cveStr = cveStr.replace(/\":/g, '\"=>');\n cveStr = cveStr.replace(/,/g, ', ');\n parts.push(`cves: ${cveStr}`);\n }\n if (parts.length === 0) {\n return entry.summary;\n }\n return parts.join('\\n');\n}\n\n/**\n * Build code_desc from component version metadata.\n * Matches heimdall2 formatCodeDesc behavior.\n */\nfunction formatCodeDesc(entry: XrayEntry): string {\n const parts: string[] = [];\n\n parts.push(`source_comp_id : ${entry.source_comp_id ?? ''}`);\n\n const vulnVersions = entry.component_versions?.vulnerable_versions;\n if (vulnVersions && vulnVersions.length > 0) {\n parts.push(`vulnerable_versions : ${JSON.stringify(vulnVersions)}`);\n } else {\n parts.push('vulnerable_versions : ');\n }\n\n const fixedVersions = entry.component_versions?.fixed_versions;\n if (fixedVersions && fixedVersions.length > 0) {\n parts.push(`fixed_versions : ${JSON.stringify(fixedVersions)}`);\n } else {\n parts.push('fixed_versions : ');\n }\n\n parts.push(`issue_type : ${entry.issue_type ?? ''}`);\n parts.push(`provider : ${entry.provider ?? ''}`);\n\n return parts.join('\\n').replace(/,/g, ', ');\n}\n\n/**\n * Builds a single EvaluatedRequirement from a group of entries sharing an ID.\n */\nfunction buildRequirement(entryID: string, entries: XrayEntry[]): EvaluatedRequirement {\n const rep = entries[0]!;\n const cweIDs = extractCWEs(rep);\n const nist = mapCWEToNIST(cweIDs, DEFAULT_STATIC_ANALYSIS_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n const tags: Record<string, unknown> = {\n nist,\n cci: cciTags,\n };\n\n if (cweIDs.length > 0) {\n tags['cweid'] = cweIDs;\n }\n\n const descriptions: Description[] = [\n { label: 'default', data: formatDescription(rep) },\n ];\n\n const results = entries.map(entry =>\n createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatCodeDesc(entry),\n })\n );\n\n return createRequirement(\n entryID,\n rep.summary,\n descriptions,\n severityToImpact(rep.severity),\n results,\n { tags }\n );\n}\n\n/**\n * Converts JFrog Xray JSON output to HDF format.\n *\n * @param input - JFrog Xray JSON string\n * @returns HDF JSON string\n */\nexport async function convertJfrogXrayToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('jfrog-xray: empty input');\n }\n validateInputSize(input, 'jfrog-xray');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const parsed = parseJSON<XrayReport>(input);\n\n if (!parsed || typeof parsed !== 'object' || !Array.isArray(parsed.data)) {\n throw new Error('jfrog-xray: invalid JSON structure');\n }\n\n const { items: limitedEntries, truncated } = limitArray(parsed.data);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedEntries.length} entries (original: ${parsed.data.length})`);\n }\n\n // Pre-compute entry IDs (hashID is async due to Web Crypto sha256)\n const entryIDs = await Promise.all(\n limitedEntries.map(async (entry) => {\n if (entry.id && entry.id.length > 0) return entry.id;\n return hashID(entry.summary);\n })\n );\n\n // Group entries by effective ID, preserving insertion order\n const groups = new Map<string, XrayEntry[]>();\n for (let i = 0; i < limitedEntries.length; i++) {\n const id = entryIDs[i]!;\n const entry = limitedEntries[i]!;\n const existing = groups.get(id);\n if (existing) {\n existing.push(entry);\n } else {\n groups.set(id, [entry]);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [entryID, entries] of groups) {\n requirements.push(buildRequirement(entryID, entries));\n }\n\n const baseline = createMinimalBaseline(\n 'JFrog Xray Scan',\n requirements,\n { resultsChecksum }\n ) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'jfrog-xray-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'JFrog Xray',\n toolFormat: 'JSON',\n baselines: [baseline],\n components: [{ name: 'JFrog Xray Scan', type: Copyright.Application }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_REMEDIATION_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, mapCWEToNIST, extractCWEIDs, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * NeuVector scan JSON output structures.\n *\n * Top-level object has \"error_message\" and \"report\" fields.\n * The report contains image metadata and a vulnerabilities array.\n */\ninterface NeuVectorScan {\n error_message: string;\n report: NeuVectorScanReport;\n}\n\ninterface NeuVectorScanReport {\n image_id: string;\n registry: string;\n repository: string;\n tag: string;\n digest: string;\n size: number;\n author: string;\n base_os: string;\n created_at: string;\n cvedb_version: string;\n cvedb_create_time: string;\n layers: unknown[];\n vulnerabilities: NeuVectorVuln[];\n modules?: NeuVectorScanModule[];\n}\n\ninterface NeuVectorVuln {\n name: string;\n score: number;\n severity: string;\n vectors: string;\n description: string;\n file_name: string;\n package_name: string;\n package_version: string;\n fixed_version: string;\n link: string;\n score_v3: number;\n vectors_v3: string;\n published_timestamp: number;\n last_modified_timestamp: number;\n cpes?: string[];\n cves?: string[];\n feed_rating: string;\n in_base_image?: boolean;\n tags?: string[];\n}\n\ninterface NeuVectorScanModule {\n name: string;\n file: string;\n version: string;\n source: string;\n}\n\n/**\n * Extracts CWE identifiers from a vulnerability description string.\n * Returns CWE-prefixed IDs (e.g., [\"CWE-444\"]) for use in tags and mapCWEToNIST.\n */\nfunction extractCWEs(description: string): string[] {\n return extractCWEIDs(description).map(id => `CWE-${id}`);\n}\n\n/**\n * Computes the HDF impact from NeuVector CVSS scores.\n * Prefers CVSS v3 score; falls back to CVSS v2 if v3 is 0.\n * Impact is normalized to 0.0-1.0 by dividing by 10.\n */\nfunction getImpact(vuln: NeuVectorVuln): number {\n if (vuln.score_v3 > 0) {\n return vuln.score_v3 / 10;\n }\n if (vuln.score > 0) {\n return vuln.score / 10;\n }\n return 0.5; // default when no score available\n}\n\n/**\n * Constructs the unique ID for a NeuVector vulnerability.\n */\nfunction vulnID(vuln: NeuVectorVuln): string {\n return `${vuln.name}/${vuln.package_name}/${vuln.package_version}`;\n}\n\n/**\n * Generates a human-readable title for the vulnerability.\n */\nfunction vulnTitle(vuln: NeuVectorVuln): string {\n return `NeuVector found a vulnerability to ${vuln.name} in ${vuln.package_name}/${vuln.package_version}.`;\n}\n\n/**\n * Generates the result message describing the fix action.\n */\nfunction vulnMessage(vuln: NeuVectorVuln): string {\n if (!vuln.fixed_version) {\n return `Vulnerable package ${vuln.package_name} is at version ${vuln.package_version}. No fixed version available.`;\n }\n return `Vulnerable package ${vuln.package_name} is at version ${vuln.package_version}. Update to fixed version ${vuln.fixed_version}.`;\n}\n\n/**\n * Builds a single EvaluatedRequirement from a NeuVector vulnerability.\n */\nfunction buildRequirement(vuln: NeuVectorVuln): EvaluatedRequirement {\n const cweIDs = extractCWEs(vuln.description);\n const nist = mapCWEToNIST(cweIDs, DEFAULT_REMEDIATION_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n const tags: Record<string, unknown> = {\n nist,\n cci: cciTags,\n };\n\n if (cweIDs.length > 0) {\n tags['cwe'] = cweIDs;\n }\n\n const descriptions: Description[] = [\n { label: 'default', data: vuln.description },\n ];\n\n const results = [\n createResult(ResultStatus.Failed, vulnMessage(vuln), {\n codeDesc: '',\n }),\n ];\n\n return createRequirement(\n vulnID(vuln),\n vulnTitle(vuln),\n descriptions,\n getImpact(vuln),\n results,\n { tags }\n );\n}\n\n/**\n * Constructs the baseline title from the image metadata.\n */\nfunction imageTitle(report: NeuVectorScanReport): string {\n return `${report.registry}/${report.repository}:${report.tag} - Digest: ${report.digest} - Image ID: ${report.image_id}`;\n}\n\n/**\n * Constructs the target name from the image metadata.\n */\nfunction targetNameFromReport(report: NeuVectorScanReport): string {\n return `${report.registry}/${report.repository}:${report.tag}`;\n}\n\n/**\n * Converts NeuVector container vulnerability scan JSON output to HDF format.\n *\n * Each vulnerability becomes a separate requirement with a unique\n * ID of name/package_name/package_version. Impact is derived from the\n * CVSS v3 score (preferred) or CVSS v2 score as fallback, normalized to 0-1.\n *\n * CWE identifiers are extracted from vulnerability descriptions via regex\n * and mapped to NIST 800-53 controls. When no CWE is found, default\n * remediation NIST tags (SI-2, RA-5) are used.\n *\n * @param input - NeuVector scan JSON string\n * @returns HDF JSON string\n */\nexport async function convertNeuvectorToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('neuvector: empty input');\n }\n validateInputSize(input, 'neuvector');\n\n const scan = parseJSON<NeuVectorScan>(input);\n\n if (!scan || typeof scan !== 'object' || !('report' in scan)) {\n throw new Error('neuvector: invalid JSON structure');\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const { items: limitedVulns, truncated } = limitArray(\n scan.report.vulnerabilities ?? []\n );\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(\n `WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${scan.report.vulnerabilities.length})`\n );\n }\n\n // Deduplicate by composite ID (name/package_name/package_version)\n const seen = new Set<string>();\n const requirements: EvaluatedRequirement[] = [];\n for (const vuln of limitedVulns) {\n const id = vulnID(vuln);\n if (seen.has(id)) {\n continue;\n }\n seen.add(id);\n requirements.push(buildRequirement(vuln));\n }\n\n const title = imageTitle(scan.report);\n\n const baseline = createMinimalBaseline(\n 'NeuVector Scan',\n requirements,\n {\n resultsChecksum,\n title,\n }\n ) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'neuvector-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'NeuVector',\n toolFormat: 'JSON',\n baselines: [baseline],\n components: [\n {\n name: targetNameFromReport(scan.report),\n type: Copyright.ContainerImage,\n labels: {\n image: `${scan.report.registry}/${scan.report.repository}:${scan.report.tag}`,\n registry: scan.report.registry,\n },\n },\n ],\n timestamp: new Date(),\n });\n}\n","import { parseXml } from '@mitre/hdf-utilities';\nimport { nistToCci } from '@mitre/hdf-mappings';\nimport {\n inputChecksum,\n buildNistCciTags,\n limitArray,\n stripHTML,\n ensureArray,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n validateInputSize,\n} from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Tool,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n} from '@mitre/hdf-schema';\n\n// NIST 800-53 reference name used by Fortify in Description.References\nconst NIST_REFERENCE_NAME =\n 'Standards Mapping - NIST Special Publication 800-53 Revision 4';\n\n\n// Regex to match NIST control identifiers like SI-10, AC-2\nconst NIST_PATTERN = /[a-zA-Z]{2}-\\d+/g;\n\n// --- FVDL XML types ---\n\ninterface FVDLParsed {\n FVDL: {\n CreatedTS?: { date?: string; time?: string };\n UUID?: string;\n Build?: {\n BuildID?: string;\n NumberFiles?: string;\n SourceBasePath?: string;\n };\n Vulnerabilities?: {\n Vulnerability?: FVDLVulnerability | FVDLVulnerability[];\n };\n Description?: FVDLDescription | FVDLDescription[];\n Snippets?: {\n Snippet?: FVDLSnippet | FVDLSnippet[];\n };\n EngineData?: {\n EngineVersion?: string;\n };\n };\n}\n\ninterface FVDLVulnerability {\n ClassInfo?: {\n ClassID?: string;\n Kingdom?: string;\n Type?: string;\n Subtype?: string;\n AnalyzerName?: string;\n DefaultSeverity?: string;\n };\n InstanceInfo?: {\n InstanceID?: string;\n InstanceSeverity?: string;\n Confidence?: string;\n };\n AnalysisInfo?: {\n Unified?: {\n Trace?: {\n Primary?: {\n Entry?: FVDLEntry | FVDLEntry[];\n };\n };\n };\n };\n}\n\ninterface FVDLEntry {\n NodeRef?: { id?: string };\n Node?: {\n isDefault?: string;\n SourceLocation?: {\n path?: string;\n line?: string;\n lineEnd?: string;\n colStart?: string;\n colEnd?: string;\n contextId?: string;\n snippet?: string;\n };\n };\n}\n\ninterface FVDLDescription {\n classID?: string;\n contentType?: string;\n Abstract?: string;\n Explanation?: string;\n Recommendations?: string;\n References?: {\n Reference?: FVDLReference | FVDLReference[];\n };\n}\n\ninterface FVDLReference {\n Title?: string;\n Author?: string;\n Publisher?: string;\n Source?: string;\n}\n\ninterface FVDLSnippet {\n id?: string;\n File?: string;\n StartLine?: string;\n EndLine?: string;\n Text?: string;\n}\n\n// --- Helpers ---\n\nfunction buildSnippetMap(snippets: FVDLSnippet[]): Map<string, FVDLSnippet> {\n const map = new Map<string, FVDLSnippet>();\n for (const s of snippets) {\n if (s.id) {\n map.set(s.id, s);\n }\n }\n return map;\n}\n\nfunction groupVulnsByClassID(vulns: FVDLVulnerability[]): Map<string, FVDLVulnerability[]> {\n const groups = new Map<string, FVDLVulnerability[]>();\n for (const vuln of vulns) {\n const classID = vuln.ClassInfo?.ClassID ?? 'unknown';\n const existing = groups.get(classID);\n if (existing) {\n existing.push(vuln);\n } else {\n groups.set(classID, [vuln]);\n }\n }\n return groups;\n}\n\nfunction extractNISTFromReferences(refs: FVDLReference[]): string[] {\n for (const ref of refs) {\n if (ref.Author === NIST_REFERENCE_NAME) {\n const matches = ref.Title?.match(NIST_PATTERN);\n if (matches && matches.length > 0) {\n return matches;\n }\n }\n }\n return [];\n}\n\nfunction formatSnippet(snippet: FVDLSnippet): string {\n const text = (snippet.Text ?? '').trim();\n return `Path: ${snippet.File ?? ''}\\nStartLine: ${snippet.StartLine ?? ''}, EndLine: ${snippet.EndLine ?? ''}\\nCode:\\n${text}`;\n}\n\nfunction buildCodeDesc(\n vuln: FVDLVulnerability,\n snippetMap: Map<string, FVDLSnippet>,\n): string {\n const parts: string[] = [];\n const entries = ensureArray(vuln.AnalysisInfo?.Unified?.Trace?.Primary?.Entry);\n\n for (const entry of entries) {\n if (!entry.Node) continue;\n\n const snippetID = entry.Node.SourceLocation?.snippet;\n if (!snippetID) {\n const path = entry.Node.SourceLocation?.path;\n const line = entry.Node.SourceLocation?.line;\n if (path) {\n parts.push(`Path: ${path}\\nLine: ${line ?? ''}`);\n }\n continue;\n }\n\n const snippet = snippetMap.get(snippetID);\n if (snippet) {\n parts.push(formatSnippet(snippet));\n }\n }\n\n if (parts.length === 0) {\n return `ClassID: ${vuln.ClassInfo?.ClassID ?? ''}, InstanceID: ${vuln.InstanceInfo?.InstanceID ?? ''}`;\n }\n\n return parts.join('\\n');\n}\n\nfunction buildRequirement(\n desc: FVDLDescription,\n vulns: FVDLVulnerability[],\n snippetMap: Map<string, FVDLSnippet>,\n startTimeStr: string,\n): EvaluatedRequirement {\n // Extract NIST tags from Description References\n const refs = ensureArray(desc.References?.Reference);\n let nistTags = extractNISTFromReferences(refs);\n if (nistTags.length === 0) {\n nistTags = [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n }\n const cciTags = nistToCci(nistTags);\n const tags = buildNistCciTags(nistTags, cciTags);\n\n // Title from Abstract (HTML stripped)\n const title = stripHTML(desc.Abstract ?? '');\n\n // Default description from Explanation (HTML stripped)\n let explanationText = stripHTML(desc.Explanation ?? '');\n if (!explanationText) {\n explanationText = title;\n }\n const descriptions: Description[] = [\n { label: 'default', data: explanationText },\n ];\n\n // Fix description from Recommendations\n if (desc.Recommendations) {\n descriptions.push({\n label: 'fix',\n data: stripHTML(desc.Recommendations),\n });\n }\n\n // Impact from the first vulnerability's DefaultSeverity / 5\n let impact = 0;\n if (vulns.length > 0) {\n const severity = parseFloat(vulns[0]!.ClassInfo?.DefaultSeverity ?? '0');\n impact = severity / 5.0;\n }\n\n // Build results — one per vulnerability instance\n const { items: limitedVulns, truncated } = limitArray(vulns);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${vulns.length})`);\n }\n\n const results: RequirementResult[] = limitedVulns.map(vuln => ({\n status: ResultStatus.Failed,\n codeDesc: buildCodeDesc(vuln, snippetMap),\n startTime: new Date(startTimeStr),\n }));\n\n return {\n id: desc.classID ?? 'unknown',\n title,\n impact,\n tags,\n descriptions,\n results,\n };\n}\n\n// --- Main converter ---\n\n/**\n * Converts Fortify FVDL XML to HDF format.\n *\n * Descriptions are used as requirements (one per unique classID).\n * Vulnerabilities are mapped to results under their corresponding Description.\n * Snippets provide code context for result code descriptions.\n *\n * @param input - Fortify FVDL XML string\n * @returns HDF JSON string\n */\nexport async function convertFortifyToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('fortify: empty input');\n }\n validateInputSize(input, 'fortify');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Parse FVDL XML — use stopNodes to preserve embedded HTML in Abstract/Explanation\n const parsed = parseXml(input, {\n stopNodes: ['FVDL.Description.Abstract', 'FVDL.Description.Explanation'],\n }) as unknown as FVDLParsed;\n\n if (!parsed.FVDL) {\n throw new Error('fortify: invalid FVDL — missing <FVDL> root element');\n }\n\n const fvdl = parsed.FVDL;\n\n // Build snippet map\n const snippets = ensureArray(fvdl.Snippets?.Snippet);\n const snippetMap = buildSnippetMap(snippets);\n\n // Get vulnerabilities grouped by ClassID\n const vulns = ensureArray(fvdl.Vulnerabilities?.Vulnerability);\n const vulnGroups = groupVulnsByClassID(vulns);\n\n // Get descriptions\n const descriptions = ensureArray(fvdl.Description);\n const { items: limitedDescs, truncated: truncatedDescs } = limitArray(descriptions);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncatedDescs) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedDescs.length} Description items (original: ${descriptions.length})`);\n }\n\n // Build timestamp string from CreatedTS\n const createdDate = fvdl.CreatedTS?.date ?? '';\n const createdTime = fvdl.CreatedTS?.time ?? '';\n const startTimeStr = `${createdDate}T${createdTime}`;\n\n // Build requirements — one per Description classID\n const requirements: EvaluatedRequirement[] = limitedDescs.map(desc => {\n const classVulns = vulnGroups.get(desc.classID ?? '') ?? [];\n return buildRequirement(desc, classVulns, snippetMap, startTimeStr);\n });\n\n // Build baseline\n const title = 'Fortify Static Analyzer Scan';\n const summary = `Fortify Static Analyzer Scan of UUID: ${fvdl.UUID ?? ''}`;\n const version = fvdl.EngineData?.EngineVersion ?? '';\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'Fortify Scan',\n requirements,\n {\n resultsChecksum,\n title,\n summary,\n version,\n status: 'loaded',\n },\n ) as EvaluatedBaseline;\n\n // Component name from SourceBasePath\n const targetName = fvdl.Build?.SourceBasePath ?? fvdl.Build?.BuildID ?? 'Unknown';\n\n const tool: Tool = {\n name: 'Fortify',\n format: 'FVDL',\n };\n\n const hdfResult: HdfResults = {\n baselines: [baseline],\n components: [\n {\n name: targetName,\n type: Copyright.Repository,\n },\n ],\n generator: {\n name: 'fortify-to-hdf',\n version: '1.0.0',\n },\n tool,\n };\n\n // Set timestamp from CreatedTS\n if (createdDate) {\n hdfResult.timestamp = new Date(startTimeStr);\n }\n\n return JSON.stringify(hdfResult, null, 2);\n}\n","/**\n * Prisma Cloud CSV to HDF converter.\n *\n * Prisma Cloud exports compliance scan results as CSV with one row per finding.\n * Findings are grouped by Hostname, producing one baseline per host.\n * Each finding maps to a single requirement with a single failed result.\n */\n\nimport { parseCsv } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, buildNistCciTags, limitArrayWithWarning, DEFAULT_REMEDIATION_NIST_TAGS, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n\n/** Required CSV columns that must be present */\nconst REQUIRED_COLUMNS = ['Hostname', 'Compliance ID', 'Severity', 'Type', 'Description'];\n\n/**\n * A single row from the Prisma Cloud CSV export.\n */\ninterface PrismaRecord {\n Hostname: string;\n Distro: string;\n 'CVE ID': string;\n 'Compliance ID': string;\n Type: string;\n Severity: string;\n Packages: string;\n Description: string;\n Cause: string;\n 'Fix Status': string;\n Published: string;\n 'Vulnerability Link': string;\n}\n\n/**\n * Prisma uses non-standard severity names: \"important\" and \"moderate\"\n * in addition to the standard critical/high/medium/low.\n */\nfunction getImpact(severity: string): number {\n switch (severity.toLowerCase()) {\n case 'critical':\n return 1.0;\n case 'important':\n return 0.9;\n case 'high':\n return 0.7;\n case 'moderate':\n case 'medium':\n return 0.5;\n case 'low':\n return 0.3;\n default:\n return 0.5;\n }\n}\n\n/**\n * Returns NIST tags based on whether the finding has a CVE.\n * CVE findings get remediation tags; non-CVE compliance findings get static analysis tags.\n */\nfunction getNistTags(cveID: string): string[] {\n if (cveID) {\n return DEFAULT_REMEDIATION_NIST_TAGS;\n }\n return DEFAULT_STATIC_ANALYSIS_NIST_TAGS;\n}\n\n/**\n * Constructs the requirement ID following the heimdall2 pattern:\n * - CVE findings: \"{ComplianceID}-{CVEID}\"\n * - Non-CVE compliance: \"{ComplianceID}-{Distro}-{Severity}\"\n */\nfunction makeRequirementID(rec: PrismaRecord): string {\n if (rec['CVE ID']) {\n return `${rec['Compliance ID']}-${rec['CVE ID']}`;\n }\n return `${rec['Compliance ID']}-${rec.Distro}-${rec.Severity}`;\n}\n\n/**\n * Builds the code description following the heimdall2 pattern.\n */\nfunction makeCodeDesc(rec: PrismaRecord): string {\n let result = '';\n if (rec.Type === 'image') {\n if (rec.Packages !== '') {\n result += `Version check of package: ${rec.Packages}`;\n }\n } else if (rec.Type === 'linux') {\n if (rec.Distro !== '') {\n result += `Configuration check for ${rec.Distro}`;\n }\n } else {\n result += `${rec.Type} check for ${rec.Hostname}`;\n }\n if (rec.Description) {\n result += `\\n\\n${rec.Description}`;\n }\n return result;\n}\n\n/**\n * Builds the result message from Fix Status and Cause fields.\n */\nfunction makeMessage(rec: PrismaRecord): string {\n const hasFixStatus = rec['Fix Status'] !== '';\n const hasCause = rec.Cause !== '';\n\n if (hasFixStatus && hasCause) {\n return `Fix Status: ${rec['Fix Status']}\\n\\n${rec.Cause}`;\n } else if (hasFixStatus) {\n return `Fix Status: ${rec['Fix Status']}`;\n } else if (hasCause) {\n return `Cause: ${rec.Cause}`;\n }\n return 'Unknown';\n}\n\n/**\n * Builds the requirement title following the heimdall2 pattern.\n */\nfunction makeTitle(rec: PrismaRecord): string {\n return `${rec.Hostname}-${rec.Distro}-${rec.Type}`;\n}\n\n/**\n * Builds a single EvaluatedRequirement from a Prisma record.\n */\nfunction buildRequirement(rec: PrismaRecord): EvaluatedRequirement {\n const id = makeRequirementID(rec);\n const title = makeTitle(rec);\n const codeDesc = makeCodeDesc(rec);\n const message = makeMessage(rec);\n\n const nist = getNistTags(rec['CVE ID']);\n const cciTags = nistToCci(nist);\n\n const extras: Record<string, unknown> = {};\n if (rec['CVE ID']) {\n extras['cve'] = [rec['CVE ID']];\n }\n\n const tags = buildNistCciTags(nist, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n const descriptions: Description[] = [\n { label: 'default', data: rec.Description },\n ];\n\n const results = [\n createResult(ResultStatus.Failed, message, {\n codeDesc,\n }),\n ];\n\n return createRequirement(\n id,\n title,\n descriptions,\n getImpact(rec.Severity),\n results,\n { tags },\n );\n}\n\n/**\n * Groups records by hostname, preserving insertion order.\n */\nfunction groupByHostname(records: PrismaRecord[]): Map<string, PrismaRecord[]> {\n const groups = new Map<string, PrismaRecord[]>();\n for (const rec of records) {\n const existing = groups.get(rec.Hostname);\n if (existing) {\n existing.push(rec);\n } else {\n groups.set(rec.Hostname, [rec]);\n }\n }\n return groups;\n}\n\n/**\n * Builds an HDF baseline from all records for a single host.\n */\nfunction buildBaseline(\n hostname: string,\n records: PrismaRecord[],\n resultsChecksum: Checksum,\n): EvaluatedBaseline {\n const limitedRecords = limitArrayWithWarning(records, 'finding');\n\n const requirements = limitedRecords.map(rec => buildRequirement(rec));\n\n const title = `Prisma Cloud Scan (${hostname})`;\n\n return createMinimalBaseline(\n 'Prisma Cloud Scan',\n requirements,\n {\n resultsChecksum,\n title,\n },\n ) as EvaluatedBaseline;\n}\n\n/**\n * Converts Prisma Cloud CSV compliance scan output to HDF format.\n * Records are grouped by hostname, producing one baseline per host.\n *\n * @param input - Prisma Cloud CSV string\n * @returns HDF JSON string\n */\nexport async function convertPrismaToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('prisma: empty input');\n }\n validateInputSize(input, 'prisma');\n\n // Parse CSV\n const records = parseCsv<PrismaRecord>(input);\n\n // Validate required columns exist by checking the first record\n if (records.length === 0) {\n throw new Error('prisma: no data rows in CSV');\n }\n const firstRecord = records[0]!;\n for (const col of REQUIRED_COLUMNS) {\n if (!(col in firstRecord)) {\n throw new Error(`prisma: missing required CSV column \"${col}\"`);\n }\n }\n\n const resultsChecksum = await inputChecksum(input);\n const hostGroups = groupByHostname(records);\n\n const baselines: EvaluatedBaseline[] = [];\n const components: HdfResults['components'] = [];\n\n for (const [hostname, hostRecords] of hostGroups) {\n baselines.push(buildBaseline(hostname, hostRecords, resultsChecksum));\n components.push({ name: hostname, type: Copyright.Host });\n }\n\n return buildHdfResults({\n generatorName: 'prisma-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Prisma Cloud',\n toolFormat: 'CSV',\n baselines,\n components,\n timestamp: new Date(),\n });\n}\n","import { parseXmlWithArrays } from '@mitre/hdf-utilities';\nimport {\n nistToCci,\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n getOwaspNistControl,\n getCweNistControl,\n} from '@mitre/hdf-mappings';\nimport {\n inputChecksum,\n buildNistCciTags,\n limitArray,\n stripHTML,\n validateInputSize,\n buildHdfResults,\n} from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n} from '@mitre/hdf-schema';\n\n// --- Netsparker/Invicti XML input types ---\n\ninterface NetsparkerXml {\n 'netsparker-enterprise'?: NetsparkerEnterprise;\n 'invicti-enterprise'?: NetsparkerEnterprise;\n}\n\ninterface NetsparkerEnterprise {\n generated?: string;\n target?: NetsparkerTarget;\n vulnerabilities?: {\n vulnerability?: NetsparkerVuln[];\n };\n}\n\ninterface NetsparkerTarget {\n 'scan-id'?: string;\n url?: string;\n initiated?: string;\n duration?: string;\n}\n\ninterface NetsparkerVuln {\n LookupId?: string;\n url?: string;\n type?: string;\n name?: string;\n severity?: string;\n certainty?: string;\n confirmed?: string;\n state?: string;\n FirstSeenDate?: string;\n LastSeenDate?: string;\n classification?: NetsparkerClassification;\n 'http-request'?: NetsparkerHttpRequest;\n 'http-response'?: NetsparkerHttpResponse;\n description?: string;\n impact?: string;\n 'remedial-actions'?: string;\n 'exploitation-skills'?: string;\n 'remedial-procedure'?: string;\n 'remedy-references'?: string;\n 'external-references'?: string;\n 'proof-of-concept'?: string;\n}\n\ninterface NetsparkerClassification {\n owasp?: string;\n wasc?: string;\n cwe?: string;\n capec?: string;\n iso27001?: string;\n}\n\ninterface NetsparkerHttpRequest {\n method?: string;\n content?: string;\n}\n\ninterface NetsparkerHttpResponse {\n 'status-code'?: string;\n duration?: string;\n content?: string;\n}\n\n// --- Severity to impact mapping ---\n\nconst IMPACT_MAPPING: Record<string, number> = {\n 'critical': 1.0,\n 'high': 0.7,\n 'medium': 0.5,\n 'low': 0.3,\n 'best_practice': 0.0,\n 'information': 0.0,\n};\n\nfunction getImpact(severity: string): number {\n return IMPACT_MAPPING[severity.toLowerCase()] ?? 0.5;\n}\n\n// --- Format helpers ---\n\nfunction formatCodeDesc(request: NetsparkerHttpRequest | undefined): string {\n const parts: string[] = [];\n parts.push(`http-request : ${request?.content ?? ''}`);\n parts.push(`method : ${request?.method ?? ''}`);\n return parts.join('\\n');\n}\n\nfunction formatMessage(response: NetsparkerHttpResponse | undefined): string {\n const parts: string[] = [];\n parts.push(`http-response : ${response?.content ?? ''}`);\n parts.push(`duration : ${response?.duration ?? ''}`);\n parts.push(`status-code : ${response?.['status-code'] ?? ''}`);\n return parts.join('\\n');\n}\n\nfunction formatControlDesc(vuln: NetsparkerVuln): string {\n const parts: string[] = [];\n if (vuln.description) {\n parts.push(stripHTML(vuln.description));\n }\n if (vuln['exploitation-skills']) {\n parts.push(`Exploitation-skills: ${vuln['exploitation-skills']}`);\n }\n const cweVal = vuln.classification?.cwe ?? '';\n const owaspVal = vuln.classification?.owasp ?? '';\n if (cweVal || owaspVal) {\n parts.push(`Classification: cwe=>${cweVal}, owasp=>${owaspVal}`);\n }\n if (vuln.impact) {\n parts.push(`Impact: ${stripHTML(vuln.impact)}`);\n }\n if (vuln.FirstSeenDate) {\n parts.push(`FirstSeenDate: ${vuln.FirstSeenDate}`);\n }\n if (vuln.LastSeenDate) {\n parts.push(`LastSeenDate: ${vuln.LastSeenDate}`);\n }\n if (vuln.certainty) {\n parts.push(`Certainty: ${vuln.certainty}`);\n }\n if (vuln.type) {\n parts.push(`Type: ${vuln.type}`);\n }\n if (vuln.confirmed) {\n parts.push(`Confirmed: ${vuln.confirmed}`);\n }\n return parts.join('\\n');\n}\n\n/**\n * Performs dual NIST mapping from both CWE and OWASP IDs.\n * Returns a deduplicated sorted list of NIST controls, falling back to\n * DEFAULT_STATIC_ANALYSIS_NIST_TAGS if no mappings are found.\n */\nfunction mapNISTFromCWEAndOWASP(cweID: string, owaspID: string): string[] {\n const controls = new Set<string>();\n\n // CWE -> NIST\n if (cweID) {\n const numericId = parseInt(cweID, 10);\n if (!isNaN(numericId)) {\n const nistControl = getCweNistControl(numericId);\n if (nistControl) {\n controls.add(nistControl);\n }\n }\n }\n\n // OWASP -> NIST\n if (owaspID) {\n const nistControl = getOwaspNistControl(owaspID);\n if (nistControl) {\n controls.add(nistControl);\n }\n }\n\n return controls.size > 0\n ? [...controls].sort()\n : [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n}\n\n/**\n * Builds a single EvaluatedRequirement from a vulnerability.\n */\nfunction buildRequirement(\n vuln: NetsparkerVuln,\n initiated: string,\n): EvaluatedRequirement {\n const cweID = vuln.classification?.cwe ?? '';\n const owaspID = vuln.classification?.owasp ?? '';\n\n const nist = mapNISTFromCWEAndOWASP(cweID, owaspID);\n const cciTags = nistToCci(nist);\n\n const extras: Record<string, unknown> = {};\n if (cweID) {\n extras.cweid = cweID;\n }\n if (owaspID) {\n extras.owasp = owaspID;\n }\n\n const tags = buildNistCciTags(nist, cciTags, Object.keys(extras).length > 0 ? extras : undefined);\n\n // Default description\n const defaultDesc = formatControlDesc(vuln);\n const descriptions: Description[] = [\n { label: 'default', data: defaultDesc || vuln.name || '' },\n ];\n\n // Check description\n const checkParts: string[] = [];\n if (vuln['exploitation-skills']) {\n checkParts.push(`Exploitation-skills: ${vuln['exploitation-skills']}`);\n }\n if (vuln['proof-of-concept']) {\n checkParts.push(`Proof-of-concept: ${stripHTML(vuln['proof-of-concept'])}`);\n }\n if (checkParts.length > 0) {\n descriptions.push({ label: 'check', data: stripHTML(checkParts.join('\\n')) });\n }\n\n // Fix description\n const fixParts: string[] = [];\n if (vuln['remedial-actions']) {\n fixParts.push(`Remedial-actions: ${stripHTML(vuln['remedial-actions'])}`);\n }\n if (vuln['remedial-procedure']) {\n fixParts.push(`Remedial-procedure: ${stripHTML(vuln['remedial-procedure'])}`);\n }\n if (vuln['remedy-references']) {\n fixParts.push(`Remedy-references: ${stripHTML(vuln['remedy-references'])}`);\n }\n if (fixParts.length > 0) {\n descriptions.push({ label: 'fix', data: fixParts.join('\\n') });\n }\n\n // Result\n const codeDesc = formatCodeDesc(vuln['http-request']);\n const message = formatMessage(vuln['http-response']);\n\n const startTime = initiated ? new Date(initiated) : new Date('0001-01-01T00:00:00Z');\n\n const results: RequirementResult[] = [{\n status: ResultStatus.Failed,\n codeDesc,\n message,\n startTime,\n }];\n\n const impact = getImpact(vuln.severity ?? '');\n\n return {\n id: vuln.LookupId ?? '',\n title: vuln.name ?? undefined,\n impact,\n tags,\n descriptions,\n results,\n };\n}\n\n/**\n * Converts Netsparker/Invicti XML scan results to HDF format.\n * Handles both <netsparker-enterprise> and <invicti-enterprise> root elements.\n *\n * @param input - Netsparker/Invicti XML string\n * @returns HDF JSON string\n */\nexport async function convertNetsparkerToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('netsparker: empty input');\n }\n validateInputSize(input, 'netsparker');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Parse XML — ensure vulnerability is always treated as array\n const parsed = parseXmlWithArrays(input, ['vulnerability']) as unknown as NetsparkerXml;\n\n // Detect root element\n const isInvicti = !!parsed['invicti-enterprise'];\n const data: NetsparkerEnterprise = parsed['invicti-enterprise'] ?? parsed['netsparker-enterprise'] ?? {};\n\n if (!data.vulnerabilities && !data.target) {\n throw new Error('netsparker: invalid XML — missing expected root element');\n }\n\n const toolName = isInvicti ? 'Invicti' : 'Netsparker';\n const vulns = data.vulnerabilities?.vulnerability ?? [];\n const target = data.target ?? {};\n const initiated = target.initiated ?? '';\n\n const { items: limitedVulns, truncated } = limitArray(vulns);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedVulns.length} vulnerability items (original: ${vulns.length})`);\n }\n\n // Build one requirement per vulnerability\n const requirements: EvaluatedRequirement[] = limitedVulns.map(\n vuln => buildRequirement(vuln, initiated),\n );\n\n const title = `${toolName} Enterprise Scan ID: ${target['scan-id'] ?? ''} URL: ${target.url ?? ''}`;\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'Netsparker Scan',\n requirements,\n {\n resultsChecksum,\n title,\n },\n ) as EvaluatedBaseline;\n\n const targetName = target.url ?? 'Unknown';\n\n return buildHdfResults({\n generatorName: 'netsparker-to-hdf',\n converterVersion: '1.0.0',\n toolName,\n toolFormat: 'XML',\n baselines: [baseline],\n components: [\n {\n name: targetName,\n type: Copyright.Application,\n },\n ],\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n getScoutsuiteNistControl,\n nistToCci,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, buildNistCciTags, limitArrayWithWarning, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * ScoutSuite JSON output structures\n */\ninterface ScoutSuiteReport {\n account_id: string;\n environment?: string;\n last_run: LastRun;\n partition?: string;\n provider_code?: string;\n provider_name: string;\n services: Record<string, ServiceData>;\n}\n\ninterface LastRun {\n ruleset_about?: string;\n ruleset_name: string;\n time: string;\n version: string;\n}\n\ninterface ServiceData {\n findings?: Record<string, ScoutSuiteFinding>;\n [key: string]: unknown;\n}\n\ninterface ScoutSuiteFinding {\n checked_items: number;\n compliance?: ComplianceItem[] | null;\n description: string;\n flagged_items: number;\n id_suffix?: string;\n items: string[];\n level: string;\n path?: string;\n rationale: string;\n references?: string[] | null;\n remediation?: string | null;\n service?: string;\n}\n\ninterface ComplianceItem {\n name: string;\n reference: string;\n version: string;\n}\n\n/**\n * Maps ScoutSuite level strings to HDF impact values.\n */\nfunction getImpact(level: string): number {\n switch (level.toLowerCase()) {\n case 'danger':\n return 0.7;\n case 'warning':\n return 0.5;\n default:\n return 0.3;\n }\n}\n\n/**\n * Determines the HDF result status based on checked and flagged item counts.\n */\nfunction getStatus(checkedItems: number, flaggedItems: number): ResultStatus {\n if (checkedItems === 0) {\n return ResultStatus.NotReviewed;\n }\n if (flaggedItems === 0) {\n return ResultStatus.Passed;\n }\n return ResultStatus.Failed;\n}\n\n/**\n * Builds the result message based on checked/flagged item counts.\n */\nfunction getMessage(checkedItems: number, flaggedItems: number, items: string[]): string {\n if (checkedItems === 0) {\n return 'Skipped because no items were checked';\n }\n if (flaggedItems === 0) {\n return `0 flagged items out of ${checkedItems} checked items`;\n }\n let msg = `${flaggedItems} flagged items out of ${checkedItems} checked items`;\n if (items.length > 0) {\n msg += ':\\n' + items.join('\\n');\n }\n return msg;\n}\n\n/** Known ScoutSuite JS variable assignment prefixes. */\nconst SCOUTSUITE_JS_PREFIX = /^\\s*(scoutsuite_results)\\s*=\\s*$/i;\n\n/**\n * Strips the \"scoutsuite_results = \" JS variable prefix from input.\n * ScoutSuite outputs results as a JS file with this prefix on the first line.\n * Only strips prefixes matching known ScoutSuite patterns; unrecognized prefixes\n * are left intact so JSON parsing produces a descriptive error.\n */\nfunction stripJSPrefix(input: string): string {\n const idx = input.indexOf('{');\n if (idx < 0) {\n return input;\n }\n if (idx === 0) {\n return input; // Already valid JSON\n }\n const prefix = input.substring(0, idx).trim();\n if (SCOUTSUITE_JS_PREFIX.test(prefix)) {\n return input.substring(idx);\n }\n // Unknown prefix — don't strip, let JSON parser report the error\n return input;\n}\n\n/**\n * Gets NIST controls for a ScoutSuite rule, splitting pipe-delimited values.\n */\nfunction getNistControls(ruleID: string): string[] {\n const ctrl = getScoutsuiteNistControl(ruleID);\n if (!ctrl) {\n return ['SA-11', 'RA-5']; // fallback\n }\n return ctrl.split('|');\n}\n\n/**\n * Collapses all service findings into a flat list of (ruleID, finding) pairs.\n */\nfunction collapseFindings(report: ScoutSuiteReport): Array<[string, ScoutSuiteFinding]> {\n const result: Array<[string, ScoutSuiteFinding]> = [];\n\n const serviceNames = Object.keys(report.services).sort();\n for (const serviceName of serviceNames) {\n const svcRaw = report.services[serviceName];\n if (!svcRaw) continue;\n\n // The service object may have properties beyond \"findings\" (filters, regions, etc.)\n // We only care about findings\n const svc = svcRaw as ServiceData;\n if (!svc.findings) continue;\n\n const ruleNames = Object.keys(svc.findings).sort();\n for (const ruleName of ruleNames) {\n const finding = svc.findings[ruleName];\n if (finding) {\n result.push([ruleName, finding]);\n }\n }\n }\n\n return result;\n}\n\n/**\n * Builds a single EvaluatedRequirement from a ScoutSuite finding.\n */\nfunction buildRequirement(\n ruleID: string,\n finding: ScoutSuiteFinding,\n startTime: string,\n): EvaluatedRequirement {\n const nist = getNistControls(ruleID);\n const cciTags = nistToCci(nist);\n const tags = buildNistCciTags(nist, cciTags);\n\n const descriptions: Description[] = [\n { label: 'default', data: finding.rationale },\n ];\n if (finding.remediation) {\n descriptions.push({ label: 'fix', data: finding.remediation });\n }\n\n const status = getStatus(finding.checked_items, finding.flagged_items);\n const message = getMessage(finding.checked_items, finding.flagged_items, finding.items);\n\n const resultObj = createResult(status, message, {\n codeDesc: finding.description,\n startTime: startTime ? new Date(startTime) : undefined,\n });\n\n return createRequirement(\n ruleID,\n finding.description,\n descriptions,\n getImpact(finding.level),\n [resultObj],\n { tags },\n );\n}\n\n/**\n * Converts ScoutSuite output to HDF format.\n * Input may be a JS file with \"scoutsuite_results = \" prefix or pure JSON.\n *\n * @param input - ScoutSuite JS/JSON string\n * @returns HDF JSON string\n */\nexport async function convertScoutsuiteToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('scoutsuite: empty input');\n }\n validateInputSize(input, 'scoutsuite');\n\n // Strip JS variable prefix if present\n const jsonStr = stripJSPrefix(input);\n\n const resultsChecksum: Checksum = await inputChecksum(jsonStr);\n\n const report = parseJSON<ScoutSuiteReport>(jsonStr);\n\n if (!report || typeof report !== 'object') {\n throw new Error('scoutsuite: invalid JSON');\n }\n\n // Collapse all service findings\n const findingPairs = collapseFindings(report);\n const limitedPairs = limitArrayWithWarning(findingPairs, 'finding');\n\n const requirements: EvaluatedRequirement[] = limitedPairs.map(\n ([ruleID, finding]) => buildRequirement(ruleID, finding, report.last_run.time),\n );\n\n const title = `Scout Suite Report using ${report.last_run.ruleset_name} ruleset on ${report.provider_name} with account ${report.account_id}`;\n\n const baseline = createMinimalBaseline(\n 'ScoutSuite Scan',\n requirements,\n {\n resultsChecksum,\n title,\n summary: report.last_run.ruleset_about,\n },\n ) as EvaluatedBaseline;\n\n const targetName = `${report.last_run.ruleset_name} ruleset:${report.provider_name}:${report.account_id}`;\n\n return buildHdfResults({\n generatorName: 'scoutsuite-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'ScoutSuite',\n toolFormat: 'JSON',\n toolVersion: report.last_run.version,\n baselines: [baseline],\n components: [{\n name: targetName,\n type: Copyright.CloudAccount,\n labels: {\n account: report.account_id,\n provider: report.provider_code ?? report.provider_name,\n },\n }],\n timestamp: report.last_run.time ? new Date(report.last_run.time) : new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n nistToCci,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, buildNistCciTags, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/** Maximum Conveyor score (used for normalization). */\nconst CONVEYOR_MAX_SCORE = 1000;\n\n/** Top-level Conveyor JSON output structure. */\ninterface ConveyorData {\n api_error_message?: string;\n api_response?: ConveyorAPIResp;\n api_server_version?: string;\n}\n\ninterface ConveyorAPIResp {\n file_tree?: Record<string, FileTreeNode>;\n results?: Record<string, ConveyorResult>;\n params?: Record<string, unknown>;\n max_score?: number;\n}\n\ninterface FileTreeNode {\n name?: string[];\n sha256?: string;\n children?: Record<string, FileTreeNode>;\n score?: number;\n size?: number;\n type?: string;\n}\n\ninterface ConveyorResult {\n sha256: string;\n classification?: string;\n created?: string;\n response: ConveyorResp;\n result: ConveyorScore;\n size?: number | null;\n type?: string | null;\n}\n\ninterface ConveyorResp {\n service_name: string;\n service_version?: string;\n service_context?: unknown;\n service_debug_info?: unknown;\n service_tool_version?: unknown;\n supplementary?: unknown;\n milestones?: ConveyorMilestone;\n}\n\ninterface ConveyorMilestone {\n service_started?: string;\n service_completed?: string;\n}\n\ninterface ConveyorScore {\n score: number;\n sections: ConveyorSection[];\n}\n\ninterface ConveyorSection {\n title_text?: string;\n body?: unknown;\n body_format?: string;\n classification?: string;\n depth?: number;\n heuristic?: Heuristic | null;\n}\n\ninterface Heuristic {\n heur_id?: string;\n name?: string;\n score?: number;\n}\n\n/**\n * Recursively walks the file tree, collecting sha256 -> filename mappings.\n */\nfunction collateSHAAndFilenames(tree: Record<string, FileTreeNode>): Map<string, string> {\n const result = new Map<string, string>();\n for (const [sha, node] of Object.entries(tree)) {\n if (node.name && node.name.length > 0) {\n result.set(sha, node.name[0]!);\n }\n if (node.children && Object.keys(node.children).length > 0) {\n for (const [childSha, childName] of collateSHAAndFilenames(node.children)) {\n result.set(childSha, childName);\n }\n }\n }\n return result;\n}\n\n/**\n * Maps a Conveyor score to an HDF result status.\n * Score 0 = Passed, non-zero = Failed.\n */\nfunction determineStatus(score: number): ResultStatus {\n return score === 0 ? ResultStatus.Passed : ResultStatus.Failed;\n}\n\n/**\n * Normalizes a Conveyor score (0-1000) to HDF impact (0.0-1.0).\n */\nfunction scoreToImpact(score: number): number {\n if (score <= 0) return 0.0;\n if (score >= CONVEYOR_MAX_SCORE) return 1.0;\n return score / CONVEYOR_MAX_SCORE;\n}\n\n/**\n * Extracts a string from a body field that may be null or a string.\n */\nfunction bodyToString(body: unknown): string {\n if (body === null || body === undefined) return '';\n if (typeof body === 'string') return body;\n return String(body);\n}\n\n/**\n * Creates the code_desc field content from a Conveyor section.\n */\nfunction buildCodeDesc(section: ConveyorSection, scannerName: string): string {\n const parts: string[] = [];\n\n if (scannerName === 'Moldy' || scannerName === 'Stigma' || scannerName === 'Clamav') {\n parts.push(`title_text:${section.title_text ?? ''}`);\n parts.push(`body:${bodyToString(section.body)}`);\n parts.push(`body_format:${section.body_format ?? ''}`);\n parts.push(`classification:${section.classification ?? ''}`);\n parts.push(`depth:${section.depth ?? 0}`);\n if (section.heuristic) {\n parts.push(`heuristic_heur_id:${section.heuristic.heur_id ?? ''}`);\n parts.push(`heuristic_score:${section.heuristic.score ?? 0}`);\n parts.push(`heuristic_name:${section.heuristic.name ?? ''}`);\n }\n } else if (scannerName === 'CodeQuality') {\n parts.push(`body:${bodyToString(section.body)}`);\n parts.push(`body_format:${section.body_format ?? ''}`);\n parts.push(`classification:${section.classification ?? ''}`);\n parts.push(`depth:${section.depth ?? 0}`);\n parts.push(`title_text:${section.title_text ?? ''}`);\n } else {\n return JSON.stringify(section);\n }\n\n return parts.join('\\n');\n}\n\n/**\n * Groups Conveyor results by their service (scanner) name.\n */\nfunction groupResultsByScanner(\n results: Record<string, ConveyorResult>,\n): { scanners: string[]; groups: Map<string, ConveyorResult[]> } {\n const groups = new Map<string, ConveyorResult[]>();\n for (const result of Object.values(results)) {\n const name = result.response.service_name;\n const existing = groups.get(name);\n if (existing) {\n existing.push(result);\n } else {\n groups.set(name, [result]);\n }\n }\n const scanners = [...groups.keys()].sort();\n return { scanners, groups };\n}\n\n/**\n * Builds an HDF requirement from a single Conveyor result.\n */\nfunction buildRequirementFromResult(\n result: ConveyorResult,\n filename: string,\n): EvaluatedRequirement {\n const nist = DEFAULT_STATIC_ANALYSIS_NIST_TAGS;\n const cciTags = nistToCci(nist);\n const tags = buildNistCciTags(nist, cciTags);\n\n // Build description from sections\n let descText = '';\n if (result.result.sections.length > 0) {\n descText = result.result.sections\n .map(s => s.title_text ?? '')\n .filter(t => t.length > 0)\n .join('; ');\n }\n if (!descText) {\n descText = `Conveyor scan result for ${result.sha256}`;\n }\n\n const descriptions: Description[] = [\n { label: 'default', data: descText },\n ];\n\n const scannerName = result.response.service_name;\n const startTimeStr = result.response.milestones?.service_started ?? '';\n const startTime = startTimeStr ? new Date(startTimeStr) : new Date();\n const score = result.result.score;\n const status = determineStatus(score);\n\n let results;\n if (result.result.sections.length > 0) {\n results = result.result.sections.map(section => {\n const codeDesc = buildCodeDesc(section, scannerName);\n return createResult(status, undefined, {\n codeDesc,\n startTime,\n });\n });\n } else {\n results = [\n createResult(status, undefined, {\n codeDesc: `No sections reported by ${scannerName}`,\n startTime,\n }),\n ];\n }\n\n return createRequirement(\n result.sha256,\n filename,\n descriptions,\n scoreToImpact(score),\n results,\n { tags },\n );\n}\n\n/**\n * Builds an HDF baseline for a single scanner's results.\n */\nfunction buildScannerBaseline(\n scannerName: string,\n results: ConveyorResult[],\n shaMap: Map<string, string>,\n resultsChecksum: Checksum,\n): EvaluatedBaseline {\n const requirements: EvaluatedRequirement[] = results.map(result => {\n const filename = shaMap.get(result.sha256) ?? '';\n return buildRequirementFromResult(result, filename);\n });\n\n const title = `Conveyor Scan (${scannerName})`;\n\n return createMinimalBaseline(\n 'Conveyor Scan',\n requirements,\n {\n resultsChecksum,\n title,\n },\n ) as EvaluatedBaseline;\n}\n\n/**\n * Converts Conveyor scan results to HDF format.\n * Results are grouped by scanner name, producing one baseline per scanner.\n *\n * @param input - Conveyor JSON string\n * @returns HDF JSON string\n */\nexport async function convertConveyorToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('conveyor: empty input');\n }\n validateInputSize(input, 'conveyor');\n\n const data = parseJSON<ConveyorData>(input);\n\n if (!data || typeof data !== 'object') {\n throw new Error('conveyor: invalid JSON');\n }\n\n if (!data.api_response) {\n throw new Error('conveyor: missing api_response field');\n }\n\n if (!data.api_response.results) {\n throw new Error('conveyor: missing api_response.results field');\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n // Build SHA -> filename mapping from file tree\n const shaMap = data.api_response.file_tree\n ? collateSHAAndFilenames(data.api_response.file_tree)\n : new Map<string, string>();\n\n // Group results by scanner\n const { scanners, groups } = groupResultsByScanner(data.api_response.results);\n\n const baselines: EvaluatedBaseline[] = scanners.map(scannerName =>\n buildScannerBaseline(\n scannerName,\n groups.get(scannerName)!,\n shaMap,\n resultsChecksum,\n ),\n );\n\n // Build target name from params.description\n let targetName = 'Conveyor Scan';\n if (data.api_response.params) {\n const desc = data.api_response.params['description'];\n if (typeof desc === 'string' && desc.length > 0) {\n targetName = desc;\n }\n }\n\n return buildHdfResults({\n generatorName: 'conveyor-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Conveyor',\n toolFormat: 'JSON',\n baselines,\n components: [{ name: targetName, type: Copyright.Application }],\n timestamp: new Date(),\n });\n}\n","/**\n * Veracode DetailedReport XML to HDF converter.\n *\n * Converts Veracode static analysis and SCA findings into HDF format.\n * Produces two types of controls:\n * - CWE-based: From severity categories (static analysis findings)\n * - CVE-based: From SCA vulnerable components\n *\n * Uses attributeNamePrefix '@_' to disambiguate XML attributes from child\n * elements (critical for the `vulnerabilities` attr/element collision on\n * `<component>`).\n */\n\nimport { parseXml } from '@mitre/hdf-utilities';\nimport { nistToCci } from '@mitre/hdf-mappings';\nimport { inputChecksum, mapCWEToNIST, buildNistCciTags, ensureArray, DEFAULT_REMEDIATION_NIST_TAGS, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n Description,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n} from '@mitre/hdf-schema';\n\n/** Attribute prefix used by fast-xml-parser — all XML attributes are accessed via `@_name`. */\nconst A = '@_';\n\n\n/** Veracode severity level (0-5) to HDF impact mapping. */\nconst IMPACT_MAPPING: Map<string, number> = new Map([\n ['5', 0.9],\n ['4', 0.7],\n ['3', 0.5],\n ['2', 0.3],\n ['1', 0.1],\n ['0', 0.0],\n]);\n\nfunction veracodeSeverityToImpact(severity: string): number {\n return IMPACT_MAPPING.get(severity) ?? 0.1;\n}\n\n// ---- Utility functions ----\n\n/** Get an attribute from a parsed XML node. */\nfunction attr(node: Record<string, unknown>, name: string): string {\n return (node[`${A}${name}`] as string) ?? '';\n}\n\n/** Decode common XML/HTML character references (&#xHH; and &#NNN;). */\nfunction decodeXmlEntities(s: string): string {\n return s\n .replace(/&#x([0-9a-fA-F]+);/g, (_, hex) => String.fromCharCode(parseInt(hex as string, 16)))\n .replace(/&#(\\d+);/g, (_, dec) => String.fromCharCode(parseInt(dec as string, 10)));\n}\n\n/** Parse Veracode timestamp format (\"2021-12-29 22:16:36 UTC\") to Date. */\nfunction parseVeracodeTimestamp(ts: string): Date | undefined {\n if (!ts) return undefined;\n // Decode XML entities in timestamps (e.g., : -> :)\n const decoded = decodeXmlEntities(ts);\n const d = new Date(decoded.replace(' UTC', 'Z').replace(' ', 'T'));\n return isNaN(d.getTime()) ? undefined : d;\n}\n\n/** Format description paragraphs into text. */\nfunction formatDesc(desc: Record<string, unknown> | undefined): string {\n if (!desc) return '';\n const paras = ensureArray(desc.para as Record<string, unknown> | Record<string, unknown>[]);\n return paras.map(p => attr(p, 'text')).filter(Boolean).join('\\n');\n}\n\n/** Format recommendations into text. */\nfunction formatRecommendations(rec: Record<string, unknown> | undefined): string {\n if (!rec) return '';\n const paras = ensureArray(rec.para as Record<string, unknown> | Record<string, unknown>[]);\n const parts: string[] = [];\n for (const p of paras) {\n const text = attr(p, 'text');\n if (text) parts.push(text);\n const bullets = ensureArray(p.bulletitem as Record<string, unknown> | Record<string, unknown>[]);\n for (const b of bullets) {\n const btext = attr(b, 'text');\n if (btext) parts.push(btext);\n }\n }\n return parts.join('\\n');\n}\n\n/** Format CWE data for the cweid tag. */\nfunction formatCWEData(cwes: Record<string, unknown>[]): string {\n return cwes.map(c => {\n let entry = `CWE-${attr(c, 'cweid')}: ${attr(c, 'cwename')}`;\n const categories: [string, string][] = [\n ['pcrirelated', attr(c, 'pcirelated')],\n ['owasp', attr(c, 'owasp')],\n ['sans', attr(c, 'sans')],\n ['certc', attr(c, 'certc')],\n ['certcpp', attr(c, 'certcpp')],\n ['certjava', attr(c, 'certjava')],\n ['owaspmobile', attr(c, 'owaspmobile')],\n ];\n for (const [name, val] of categories) {\n if (val) entry += `${name}: ${val}\\n`;\n }\n return entry;\n }).join('\\n');\n}\n\n/** Format CWE descriptions for the cweDescription tag. */\nfunction formatCWEDesc(cwes: Record<string, unknown>[]): string {\n return cwes.map(c => {\n const desc = c.description as Record<string, unknown> | undefined;\n const text = desc?.text as Record<string, unknown> | undefined;\n const descText = text ? attr(text, 'text') : '';\n return `CWE-${attr(c, 'cweid')}: ${attr(c, 'cwename')} Description: ${descText}; `;\n }).join('\\n');\n}\n\n/** Format a static flaw as a code description. */\nfunction formatFlawCodeDesc(flaw: Record<string, unknown>): string {\n const sourcefilepath = attr(flaw, 'sourcefilepath');\n if (!sourcefilepath) {\n return `Issue ID: ${attr(flaw, 'issueid')}`;\n }\n\n const parts: string[] = [`Sourcefile Path: ${sourcefilepath}`];\n const fields: [string, string][] = [\n ['Line Number', attr(flaw, 'line')],\n ['Affect Policy Compliance', attr(flaw, 'affects_policy_compliance')],\n ['Remediation Effort', attr(flaw, 'remediationeffort')],\n ['Exploit level', attr(flaw, 'exploitLevel')],\n ['Issue ID', attr(flaw, 'issueid')],\n ['Module', attr(flaw, 'module')],\n ['Type', attr(flaw, 'type')],\n ['CWE ID', attr(flaw, 'cweid')],\n ['Date First Occurence', attr(flaw, 'date_first_occurrence')],\n ['CIA Impact', attr(flaw, 'cia_impact')],\n ['Description', attr(flaw, 'description')],\n ['Source File', attr(flaw, 'sourcefile')],\n ['Scope', attr(flaw, 'scope')],\n ['PCI Related', attr(flaw, 'pcirelated')],\n ['Function Prototype', attr(flaw, 'functionprototype')],\n ['Function Relative Location', attr(flaw, 'functionrelativelocation')],\n ];\n\n for (const [title, value] of fields) {\n if (value) parts.push(`${title}: ${value}`);\n }\n\n return parts.join('\\n');\n}\n\n/** Format an SCA component as a code description. */\nfunction formatSCACodeDesc(comp: Record<string, unknown>): string {\n const parts: string[] = [`component_id: ${attr(comp, 'component_id')}`];\n const fields: [string, string][] = [\n ['sha1', attr(comp, 'sha1')],\n ['file_name', attr(comp, 'file_name')],\n ['max_cvss_score', attr(comp, 'max_cvss_score')],\n ['version', attr(comp, 'version')],\n ['library', attr(comp, 'library')],\n ['library_id', attr(comp, 'library_id')],\n ['vendor', attr(comp, 'vendor')],\n ['description', attr(comp, 'description')],\n ['added_date', attr(comp, 'added_date')],\n ['component_affects_policy_compliance', attr(comp, 'component_affects_policy_compliance')],\n ];\n\n for (const [title, value] of fields) {\n if (value) parts.push(`${title}: ${value}`);\n }\n\n // File paths\n const filePaths = comp.file_paths as Record<string, unknown> | undefined;\n if (filePaths) {\n const fps = ensureArray(filePaths.file_path as Record<string, unknown> | Record<string, unknown>[]);\n for (const fp of fps) {\n const val = attr(fp, 'value');\n if (val) parts.push(`file_path: ${val}`);\n }\n }\n\n return parts.join('\\n');\n}\n\n// ---- Requirement builders ----\n\n/** Build CWE-based requirements from severity categories. */\nfunction buildCWERequirements(severities: Record<string, unknown>[], firstBuildDate: string): EvaluatedRequirement[] {\n const requirements: EvaluatedRequirement[] = [];\n\n for (const sev of severities) {\n const impact = veracodeSeverityToImpact(attr(sev, 'level'));\n const categories = ensureArray(sev.category as Record<string, unknown> | Record<string, unknown>[]);\n\n for (const cat of categories) {\n requirements.push(buildCWERequirement(cat, impact, firstBuildDate));\n }\n }\n\n return requirements;\n}\n\n/** Build a single CWE-based requirement from a category. */\nfunction buildCWERequirement(cat: Record<string, unknown>, impact: number, firstBuildDate: string): EvaluatedRequirement {\n const cwes = ensureArray(cat.cwe as Record<string, unknown> | Record<string, unknown>[]);\n\n // Collect CWE IDs for NIST mapping\n const cweIDs = cwes.map(c => attr(c, 'cweid')).filter(Boolean);\n const nist = mapCWEToNIST(cweIDs, DEFAULT_REMEDIATION_NIST_TAGS);\n const cciTags = nistToCci(nist);\n\n // Build tags\n const extras: Record<string, unknown> = {};\n const cweData = formatCWEData(cwes);\n if (cweData) extras.cweid = cweData;\n const cweDescStr = formatCWEDesc(cwes);\n if (cweDescStr) extras.cweDescription = cweDescStr;\n\n const tags = buildNistCciTags(nist, cciTags, extras);\n\n // Build descriptions\n const descriptions: Description[] = [\n { label: 'default', data: formatDesc(cat.desc as Record<string, unknown> | undefined) },\n ];\n const recText = formatRecommendations(cat.recommendations as Record<string, unknown> | undefined);\n if (recText) {\n descriptions.push({ label: 'fix', data: recText });\n }\n\n // Collect all flaws from all CWEs in this category\n const startTime = parseVeracodeTimestamp(firstBuildDate) ?? new Date();\n const results = cwes.flatMap(c => {\n const staticflaws = c.staticflaws as Record<string, unknown> | undefined;\n const flaws = ensureArray(staticflaws?.flaw as Record<string, unknown> | Record<string, unknown>[]);\n return flaws.map(flaw => createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatFlawCodeDesc(flaw),\n startTime,\n }));\n });\n\n return createRequirement(\n attr(cat, 'categoryid'),\n attr(cat, 'categoryname'),\n descriptions,\n impact,\n results,\n { tags },\n );\n}\n\n/** Build CVE-based requirements from SCA components. */\nfunction buildCVERequirements(\n sca: Record<string, unknown> | undefined,\n firstBuildDate: string,\n): EvaluatedRequirement[] {\n if (!sca) return [];\n const vulnComps = sca.vulnerable_components as Record<string, unknown> | undefined;\n if (!vulnComps?.component) return [];\n\n const components = ensureArray(vulnComps.component as Record<string, unknown> | Record<string, unknown>[]);\n\n // Group vulnerabilities by CVE ID across all components\n interface CVEEntry {\n vuln: Record<string, unknown>;\n components: Record<string, unknown>[];\n }\n\n const cveOrder: string[] = [];\n const cveMap = new Map<string, CVEEntry>();\n\n for (const comp of components) {\n const vulnCountAttr = attr(comp, 'vulnerabilities');\n if (vulnCountAttr === '0') continue;\n\n // With @_ prefix, child element <vulnerabilities> is at key 'vulnerabilities',\n // and the attribute is at '@_vulnerabilities'\n const vulnsElem = comp.vulnerabilities as Record<string, unknown> | undefined;\n if (!vulnsElem?.vulnerability) continue;\n const vulns = ensureArray(vulnsElem.vulnerability as Record<string, unknown> | Record<string, unknown>[]);\n\n for (const vuln of vulns) {\n const cveID = attr(vuln, 'cve_id');\n if (!cveID) continue;\n\n const existing = cveMap.get(cveID);\n if (existing) {\n existing.components.push(comp);\n } else {\n cveOrder.push(cveID);\n cveMap.set(cveID, { vuln, components: [comp] });\n }\n }\n }\n\n return cveOrder.map(cveID => {\n const entry = cveMap.get(cveID)!;\n return buildCVERequirement(entry.vuln, entry.components, firstBuildDate);\n });\n}\n\n/** Build a single CVE-based requirement. */\nfunction buildCVERequirement(\n vuln: Record<string, unknown>,\n components: Record<string, unknown>[],\n firstBuildDate: string,\n): EvaluatedRequirement {\n const impact = veracodeSeverityToImpact(attr(vuln, 'severity'));\n\n // Map CWE to NIST\n const cweID = attr(vuln, 'cwe_id');\n let nist: string[];\n if (cweID) {\n nist = mapCWEToNIST([cweID.replace(/^CWE-/, '')], DEFAULT_REMEDIATION_NIST_TAGS);\n } else {\n nist = DEFAULT_REMEDIATION_NIST_TAGS;\n }\n const cciTags = nistToCci(nist);\n const extras: Record<string, unknown> = {};\n if (cweID) extras.cwe = cweID;\n const tags = buildNistCciTags(nist, cciTags, extras);\n\n // One result per affected component\n const startTime = parseVeracodeTimestamp(firstBuildDate) ?? new Date();\n\n const results = components.map(comp => createResult(ResultStatus.Failed, undefined, {\n codeDesc: formatSCACodeDesc(comp),\n startTime,\n }));\n\n const cveSummary = attr(vuln, 'cve_summary');\n const cveId = attr(vuln, 'cve_id');\n const descriptions: Description[] = [\n { label: 'default', data: cveSummary || '' },\n ];\n\n return createRequirement(\n cveId,\n cveId,\n descriptions,\n impact,\n results,\n { tags },\n );\n}\n\n// ---- Main converter ----\n\n/**\n * Convert Veracode DetailedReport XML to HDF JSON string.\n *\n * @param input - Veracode DetailedReport XML string\n * @returns HDF JSON string\n */\nexport async function convertVeracodeToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('veracode: empty input');\n }\n validateInputSize(input, 'veracode');\n\n // Parse XML with @_ attribute prefix to disambiguate attributes from child elements.\n // This is critical for the <component> element where both `vulnerabilities` attribute\n // (count) and child `<vulnerabilities>` element (list) exist.\n const parsed = parseXml(input, { attributeNamePrefix: '@_' }) as Record<string, unknown>;\n\n // Check for summary report\n if ('summaryreport' in parsed) {\n throw new Error('veracode: summary reports are not supported; use a detailed report');\n }\n\n const report = parsed.detailedreport as Record<string, unknown> | undefined;\n if (!report) {\n throw new Error('veracode: invalid XML - no <detailedreport> root element');\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const firstBuildDate = attr(report, 'first_build_submitted_date');\n\n // Ensure severities is an array\n const severities = ensureArray(report.severity as Record<string, unknown> | Record<string, unknown>[]);\n\n // Build CWE-based requirements\n const cweRequirements = buildCWERequirements(severities, firstBuildDate);\n\n // Build CVE-based requirements from SCA\n const cveRequirements = buildCVERequirements(\n report.software_composition_analysis as Record<string, unknown> | undefined,\n firstBuildDate,\n );\n\n // Merge\n const allRequirements = [...cweRequirements, ...cveRequirements];\n\n // Get module name for title\n let title: string | undefined;\n const staticAnalysis = report['static-analysis'] as Record<string, unknown> | undefined;\n if (staticAnalysis) {\n const modules = staticAnalysis.modules as Record<string, unknown> | undefined;\n if (modules?.module) {\n const moduleList = ensureArray(modules.module as Record<string, unknown> | Record<string, unknown>[]);\n if (moduleList.length > 0) {\n title = attr(moduleList[0]!, 'name');\n }\n }\n }\n\n const baseline = createMinimalBaseline('Veracode Scan', allRequirements, {\n resultsChecksum,\n title,\n version: attr(report, 'policy_version'),\n summary: attr(report, 'policy_name'),\n }) as EvaluatedBaseline;\n\n const targetName = attr(report, 'app_name') || 'Veracode Application';\n const timestamp = parseVeracodeTimestamp(firstBuildDate);\n\n return buildHdfResults({\n generatorName: 'veracode-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Veracode',\n toolFormat: 'XML',\n baselines: [baseline],\n components: [{ name: targetName, type: Copyright.Application }],\n timestamp,\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport {\n DEFAULT_STATIC_ANALYSIS_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport { inputChecksum, limitArray, stripHTML, buildNistCciTags, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Microsoft Graph Secure Score structures.\n * Defined locally to avoid external dependency on @microsoft/microsoft-graph-types.\n */\ninterface CombinedResponse {\n secureScore: SecureScoreResponse;\n profiles: ProfileResponse;\n}\n\ninterface SecureScoreResponse {\n '@odata.context'?: string;\n value: SecureScore[];\n}\n\ninterface SecureScore {\n id: string;\n azureTenantId: string;\n activeUserCount?: number;\n createdDateTime: string;\n currentScore?: number;\n enabledServices?: string[];\n licensedUserCount?: number;\n maxScore?: number;\n controlScores: ControlScore[];\n averageComparativeScores?: unknown[];\n}\n\ninterface ControlScore {\n controlCategory: string;\n controlName: string;\n description: string;\n score: number;\n lastSynced?: string;\n implementationStatus: string;\n on?: string;\n scoreInPercentage: number;\n}\n\ninterface ProfileResponse {\n '@odata.context'?: string;\n '@odata.nextLink'?: string;\n value: SecureScoreControlProfile[];\n}\n\ninterface SecureScoreControlProfile {\n id: string;\n azureTenantId?: string;\n controlCategory?: string;\n title?: string;\n maxScore?: number;\n rank?: unknown;\n remediation?: string;\n remediationImpact?: string;\n service?: string;\n threats?: unknown;\n tier?: string;\n userImpact?: string;\n}\n\n/**\n * Returns all profiles matching a given control name.\n */\nfunction getMatchingProfiles(\n profiles: SecureScoreControlProfile[],\n controlName: string,\n): SecureScoreControlProfile[] {\n return profiles.filter(p => p.id === controlName);\n}\n\n/**\n * Gets the title from matching profiles, or falls back to category:name.\n */\nfunction getTitle(\n profiles: SecureScoreControlProfile[],\n cs: ControlScore,\n): string {\n const matched = getMatchingProfiles(profiles, cs.controlName);\n const titles = matched\n .map(p => p.title)\n .filter((t): t is string => t !== undefined && t !== '');\n\n if (titles.length > 0) {\n return titles[0]!;\n }\n\n // Fallback\n return [cs.controlCategory, cs.controlName].filter(Boolean).join(':');\n}\n\n/**\n * Computes impact from profile maxScore (maxScore / 10.0).\n * Falls back to 0.5 when no matching profile exists.\n * Capped at 1.0.\n */\nfunction getImpact(\n profiles: SecureScoreControlProfile[],\n cs: ControlScore,\n): number {\n const matched = getMatchingProfiles(profiles, cs.controlName);\n if (matched.length === 0) {\n return 0.5;\n }\n\n const maxScore = Math.max(...matched.map(p => p.maxScore ?? 0));\n const impact = maxScore / 10.0;\n return Math.min(Math.round(impact * 100) / 100, 1.0);\n}\n\n/**\n * Determines the result status based on scoreInPercentage and profile maxScore.\n */\nfunction getStatus(\n profiles: SecureScoreControlProfile[],\n cs: ControlScore,\n): ResultStatus {\n if (cs.scoreInPercentage === 100) {\n return ResultStatus.Passed;\n }\n\n const matched = getMatchingProfiles(profiles, cs.controlName);\n if (matched.length === 0) {\n return ResultStatus.Failed;\n }\n\n const maxScore = Math.max(...matched.map(p => p.maxScore ?? 0));\n if (cs.score === maxScore) {\n return ResultStatus.Passed;\n }\n\n return ResultStatus.Failed;\n}\n\n/**\n * Builds an EvaluatedRequirement from a ControlScore.\n */\nfunction buildRequirement(\n cs: ControlScore,\n profiles: SecureScoreControlProfile[],\n createdDateTime: string,\n): EvaluatedRequirement {\n const id = `${cs.controlCategory}:${cs.controlName}`;\n const title = getTitle(profiles, cs);\n const impact = getImpact(profiles, cs);\n const status = getStatus(profiles, cs);\n\n // NIST tags: use default static analysis tags\n const nist = [...DEFAULT_STATIC_ANALYSIS_NIST_TAGS];\n const tags = buildNistCciTags(nist, []);\n\n // Descriptions\n const descriptions: Description[] = [\n { label: 'default', data: stripHTML(cs.description) },\n ];\n\n // Add fix description from profile remediation\n const matched = getMatchingProfiles(profiles, cs.controlName);\n if (matched.length > 0) {\n const remediations = matched\n .map(p => p.remediation)\n .filter((r): r is string => r !== undefined && r !== '');\n if (remediations.length > 0) {\n descriptions.push({ label: 'fix', data: stripHTML(remediations[0]!) });\n }\n\n const impacts = matched\n .map(p => p.remediationImpact)\n .filter((r): r is string => r !== undefined && r !== '');\n if (impacts.length > 0) {\n descriptions.push({ label: 'rationale', data: stripHTML(impacts[0]!) });\n }\n }\n\n // CodeDesc from implementationStatus\n const codeDesc = cs.implementationStatus || 'No implementation status provided';\n\n // StartTime from createdDateTime\n const startTime = createdDateTime ? new Date(createdDateTime) : undefined;\n\n const results = [\n createResult(status, undefined, {\n codeDesc,\n ...(startTime ? { startTime } : {}),\n }),\n ];\n\n return createRequirement(\n id,\n title,\n descriptions,\n impact,\n results,\n { tags },\n );\n}\n\n/**\n * Converts Microsoft Secure Score combined JSON to HDF format.\n *\n * Input is the combined JSON containing both secureScore and profiles data\n * from the Microsoft Graph API.\n *\n * @param input - Combined JSON string with secureScore and profiles\n * @returns HDF JSON string\n */\nexport async function convertMsftSecureScoreToHdf(input: string): Promise<string> {\n if (!input || input.trim().length === 0) {\n throw new Error('msft-secure-score: empty input');\n }\n validateInputSize(input, 'msft-secure-score');\n\n const combined = parseJSON<CombinedResponse>(input);\n\n if (!combined || typeof combined !== 'object') {\n throw new Error('msft-secure-score: invalid JSON');\n }\n\n if (!combined.secureScore?.value) {\n throw new Error('msft-secure-score: missing secureScore.value');\n }\n if (!combined.profiles?.value) {\n throw new Error('msft-secure-score: missing profiles.value');\n }\n if (combined.secureScore.value.length === 0) {\n throw new Error('msft-secure-score: secureScore.value is empty');\n }\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const profiles = combined.profiles.value;\n let tenantId = '';\n\n const baselines: EvaluatedBaseline[] = combined.secureScore.value.map(ss => {\n if (!tenantId) {\n tenantId = ss.azureTenantId;\n }\n\n const { items: limitedControlScores, truncated } = limitArray(ss.controlScores);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedControlScores.length} controlScore items (original: ${ss.controlScores.length})`);\n }\n\n const requirements = limitedControlScores.map(cs =>\n buildRequirement(cs, profiles, ss.createdDateTime),\n );\n\n const title = `Azure Secure Score report - Tenant ID: ${ss.azureTenantId} - Run ID: ${ss.id}`;\n\n return createMinimalBaseline(\n 'Microsoft Secure Score',\n requirements,\n {\n resultsChecksum,\n title,\n },\n ) as EvaluatedBaseline;\n });\n\n return buildHdfResults({\n generatorName: 'msft-secure-score-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Microsoft Secure Score',\n toolFormat: 'JSON',\n baselines,\n components: [{\n name: `Azure Tenant: ${tenantId}`,\n type: Copyright.CloudAccount,\n labels: { account: tenantId, provider: 'azure' },\n }],\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { convertSarifToHdf } from '../../sarif-to-hdf/typescript/converter.js';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfResults, Component } from '@mitre/hdf-schema';\nimport { Copyright } from '@mitre/hdf-schema';\n\n// --- MSDO-specific SARIF type definitions ---\n// These capture fields that the generic SARIF converter ignores.\n\ninterface MsdoSarif {\n runs: MsdoRun[];\n}\n\ninterface MsdoRun {\n tool: {\n driver: MsdoDriver;\n };\n versionControlProvenance?: VersionControlProvenance[];\n policies?: MsdoPolicy[];\n results?: MsdoResult[];\n}\n\ninterface MsdoDriver {\n name?: string;\n organization?: string;\n product?: string;\n fullName?: string;\n properties?: Record<string, unknown>;\n}\n\ninterface VersionControlProvenance {\n repositoryUri: string;\n revisionId?: string;\n branch?: string;\n}\n\ninterface MsdoPolicy {\n name: string;\n version: string;\n}\n\ninterface MsdoResult {\n ruleId: string;\n properties?: Record<string, unknown>;\n}\n\ninterface RunEnrichment {\n toolTags: Record<string, unknown>;\n policyTag: string;\n resultProps: Map<string, Record<string, unknown>[]>;\n}\n\n/**\n * Converts Microsoft Defender for DevOps SARIF output to HDF format.\n * Delegates base conversion to the generic SARIF converter and enriches\n * the output with MSDO-specific metadata.\n */\nexport async function convertMsftDefenderDevopsToHdf(input: string): Promise<string> {\n validateInputSize(input, 'msft-defender-devops');\n\n // 1. Parse raw SARIF to extract MSDO-specific fields\n const raw = parseJSON<MsdoSarif>(input);\n if (!raw || !Array.isArray(raw.runs)) {\n throw new Error('Invalid MSDO SARIF structure: missing or invalid runs field');\n }\n const { components, runEnrichments } = extractEnrichments(raw);\n\n // 2. Delegate to the generic SARIF converter for base HDF\n const hdfJson = await convertSarifToHdf(input);\n const result = JSON.parse(hdfJson) as HdfResults;\n\n // 3. Apply enrichments\n applyEnrichments(result, components, runEnrichments);\n\n // 4. Override generator name and data source\n if (result.generator) {\n result.generator.name = 'msft-defender-devops-to-hdf';\n }\n if (result.tool) {\n result.tool.name = 'Microsoft Defender for DevOps';\n }\n\n return JSON.stringify(result, null, 2);\n}\n\nfunction extractEnrichments(raw: MsdoSarif): {\n components: Component[];\n runEnrichments: RunEnrichment[];\n} {\n const components: Component[] = [];\n const seenRepos = new Set<string>();\n const runEnrichments: RunEnrichment[] = [];\n\n for (const run of raw.runs) {\n // Extract repository components from versionControlProvenance\n for (const vcp of run.versionControlProvenance ?? []) {\n if (vcp.repositoryUri && !seenRepos.has(vcp.repositoryUri)) {\n seenRepos.add(vcp.repositoryUri);\n const target: Component = {\n name: repoNameFromURI(vcp.repositoryUri),\n type: Copyright.Repository,\n url: vcp.repositoryUri,\n labels: {},\n };\n if (vcp.branch) {\n target.branch = vcp.branch;\n }\n if (vcp.revisionId) {\n target.commit = vcp.revisionId;\n }\n components.push(target);\n }\n }\n\n // Extract tool metadata tags\n const toolTags: Record<string, unknown> = {};\n const driver = run.tool.driver;\n if (driver.organization) {\n toolTags.msdo_organization = driver.organization;\n }\n if (driver.product) {\n toolTags.msdo_product = driver.product;\n }\n if (driver.fullName) {\n toolTags.msdo_fullName = driver.fullName;\n }\n if (driver.properties?.RawName) {\n toolTags.msdo_rawName = driver.properties.RawName;\n }\n if (driver.properties?.IsPreview !== undefined) {\n toolTags.msdo_isPreview = driver.properties.IsPreview;\n }\n\n // Extract policy tags\n let policyTag = '';\n if (run.policies && run.policies.length > 0) {\n policyTag = run.policies.map(p => `${p.name} ${p.version}`).join(', ');\n }\n\n // Extract result-level properties keyed by ruleId\n const resultProps = new Map<string, Record<string, unknown>[]>();\n for (const res of run.results ?? []) {\n if (res.properties && Object.keys(res.properties).length > 0) {\n const existing = resultProps.get(res.ruleId) ?? [];\n existing.push(res.properties);\n resultProps.set(res.ruleId, existing);\n }\n }\n\n runEnrichments.push({ toolTags, policyTag, resultProps });\n }\n\n return { components, runEnrichments };\n}\n\nfunction applyEnrichments(\n result: HdfResults,\n components: Component[],\n runEnrichments: RunEnrichment[],\n): void {\n // Add components\n if (components.length > 0) {\n result.components = components;\n }\n\n // Apply per-baseline (per-run) enrichments\n const baselines = result.baselines ?? [];\n for (let i = 0; i < baselines.length && i < runEnrichments.length; i++) {\n const re = runEnrichments[i]!;\n const requirements = baselines[i]!.requirements ?? [];\n\n for (const req of requirements) {\n const tags = (req.tags ?? {}) as Record<string, unknown>;\n\n // Add tool metadata tags\n for (const [k, v] of Object.entries(re.toolTags)) {\n tags[k] = v;\n }\n\n // Add policy tag\n if (re.policyTag) {\n tags.msdo_policy = re.policyTag;\n }\n\n // Add result-level properties for this requirement's ruleId\n const props = re.resultProps.get(req.id);\n if (props && props.length > 0) {\n tags.msdo_properties = props[0];\n }\n\n req.tags = tags;\n }\n }\n}\n\nfunction repoNameFromURI(uri: string): string {\n const parts = uri.split('/');\n const name = parts[parts.length - 1];\n return name || uri;\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { inputChecksum, limitArray, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Component,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Microsoft Defender for Cloud assessment structures.\n * Derived from Azure REST API: /providers/Microsoft.Security/assessments\n * See: https://learn.microsoft.com/en-us/rest/api/defenderforcloud/assessments/list\n */\ninterface DefenderCloudInput {\n value: Assessment[];\n}\n\ninterface Assessment {\n id: string;\n name: string;\n type: string;\n properties: AssessmentProperties;\n}\n\ninterface AssessmentProperties {\n displayName: string;\n resourceDetails: ResourceDetails;\n status: StatusBlock;\n metadata: Metadata;\n}\n\ninterface ResourceDetails {\n source: string;\n id: string;\n}\n\ninterface StatusBlock {\n code: string;\n cause: string;\n description: string;\n}\n\ninterface Metadata {\n displayName: string;\n assessmentType: string;\n policyDefinitionId: string;\n description: string;\n remediationDescription: string;\n categories: string[];\n severity: string;\n userImpact: string;\n implementationEffort: string;\n threats: string[];\n tactics: string[];\n techniques: string[];\n}\n\n/**\n * Severity to HDF impact mapping.\n */\nconst IMPACT_MAPPING: Record<string, number> = {\n high: 0.7,\n medium: 0.5,\n low: 0.3,\n};\n\n/**\n * Maps Azure status code to HDF ResultStatus.\n */\nfunction mapStatus(code: string): ResultStatus {\n switch (code.toLowerCase()) {\n case 'healthy':\n return ResultStatus.Passed;\n case 'unhealthy':\n return ResultStatus.Failed;\n case 'notapplicable':\n return ResultStatus.NotApplicable;\n default:\n return ResultStatus.NotReviewed;\n }\n}\n\n/**\n * Extracts subscription ID from an Azure resource path.\n */\nfunction extractSubscriptionID(resourcePath: string): string {\n const lower = resourcePath.toLowerCase();\n const idx = lower.indexOf('/subscriptions/');\n if (idx === -1) {\n return '';\n }\n const rest = resourcePath.substring(idx + '/subscriptions/'.length);\n const slashIdx = rest.indexOf('/');\n if (slashIdx !== -1) {\n return rest.substring(0, slashIdx);\n }\n return rest;\n}\n\n/**\n * Converts a group of assessments sharing an assessment ID into one EvaluatedRequirement.\n */\nfunction buildRequirement(assessmentID: string, assessments: Assessment[]): EvaluatedRequirement {\n const rep = assessments[0]!;\n const meta = rep.properties.metadata;\n\n const impact = IMPACT_MAPPING[meta.severity.toLowerCase()] ?? 0.5;\n\n const tags: Record<string, unknown> = {};\n\n if (meta.categories.length > 0) {\n tags['categories'] = meta.categories;\n }\n if (meta.tactics.length > 0) {\n tags['tactics'] = meta.tactics;\n }\n if (meta.techniques.length > 0) {\n tags['techniques'] = meta.techniques;\n }\n if (meta.threats.length > 0) {\n tags['threats'] = meta.threats;\n }\n\n tags['severity'] = meta.severity;\n if (meta.userImpact) {\n tags['userImpact'] = meta.userImpact;\n }\n if (meta.implementationEffort) {\n tags['implementationEffort'] = meta.implementationEffort;\n }\n if (meta.assessmentType) {\n tags['assessmentType'] = meta.assessmentType;\n }\n\n const descriptions: Description[] = [\n { label: 'default', data: meta.description },\n ];\n if (meta.remediationDescription) {\n descriptions.push({ label: 'fix', data: meta.remediationDescription });\n }\n\n const results = assessments.map(buildResultFromAssessment);\n\n return createRequirement(assessmentID, rep.properties.displayName, descriptions, impact, results, { tags });\n}\n\n/**\n * Converts a single assessment into an HDF RequirementResult.\n */\nfunction buildResultFromAssessment(a: Assessment): RequirementResult {\n const status = mapStatus(a.properties.status.code);\n const codeDesc = `Resource: ${a.properties.resourceDetails.id}`;\n const message = a.properties.status.description || a.properties.status.cause || undefined;\n\n return createResult(status, message, { codeDesc });\n}\n\n/**\n * Converts Microsoft Defender for Cloud assessment output to HDF format.\n *\n * @param input - JSON string containing Azure Security Assessments API response\n * @returns HDF JSON string\n */\nexport async function convertMsftDefenderCloudToHdf(input: string): Promise<string> {\n validateInputSize(input, 'msft-defender-cloud');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const raw = parseJSON<DefenderCloudInput>(input);\n\n if (!raw || typeof raw !== 'object') {\n throw new Error('Invalid Defender for Cloud structure: not a valid JSON object');\n }\n\n if (!Array.isArray(raw.value)) {\n throw new Error('Invalid Defender for Cloud structure: missing or invalid value array');\n }\n\n const { items: limitedAssessments, truncated } = limitArray(raw.value);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedAssessments.length} assessment items (original: ${raw.value.length})`);\n }\n\n // Group assessments by name (GUID), preserving insertion order.\n const groups = new Map<string, Assessment[]>();\n for (const a of limitedAssessments) {\n const existing = groups.get(a.name);\n if (existing) {\n existing.push(a);\n } else {\n groups.set(a.name, [a]);\n }\n }\n\n const requirements: EvaluatedRequirement[] = [];\n for (const [assessmentID, assessments] of groups) {\n requirements.push(buildRequirement(assessmentID, assessments));\n }\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'Microsoft Defender for Cloud Assessments',\n requirements,\n { resultsChecksum },\n ) as EvaluatedBaseline;\n\n // Build target from subscription ID\n const components: Component[] = [];\n if (limitedAssessments.length > 0) {\n const subscriptionID = extractSubscriptionID(limitedAssessments[0]!.id);\n if (subscriptionID) {\n components.push({\n name: `Azure Subscription ${subscriptionID}`,\n type: Copyright.CloudAccount,\n accountId: subscriptionID,\n provider: 'azure' as Component['provider'],\n labels: { account: subscriptionID, provider: 'azure' },\n });\n }\n }\n\n return buildHdfResults({\n generatorName: 'msft-defender-cloud-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Microsoft Defender for Cloud',\n toolFormat: 'JSON',\n baselines: [baseline],\n components,\n timestamp: new Date(),\n });\n}\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport { inputChecksum, limitArray, validateInputSize, buildHdfResults } from '../../../shared/typescript/converterutil.js';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n Checksum,\n Component,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n Copyright,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\n\n/**\n * Microsoft Graph Security API v2 alert response structure.\n * Derived from official Microsoft documentation:\n * https://learn.microsoft.com/en-us/graph/api/resources/security-alert\n */\ninterface MdeAlertResponse {\n '@odata.context'?: string;\n value: MdeAlert[];\n}\n\ninterface MdeAlert {\n id: string;\n incidentId?: string;\n status: string;\n severity: string;\n classification?: string | null;\n determination?: string | null;\n serviceSource?: string;\n detectionSource?: string;\n category: string;\n title: string;\n description: string;\n alertWebUrl?: string;\n createdDateTime?: string;\n firstActivityDateTime?: string;\n lastActivityDateTime?: string;\n lastUpdateDateTime?: string;\n resolvedDateTime?: string | null;\n assignedTo?: string | null;\n tenantId?: string;\n actorDisplayName?: string | null;\n threatDisplayName?: string | null;\n threatFamilyName?: string | null;\n mitreTechniques?: string[];\n recommendedActions?: string;\n comments?: unknown[];\n evidence?: MdeEvidence[];\n}\n\ninterface MdeEvidence {\n '@odata.type'?: string;\n deviceDnsName?: string;\n osPlatform?: string;\n mdeDeviceId?: string;\n healthStatus?: string;\n onboardingStatus?: string;\n rbacGroupName?: string;\n processId?: number;\n processCommandLine?: string;\n imageFile?: MdeImageFile;\n detectionStatus?: string;\n parentProcess?: MdeParentProcess;\n fileName?: string;\n filePath?: string;\n sha256?: string;\n}\n\ninterface MdeImageFile {\n fileName?: string;\n filePath?: string;\n sha256?: string;\n}\n\ninterface MdeParentProcess {\n processId?: number;\n imageFile?: MdeImageFile;\n}\n\n/**\n * Severity to HDF impact mapping.\n */\nconst IMPACT_MAPPING: Record<string, number> = {\n high: 0.7,\n medium: 0.5,\n low: 0.3,\n informational: 0.0,\n};\n\n/**\n * Maps MDE severity to HDF impact value.\n */\nfunction severityToImpact(severity: string): number {\n return IMPACT_MAPPING[severity.toLowerCase()] ?? 0.5;\n}\n\n/**\n * Maps MDE alert status + classification to HDF result status.\n * new/inProgress → Failed, resolved with falsePositive → Passed, otherwise → Failed.\n */\nfunction statusToResultStatus(status: string, classification?: string | null): ResultStatus {\n if (status.toLowerCase() === 'resolved') {\n if (classification && classification.toLowerCase() === 'falsepositive') {\n return ResultStatus.Passed;\n }\n return ResultStatus.Failed;\n }\n return ResultStatus.Failed;\n}\n\n/**\n * Formats evidence items into a human-readable code_desc string.\n */\nfunction formatEvidence(evidence: MdeEvidence[]): string {\n if (!evidence || evidence.length === 0) {\n return 'No evidence available';\n }\n\n const parts: string[] = [];\n for (const ev of evidence) {\n const odataType = ev['@odata.type'] ?? '';\n if (odataType.includes('deviceEvidence')) {\n parts.push(`Device: ${ev.deviceDnsName ?? 'unknown'} (OS: ${ev.osPlatform ?? 'unknown'})`);\n } else if (odataType.includes('processEvidence')) {\n if (ev.imageFile) {\n parts.push(`Process: ${ev.imageFile.filePath ?? ''}\\\\${ev.imageFile.fileName ?? ''} (Command: ${ev.processCommandLine ?? ''})`);\n } else {\n parts.push(`Process: (Command: ${ev.processCommandLine ?? ''})`);\n }\n } else if (odataType.includes('fileEvidence')) {\n parts.push(`File: ${ev.filePath ?? ''}\\\\${ev.fileName ?? ''}`);\n } else {\n parts.push(`Evidence type: ${odataType}`);\n }\n }\n\n return parts.join('\\n');\n}\n\n/**\n * Formats the message string for a result.\n */\nfunction formatMessage(alert: MdeAlert): string {\n const parts: string[] = [];\n parts.push(`Alert: ${alert.title}`);\n parts.push(`Status: ${alert.status}`);\n parts.push(`Severity: ${alert.severity}`);\n if (alert.threatDisplayName) {\n parts.push(`Threat: ${alert.threatDisplayName}`);\n }\n if (alert.alertWebUrl) {\n parts.push(`URL: ${alert.alertWebUrl}`);\n }\n return parts.join('\\n');\n}\n\n/**\n * Extracts a Host target from device evidence, or falls back to tenant as cloud account.\n */\nfunction extractDeviceTarget(alert: MdeAlert): Component {\n if (alert.evidence) {\n for (const ev of alert.evidence) {\n const odataType = ev['@odata.type'] ?? '';\n if (odataType.includes('deviceEvidence') && ev.deviceDnsName) {\n const target: Component = {\n name: ev.deviceDnsName,\n type: Copyright.Host,\n labels: { provider: 'azure' },\n };\n if (ev.deviceDnsName) {\n target.fqdn = ev.deviceDnsName;\n }\n if (ev.osPlatform) {\n target.osName = ev.osPlatform;\n }\n return target;\n }\n }\n }\n // No device evidence — use tenant as cloud account\n return {\n name: alert.tenantId ?? 'unknown',\n type: Copyright.CloudAccount,\n accountId: alert.tenantId,\n labels: { account: alert.tenantId ?? '', provider: 'azure' },\n };\n}\n\n/**\n * Builds tags map for a requirement.\n */\nfunction buildTags(alert: MdeAlert): Record<string, unknown> {\n const tags: Record<string, unknown> = {\n nist: ['SA-11', 'RA-5'],\n };\n\n if (alert.category) {\n tags['category'] = alert.category;\n }\n\n if (alert.mitreTechniques && alert.mitreTechniques.length > 0) {\n tags['mitre'] = alert.mitreTechniques;\n }\n\n if (alert.classification) {\n tags['classification'] = alert.classification;\n }\n if (alert.determination) {\n tags['determination'] = alert.determination;\n }\n\n return tags;\n}\n\n/**\n * Converts a single MDE alert to an HDF EvaluatedRequirement.\n */\nfunction alertToRequirement(alert: MdeAlert): EvaluatedRequirement {\n const impact = severityToImpact(alert.severity);\n const status = statusToResultStatus(alert.status, alert.classification);\n\n const codeDesc = formatEvidence(alert.evidence ?? []);\n const message = formatMessage(alert);\n\n const results: RequirementResult[] = [\n createResult(status, message, { codeDesc }),\n ];\n\n const descriptions: Description[] = [\n { label: 'default', data: alert.description },\n ];\n if (alert.recommendedActions) {\n descriptions.push({ label: 'fix', data: alert.recommendedActions });\n }\n\n const tags = buildTags(alert);\n\n return createRequirement(alert.id, alert.title, descriptions, impact, results, { tags });\n}\n\n/**\n * Converts Microsoft Defender for Endpoint alerts (Microsoft Graph Security API v2 format) to HDF.\n * Each alert becomes one requirement with one result.\n *\n * @param input - JSON string of MDE alert response\n * @returns HDF JSON string\n */\nexport async function convertMsftDefenderEndpointToHdf(input: string): Promise<string> {\n validateInputSize(input, 'msft-defender-endpoint');\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const response = parseJSON<MdeAlertResponse>(input);\n\n if (!response || typeof response !== 'object') {\n throw new Error('Invalid Microsoft Defender for Endpoint structure: not a valid JSON object');\n }\n\n if (!Array.isArray(response.value)) {\n throw new Error('Invalid Microsoft Defender for Endpoint structure: missing or invalid value array');\n }\n\n const { items: limitedAlerts, truncated } = limitArray(response.value);\n /* v8 ignore next -- truncation only triggers with >100K items */\n if (truncated) {\n // eslint-disable-next-line no-console\n console.warn(`WARNING: Input truncated at ${limitedAlerts.length} alert items (original: ${response.value.length})`);\n }\n\n const requirements: EvaluatedRequirement[] = limitedAlerts.map(alertToRequirement);\n\n // Build components — deduplicate by device name\n const seenTargets = new Set<string>();\n const components: Component[] = [];\n for (const alert of limitedAlerts) {\n const target = extractDeviceTarget(alert);\n if (!seenTargets.has(target.name)) {\n seenTargets.add(target.name);\n components.push(target);\n }\n }\n\n const baseline: EvaluatedBaseline = createMinimalBaseline(\n 'Microsoft Defender for Endpoint Scan',\n requirements,\n { resultsChecksum },\n ) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'msft-defender-endpoint-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Microsoft Defender for Endpoint',\n baselines: [baseline],\n components,\n timestamp: new Date(),\n });\n}\n","import { parseJSON, buildXml } from '@mitre/hdf-utilities';\nimport type {\n HdfResults,\n EvaluatedRequirement,\n Description,\n} from '@mitre/hdf-schema';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\n\n/** Attribute prefix used by fast-xml-parser to distinguish attrs from elements. */\nconst ATTR = '@_';\n\n/** XML build options that enable attribute rendering via @_ prefix. */\nconst BUILD_OPTIONS = {\n attributeNamePrefix: ATTR,\n textNodeName: '#text',\n ignoreAttributes: false,\n format: true,\n indentBy: ' ',\n suppressEmptyNode: false,\n};\n\n/**\n * Convert HDF Results JSON to XCCDF 1.2 Benchmark XML.\n *\n * @param input - HDF Results JSON string\n * @returns XCCDF 1.2 XML string\n */\nexport function convertHdfToXccdf(input: string): string {\n validateInputSize(input, 'hdf-to-xccdf');\n\n const hdfData = parseJSON<HdfResults>(input);\n\n if (!hdfData || typeof hdfData !== 'object' || !('baselines' in hdfData)) {\n throw new Error('Invalid HDF structure: missing baselines field');\n }\n\n if (!Array.isArray(hdfData.baselines)) {\n throw new Error('Invalid HDF structure: baselines must be an array');\n }\n\n const xmlObj = { Benchmark: buildBenchmarkObj(hdfData) };\n\n const xmlBody = buildXml(xmlObj, BUILD_OPTIONS);\n return `<?xml version=\"1.0\" encoding=\"UTF-8\"?>\\n${xmlBody}`;\n}\n\n/** Wrap a primitive value to force it as a text node in XML output. */\nfunction wrap(\n value: string | number | boolean,\n): { '#text': string | number | boolean } {\n return { '#text': value };\n}\n\n/** Map HDF impact (0.0-1.0) to XCCDF severity string. */\nfunction impactToSeverity(impact: number): string {\n if (impact >= 0.7) return 'high';\n if (impact >= 0.4) return 'medium';\n if (impact >= 0.1) return 'low';\n return 'info';\n}\n\n/** Map HDF result status to XCCDF result value. */\nfunction hdfStatusToXccdf(status: string): string {\n const statusMap: Record<string, string> = {\n passed: 'pass',\n failed: 'fail',\n error: 'error',\n notReviewed: 'notchecked',\n notApplicable: 'notapplicable',\n };\n return statusMap[status] ?? 'unknown';\n}\n\n/** Find a description by label. */\nfunction findDescription(\n descriptions: Description[] | undefined,\n label: string,\n): string | undefined {\n return descriptions?.find((d) => d.label === label)?.data;\n}\n\n/** Replace characters not valid in XCCDF IDs with underscores. */\nfunction sanitizeXccdfId(id: string): string {\n return id.replace(/[^a-zA-Z0-9_.\\-]/g, '_');\n}\n\n/** Build the Benchmark XML object from HDF data. */\nfunction buildBenchmarkObj(hdfData: HdfResults): Record<string, unknown> {\n const benchmark: Record<string, unknown> = {\n [`${ATTR}xmlns`]: 'http://checklists.nist.gov/xccdf/1.2',\n [`${ATTR}resolved`]: '1',\n status: wrap('incomplete'),\n };\n\n if (!hdfData.baselines || hdfData.baselines.length === 0) {\n benchmark[`${ATTR}id`] = 'xccdf_hdf_benchmark_exported';\n benchmark.title = wrap('HDF Export');\n benchmark.version = wrap('1.0');\n return benchmark;\n }\n\n const baseline = hdfData.baselines[0]!;\n\n benchmark[`${ATTR}id`] = sanitizeXccdfId(\n 'xccdf_hdf_benchmark_' + baseline.name,\n );\n benchmark.title = wrap(baseline.title ?? baseline.name);\n benchmark.version = wrap(baseline.version ?? '1.0');\n\n // Profile\n benchmark.Profile = {\n [`${ATTR}id`]: sanitizeXccdfId('xccdf_hdf_profile_' + baseline.name),\n title: wrap(baseline.title ?? baseline.name),\n };\n\n // Rules\n if (baseline.requirements && baseline.requirements.length > 0) {\n benchmark.Rule = baseline.requirements.map((req) => buildRuleObj(req));\n }\n\n // TestResult\n benchmark.TestResult = buildTestResultObj(hdfData, baseline);\n\n return benchmark;\n}\n\n/** Build an XCCDF Rule object from an HDF EvaluatedRequirement. */\nfunction buildRuleObj(req: EvaluatedRequirement): Record<string, unknown> {\n const ruleId = sanitizeXccdfId('xccdf_hdf_rule_' + req.id + '_rule');\n\n const rule: Record<string, unknown> = {\n [`${ATTR}id`]: ruleId,\n [`${ATTR}severity`]: impactToSeverity(req.impact),\n [`${ATTR}selected`]: 'true',\n title: wrap(req.title ?? req.id),\n };\n\n const description = findDescription(req.descriptions, 'default');\n if (description) {\n rule.description = wrap(description);\n }\n\n const fixtext = findDescription(req.descriptions, 'fix');\n if (fixtext) {\n rule.fixtext = wrap(fixtext);\n }\n\n // CCI idents\n if (req.tags && Array.isArray(req.tags['cci'])) {\n const ccis = req.tags['cci'] as string[];\n if (ccis.length > 0) {\n rule.ident = ccis.map((cci) => ({\n [`${ATTR}system`]: 'http://cyber.mil/cci',\n '#text': cci,\n }));\n }\n }\n\n // Check content\n const checkContent = findDescription(req.descriptions, 'check');\n if (checkContent) {\n rule.check = {\n [`${ATTR}system`]: 'http://oval.mitre.org/XMLSchema/oval-definitions-5',\n 'check-content': wrap(checkContent),\n };\n }\n\n return rule;\n}\n\n/** Build the XCCDF TestResult object. */\nfunction buildTestResultObj(\n hdfData: HdfResults,\n baseline: HdfResults['baselines'][0],\n): Record<string, unknown> {\n const testResult: Record<string, unknown> = {\n [`${ATTR}id`]: 'xccdf_hdf_testresult_1',\n title: wrap('HDF Assessment Results'),\n };\n\n // Timestamps\n if (hdfData.timestamp) {\n const ts =\n typeof hdfData.timestamp === 'string'\n ? hdfData.timestamp\n : (hdfData.timestamp as Date).toISOString();\n testResult[`${ATTR}start-time`] = ts;\n testResult[`${ATTR}end-time`] = ts;\n }\n\n // Component\n if (hdfData.components && hdfData.components.length > 0) {\n const target = hdfData.components[0]!;\n testResult.target = wrap(target.name);\n if (target.ipAddress) {\n testResult['target-address'] = wrap(target.ipAddress);\n }\n } else {\n testResult.target = wrap('unknown');\n }\n\n // Rule results\n const ruleResults: Record<string, unknown>[] = [];\n for (const req of baseline.requirements) {\n const ruleIdRef = sanitizeXccdfId('xccdf_hdf_rule_' + req.id + '_rule');\n\n for (const result of req.results) {\n const rr: Record<string, unknown> = {\n [`${ATTR}idref`]: ruleIdRef,\n result: wrap(hdfStatusToXccdf(result.status)),\n };\n\n const startTime =\n typeof result.startTime === 'string'\n ? result.startTime\n : (result.startTime as Date).toISOString();\n rr[`${ATTR}time`] = startTime;\n\n if (result.message) {\n rr.message = wrap(result.message);\n }\n\n if (result.codeDesc) {\n rr.check = {\n [`${ATTR}system`]:\n 'http://oval.mitre.org/XMLSchema/oval-definitions-5',\n 'check-content': wrap(result.codeDesc),\n };\n }\n\n ruleResults.push(rr);\n }\n }\n\n testResult['rule-result'] = ruleResults;\n\n return testResult;\n}\n","/**\n * Shared helper functions for OSCAL-to-HDF converters.\n *\n * Mirrors the Go helpers in converters/oscal-to-hdf/go/shared.go.\n */\n\nimport type { Property, Part, Characterization, DocumentMetadata, Oscal } from './types.js';\n\nconst controlEnhancementRe = /^([a-z]{2}-\\d+)\\.(\\d+)$/;\nconst objectiveIDRe = /^([a-z]{2}-\\d+(?:\\.\\d+)?)/;\n\n/**\n * Converts an OSCAL control ID to NIST 800-53 notation.\n * \"ac-1\" -> \"AC-1\", \"ac-2.3\" -> \"AC-2 (3)\"\n */\nexport function controlIdToNistTag(id: string): string {\n const m = controlEnhancementRe.exec(id);\n if (m) {\n return `${m[1]!.toUpperCase()} (${m[2]!})`;\n }\n return id.toUpperCase();\n}\n\n/**\n * Converts a list of OSCAL control IDs to NIST tags, deduplicating.\n */\nexport function controlIdsToNistTags(ids: string[]): string[] {\n const tags: string[] = [];\n const seen = new Set<string>();\n for (const id of ids) {\n const tag = controlIdToNistTag(id);\n if (!seen.has(tag)) {\n seen.add(tag);\n tags.push(tag);\n }\n }\n return tags;\n}\n\n/**\n * Extracts the base control ID from a SAR objective ID.\n * \"ac-1.a.1_obj.1\" -> \"ac-1\"\n */\nexport function extractControlIdFromObjectiveId(objectiveId: string): string {\n const m = objectiveIDRe.exec(objectiveId);\n if (m) {\n return m[1]!;\n }\n return objectiveId;\n}\n\n/**\n * Maps OSCAL finding/risk status strings to HDF-compatible status strings.\n * \"satisfied\"/\"closed\" -> \"passed\", \"not-satisfied\"/\"open\" -> \"failed\"\n */\nexport function oscalStatusToHdf(state: string): string | undefined {\n switch (state.toLowerCase().trim()) {\n case 'satisfied':\n case 'closed':\n return 'passed';\n case 'not-satisfied':\n case 'open':\n return 'failed';\n default:\n return undefined;\n }\n}\n\n/**\n * Finds the first property with the given name and returns its value.\n * If ns is non-empty, the property must also match that namespace.\n */\nexport function extractPropValue(\n props: Property[] | undefined,\n name: string,\n ns?: string,\n): string | undefined {\n if (!props) return undefined;\n for (const p of props) {\n if (p.name === name && (!ns || p.ns === ns)) {\n return p.value;\n }\n }\n return undefined;\n}\n\n/**\n * Returns all property values matching the given name.\n */\nexport function extractAllPropValues(\n props: Property[] | undefined,\n name: string,\n ns?: string,\n): string[] {\n if (!props) return [];\n const values: string[] = [];\n for (const p of props) {\n if (p.name === name && (!ns || p.ns === ns)) {\n values.push(p.value);\n }\n }\n return values;\n}\n\n/**\n * Recursively concatenates prose from a Part tree, joining with newlines.\n */\nexport function flattenParts(parts: Part[] | undefined): string {\n if (!parts) return '';\n const pieces: string[] = [];\n flattenPartsRecursive(parts, pieces);\n return pieces.join('\\n').trim();\n}\n\nfunction flattenPartsRecursive(parts: Part[], pieces: string[]): void {\n for (const p of parts) {\n if (p.prose) {\n pieces.push(p.prose);\n }\n if (p.parts && p.parts.length > 0) {\n flattenPartsRecursive(p.parts, pieces);\n }\n }\n}\n\n/**\n * Like flattenParts but only includes top-level parts matching the given name.\n * Nested parts are included regardless of their name.\n */\nexport function flattenPartsByName(\n parts: Part[] | undefined,\n name: string,\n): string {\n if (!parts) return '';\n const pieces: string[] = [];\n for (const p of parts) {\n if (p.name === name) {\n if (p.prose) {\n pieces.push(p.prose);\n }\n if (p.parts && p.parts.length > 0) {\n flattenPartsRecursive(p.parts, pieces);\n }\n }\n }\n return pieces.join('\\n').trim();\n}\n\n/**\n * Extracts impact/severity from risk characterization facets.\n * Returns a normalized 0.0-1.0 impact value. Falls back to defaultImpact.\n */\nexport function extractRiskSeverity(\n characterizations: Characterization[] | undefined,\n defaultImpact: number,\n): number {\n if (!characterizations) return defaultImpact;\n for (const c of characterizations) {\n if (!c.facets) continue;\n for (const f of c.facets) {\n if (f.name === 'impact' || f.name === 'risk' || f.name === 'likelihood') {\n switch (f.value.toLowerCase()) {\n case 'critical':\n return 0.9;\n case 'high':\n return 0.7;\n case 'moderate':\n case 'medium':\n return 0.5;\n case 'low':\n return 0.3;\n case 'info':\n case 'informational':\n case 'none':\n return 0.0;\n }\n }\n }\n }\n return defaultImpact;\n}\n\n/** Holds extracted metadata common to all OSCAL documents. */\nexport interface MetadataInfo {\n title: string;\n version: string;\n oscalVersion: string;\n lastModified: string;\n}\n\n/** Pulls common fields from OSCAL metadata. */\nexport function extractMetadata(m: DocumentMetadata): MetadataInfo {\n return {\n title: m.title,\n version: m.version,\n oscalVersion: m['oscal-version'],\n lastModified: String(m['last-modified']),\n };\n}\n\n/** Matches NIST 800-53 tags with enhancements like \"AC-2 (3)\". */\nconst nistEnhancementReverseRe = /^([A-Z]{2}-\\d+)\\s*\\((\\d+)\\)$/;\n\n/**\n * Converts NIST 800-53 notation back to OSCAL control ID.\n * \"AC-1\" -> \"ac-1\", \"AC-2 (3)\" -> \"ac-2.3\", \"SI-7 (1)\" -> \"si-7.1\"\n */\nexport function nistTagToControlId(tag: string): string {\n tag = tag.trim();\n const m = nistEnhancementReverseRe.exec(tag);\n if (m) {\n return `${m[1]!.toLowerCase()}.${m[2]!}`;\n }\n return tag.toLowerCase();\n}\n\n/**\n * Converts a 0.0-1.0 impact value to an OSCAL severity string.\n * This is the reverse of extractRiskSeverity.\n */\nexport function impactToSeverity(impact: number): string {\n if (impact >= 0.9) return 'critical';\n if (impact >= 0.7) return 'high';\n if (impact >= 0.4) return 'moderate';\n if (impact >= 0.1) return 'low';\n return 'info';\n}\n\n/**\n * Maps an HDF status string to an OSCAL risk status string.\n * \"passed\"/\"notApplicable\" -> \"closed\", everything else -> \"open\".\n */\nexport function hdfStatusToOscalRiskStatus(status: string): string {\n if (status === 'passed' || status === 'notApplicable') {\n return 'closed';\n }\n return 'open';\n}\n\n/** OSCAL specification version used in reverse converter output documents. */\nexport const OSCAL_VERSION = '1.1.2';\n\n/**\n * Parses an OSCAL document from JSON input, validates the document type.\n * Throws if input is empty, invalid JSON, or not the expected type.\n */\nexport function parseOscalDocument<T extends keyof Oscal>(\n input: string,\n expectedKey: T,\n converterName: string,\n): NonNullable<Oscal[T]> {\n if (!input || input.trim().length === 0) {\n throw new Error(`${converterName}: empty input`);\n }\n\n let doc: Oscal;\n try {\n doc = JSON.parse(input) as Oscal;\n } catch {\n throw new Error(`${converterName}: failed to parse JSON`);\n }\n\n const value = doc[expectedKey];\n if (!value) {\n throw new Error(`${converterName}: expected ${String(expectedKey)} document`);\n }\n\n return value as NonNullable<Oscal[T]>;\n}\n\n/**\n * Converts a title to kebab-case, truncated to 80 characters.\n * Shared utility used by multiple converters for deriving names.\n */\nexport function toKebabCase(title: string, fallback: string): string {\n if (!title) return fallback;\n let name = title.toLowerCase();\n name = name.replace(/[^a-z0-9]/g, '-');\n // Collapse consecutive dashes\n while (name.includes('--')) {\n name = name.replace(/--/g, '-');\n }\n name = name.replace(/^-+|-+$/g, '');\n if (name.length > 80) {\n name = name.slice(0, 80);\n }\n return name;\n}\n","/**\n * Converts HDF Results to OSCAL Assessment Results (SAR) format.\n *\n * This is the reverse direction of the oscal-to-hdf SAR converter. It takes HDF\n * Results JSON and produces an OSCAL 1.1.2 assessment-results JSON document.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfResults, EvaluatedBaseline, EvaluatedRequirement, Description, RequirementResult } from '@mitre/hdf-schema';\nimport type {\n SecurityAssessmentResultsSAR,\n DocumentMetadata,\n ImportAssessmentPlan,\n AssessmentResult,\n Finding,\n TargetClass,\n StatusClass,\n Observation,\n IdentifiedRisk,\n Property,\n} from '../../oscal-to-hdf/typescript/types.js';\nimport {\n nistTagToControlId,\n impactToSeverity,\n OSCAL_VERSION,\n} from '../../oscal-to-hdf/typescript/shared.js';\n\n/** Root wrapper for the output JSON. */\ninterface OscalSARDocument {\n 'assessment-results': SecurityAssessmentResultsSAR;\n}\n\n/**\n * Convert HDF Results JSON to OSCAL Assessment Results (SAR) JSON.\n *\n * @param input - HDF Results JSON string\n * @returns OSCAL SAR JSON string\n */\nexport async function convertHdfToOscalSar(input: string): Promise<string> {\n validateInputSize(input, 'hdf-to-oscal-sar');\n\n if (!input || input.trim().length === 0) {\n throw new Error('hdf-to-oscal-sar: empty input');\n }\n\n let hdfResults: HdfResults;\n try {\n hdfResults = parseJSON<HdfResults>(input);\n } catch {\n throw new Error('hdf-to-oscal-sar: failed to parse HDF JSON');\n }\n\n if (!hdfResults || typeof hdfResults !== 'object' || !('baselines' in hdfResults)) {\n throw new Error('hdf-to-oscal-sar: invalid HDF structure: missing baselines field');\n }\n\n const doc = buildOSCALDocument(hdfResults);\n return JSON.stringify(doc, null, 2);\n}\n\n/**\n * Constructs the full OSCAL assessment-results document from HDF results.\n */\nfunction buildOSCALDocument(hdfResults: HdfResults): OscalSARDocument {\n let timestamp = new Date().toISOString();\n if (hdfResults.timestamp) {\n timestamp = typeof hdfResults.timestamp === 'string'\n ? hdfResults.timestamp\n : hdfResults.timestamp.toISOString();\n }\n\n const metadata = {\n title: 'HDF Assessment Results Export',\n 'last-modified': timestamp,\n version: '1.0.0',\n 'oscal-version': OSCAL_VERSION,\n } as unknown as DocumentMetadata;\n\n let importAP: ImportAssessmentPlan;\n if (hdfResults.planRef && hdfResults.planRef !== '') {\n importAP = { href: hdfResults.planRef };\n } else {\n importAP = { href: '#' };\n }\n\n const results: AssessmentResult[] = [];\n for (const baseline of hdfResults.baselines) {\n results.push(baselineToResult(baseline, timestamp));\n }\n\n return {\n 'assessment-results': {\n uuid: crypto.randomUUID(),\n metadata,\n 'import-ap': importAP,\n results,\n },\n };\n}\n\n/**\n * Converts a single EvaluatedBaseline to an OSCAL Result.\n */\nfunction baselineToResult(baseline: EvaluatedBaseline, timestamp: string): AssessmentResult {\n let title = baseline.name;\n if (baseline.title && baseline.title !== '') {\n title = baseline.title;\n }\n\n let description: string | undefined = 'Converted from HDF results';\n if (baseline.description && baseline.description !== '') {\n description = baseline.description;\n }\n\n const findings: Finding[] = [];\n const observations: Observation[] = [];\n const risks: IdentifiedRisk[] = [];\n\n for (const req of baseline.requirements) {\n const { finding, observation, risk } = requirementToFindingSet(req, timestamp);\n findings.push(finding);\n if (observation) {\n observations.push(observation);\n }\n if (risk) {\n risks.push(risk);\n }\n }\n\n const result = {\n uuid: crypto.randomUUID(),\n title,\n description,\n start: timestamp,\n findings,\n observations,\n risks,\n } as unknown as AssessmentResult;\n\n return result;\n}\n\n/**\n * Converts an EvaluatedRequirement into a Finding, optional Observation, and optional Risk.\n */\nfunction requirementToFindingSet(\n req: EvaluatedRequirement,\n timestamp: string,\n): { finding: Finding; observation: Observation | undefined; risk: IdentifiedRisk | undefined } {\n const controlID = nistTagToControlId(req.id);\n const { state, reason } = aggregateStatus(req.results);\n const findingDesc = extractDefaultDescription(req.descriptions);\n\n // Build props from NIST tags\n const props: Property[] = [];\n if (req.tags) {\n const nistRaw = req.tags['nist'];\n if (Array.isArray(nistRaw)) {\n for (const v of nistRaw) {\n if (typeof v === 'string') {\n props.push({ name: 'nist', value: v });\n }\n }\n }\n }\n\n let title = req.id;\n if (req.title && req.title !== '') {\n title = req.title;\n }\n\n const targetStatus: StatusClass = { state } as unknown as StatusClass;\n if (reason) {\n targetStatus.reason = reason;\n }\n\n const target = {\n type: 'objective-id',\n 'target-id': controlID,\n status: targetStatus,\n } as unknown as TargetClass;\n\n const finding = {\n uuid: crypto.randomUUID(),\n title,\n description: findingDesc || '',\n props: props.length > 0 ? props : undefined,\n target,\n } as Finding;\n\n // Build observation from requirement results\n let observation: Observation | undefined;\n if (req.results.length > 0) {\n const obsUUID = crypto.randomUUID();\n const obsDesc = buildObservationDescription(req.results);\n observation = {\n uuid: obsUUID,\n description: obsDesc,\n methods: ['TEST'],\n collected: timestamp,\n } as unknown as Observation;\n finding['related-observations'] = [{ 'observation-uuid': obsUUID }];\n }\n\n // Build risk from impact\n let risk: IdentifiedRisk | undefined;\n if (req.impact > 0) {\n const riskUUID = crypto.randomUUID();\n const severity = impactToSeverity(req.impact);\n risk = {\n uuid: riskUUID,\n title: `Risk for ${req.id}`,\n description: `Impact: ${req.impact.toFixed(1)} (${severity})`,\n statement: `Impact: ${req.impact.toFixed(1)} (${severity})`,\n status: riskStatusFromState(state),\n characterizations: [\n {\n facets: [\n {\n name: 'impact',\n system: 'https://fedramp.gov',\n value: severity,\n },\n ],\n },\n ],\n } as unknown as IdentifiedRisk;\n finding['related-risks'] = [{ 'risk-uuid': riskUUID }];\n }\n\n return { finding, observation, risk };\n}\n\n\n/**\n * Determines the overall finding status from requirement results.\n */\nexport function aggregateStatus(results: RequirementResult[]): { state: string; reason: string } {\n if (results.length === 0) {\n return { state: 'not-satisfied', reason: 'other' };\n }\n\n let hasFailed = false;\n let hasError = false;\n let hasNotReviewed = false;\n let hasNotApplicable = false;\n let allPassed = true;\n\n for (const r of results) {\n switch (r.status) {\n case 'passed':\n break;\n case 'failed':\n hasFailed = true;\n allPassed = false;\n break;\n case 'error':\n hasError = true;\n allPassed = false;\n break;\n case 'notReviewed':\n hasNotReviewed = true;\n allPassed = false;\n break;\n case 'notApplicable':\n hasNotApplicable = true;\n allPassed = false;\n break;\n default:\n allPassed = false;\n break;\n }\n }\n\n if (allPassed) {\n return { state: 'satisfied', reason: '' };\n }\n if (hasFailed || hasError) {\n return { state: 'not-satisfied', reason: '' };\n }\n if (hasNotReviewed) {\n return { state: 'not-satisfied', reason: 'other' };\n }\n if (hasNotApplicable) {\n return { state: 'not-satisfied', reason: 'not-applicable' };\n }\n return { state: 'not-satisfied', reason: '' };\n}\n\n/**\n * Finds the \"default\" labeled description.\n */\nfunction extractDefaultDescription(descriptions: Description[]): string {\n for (const d of descriptions) {\n if (d.label === 'default') {\n return d.data;\n }\n }\n if (descriptions.length > 0) {\n return descriptions[0]!.data;\n }\n return '';\n}\n\n/**\n * Concatenates result code descriptions and messages.\n */\nfunction buildObservationDescription(results: RequirementResult[]): string {\n const parts: string[] = [];\n for (const r of results) {\n let desc = `[${r.status}] ${r.codeDesc}`;\n if (r.message && r.message !== '') {\n desc += ': ' + r.message;\n }\n parts.push(desc);\n }\n if (parts.length === 0) {\n return 'No observations recorded';\n }\n return parts.join('\\n');\n}\n\n\n/**\n * Maps OSCAL finding state to risk status.\n */\nfunction riskStatusFromState(state: string): string {\n if (state === 'satisfied') {\n return 'closed';\n }\n return 'open';\n}\n","/**\n * Converts HDF Amendments to OSCAL Plan of Action and Milestones (POA&M) format.\n *\n * This is the reverse direction of the oscal-poam to HDF converter.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfAmendments, StandaloneOverride } from '@mitre/hdf-schema';\nimport type {\n Oscal,\n DocumentMetadata,\n ImportSystemSecurityPlan,\n PlanOfActionAndMilestonesPOAM,\n POAMItem,\n IdentifiedRisk,\n Property,\n RiskResponse,\n RiskLog,\n} from '../../oscal-to-hdf/typescript/types.js';\nimport {\n nistTagToControlId,\n hdfStatusToOscalRiskStatus,\n OSCAL_VERSION,\n} from '../../oscal-to-hdf/typescript/shared.js';\n\n/**\n * Convert HDF Amendments JSON to OSCAL POA&M JSON.\n *\n * @param input - HDF Amendments JSON string\n * @returns OSCAL POA&M JSON string\n */\nexport async function convertHdfToOscalPoam(input: string): Promise<string> {\n validateInputSize(input, 'hdf-to-oscal-poam');\n\n if (!input || input.trim().length === 0) {\n throw new Error('hdf-to-oscal-poam: empty input');\n }\n\n let amendments: HdfAmendments;\n try {\n amendments = parseJSON<HdfAmendments>(input);\n } catch {\n throw new Error('hdf-to-oscal-poam: failed to parse JSON');\n }\n\n const poam = amendmentsToPOAM(amendments);\n\n const doc: Oscal = {\n 'plan-of-action-and-milestones': poam,\n };\n\n return JSON.stringify(doc, null, 2);\n}\n\n/**\n * Converts parsed HdfAmendments to an OSCAL PlanOfActionAndMilestones.\n */\nfunction amendmentsToPOAM(amendments: HdfAmendments): PlanOfActionAndMilestonesPOAM {\n const now = new Date().toISOString();\n\n const metadata = {\n title: amendments.name,\n 'last-modified': now,\n version: '1.0.0',\n 'oscal-version': OSCAL_VERSION,\n } as unknown as DocumentMetadata;\n\n // Add responsible parties from appliedBy\n if (amendments.appliedBy) {\n const partyUUID = crypto.randomUUID();\n metadata.parties = [\n {\n uuid: partyUUID,\n type: 'person' as unknown,\n name: amendments.appliedBy.identifier,\n },\n ] as unknown as DocumentMetadata['parties'];\n metadata['responsible-parties'] = [\n {\n 'role-id': 'prepared-by',\n 'party-uuids': [partyUUID],\n },\n ];\n metadata.roles = [\n {\n id: 'prepared-by',\n title: 'Prepared By',\n },\n ];\n }\n\n // Build import-ssp\n let importSSP: ImportSystemSecurityPlan;\n if (amendments.systemRef && amendments.systemRef !== '') {\n importSSP = { href: amendments.systemRef } as ImportSystemSecurityPlan;\n } else {\n importSSP = { href: '#' } as ImportSystemSecurityPlan;\n }\n\n // Convert overrides to poam-items and collect risks\n const poamItems: POAMItem[] = [];\n const risks: IdentifiedRisk[] = [];\n\n for (const override of amendments.overrides) {\n const { item, itemRisks } = overrideToPOAMItem(override);\n poamItems.push(item);\n risks.push(...itemRisks);\n }\n\n return {\n uuid: crypto.randomUUID(),\n metadata,\n 'import-ssp': importSSP,\n risks,\n 'poam-items': poamItems,\n };\n}\n\n/**\n * Converts a single StandaloneOverride to a POAMItem and its associated Risk(s).\n */\nfunction overrideToPOAMItem(override: StandaloneOverride): { item: POAMItem; itemRisks: IdentifiedRisk[] } {\n const riskUUID = crypto.randomUUID();\n\n // Map HDF status to OSCAL risk status\n const riskStatus = hdfStatusToOscalRiskStatus(String(override.status));\n\n // Convert requirement ID from NIST notation to OSCAL control ID\n const controlID = nistTagToControlId(override.requirementId);\n\n // Build risk props with impacted-control-id\n const riskProps: Property[] = [\n {\n name: 'impacted-control-id',\n value: controlID,\n },\n ];\n\n // Build remediations from milestones\n const remediations: RiskResponse[] = [];\n if (override.milestones) {\n for (const ms of override.milestones) {\n remediations.push({\n uuid: crypto.randomUUID(),\n lifecycle: 'planned',\n title: ms.description,\n description: ms.description,\n });\n }\n }\n\n // Build risk log entry for expiration tracking\n let riskLog: RiskLog | undefined;\n const expiresAt = override.expiresAt;\n if (expiresAt) {\n const expiresDate = typeof expiresAt === 'string' ? new Date(expiresAt) : expiresAt;\n if (!isNaN(expiresDate.getTime()) && expiresDate.getTime() > 0) {\n riskLog = {\n entries: [\n {\n uuid: crypto.randomUUID(),\n title: 'Scheduled review',\n description: 'Amendment expiration date',\n start: expiresDate.toISOString(),\n 'status-change': riskStatus,\n },\n ],\n } as unknown as RiskLog;\n }\n }\n\n const risk = {\n uuid: riskUUID,\n title: override.requirementId,\n description: override.reason,\n statement: override.reason,\n status: riskStatus,\n props: riskProps,\n remediations: remediations.length > 0 ? remediations : undefined,\n 'risk-log': riskLog,\n } as unknown as IdentifiedRisk;\n\n const item: POAMItem = {\n uuid: crypto.randomUUID(),\n title: override.requirementId,\n description: override.reason,\n 'related-risks': [{ 'risk-uuid': riskUUID }],\n };\n\n return { item, itemRisks: [risk] };\n}\n\n","import { parseJSON } from '@mitre/hdf-utilities';\nimport type {\n EvaluatedBaseline,\n EvaluatedRequirement,\n Checksum,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createDescription,\n createResult,\n} from '@mitre/hdf-schema';\nimport {\n nistToCci,\n DEFAULT_COMPONENT_MANAGEMENT_NIST_TAGS,\n} from '@mitre/hdf-mappings';\nimport {\n inputChecksum,\n buildNistCciTags,\n validateInputSize,\n buildHdfResults,\n} from '../../../shared/typescript/converterutil.js';\n\n// ---- Input types ----\n\ninterface IonChannelAnalysis {\n id: string;\n analysis_id: string;\n team_id: string;\n project_id: string;\n name: string;\n text: string;\n type: string;\n source: string;\n branch: string;\n description: string;\n risk: string;\n summary: string;\n passed: boolean;\n ruleset_id: string;\n ruleset_name: string;\n status: string;\n created_at: string;\n updated_at: string;\n duration: number;\n trigger_hash: string;\n trigger_text: string;\n trigger_author: string;\n trigger: string;\n public: boolean;\n scan_summaries: ScanSummary[];\n}\n\ninterface ScanSummary {\n id: string;\n team_id: string;\n project_id: string;\n analysis_id: string;\n summary: string;\n results: ScanResults;\n created_at: string;\n updated_at: string;\n duration: number;\n name: string;\n description: string;\n}\n\ninterface ScanResults {\n type: string;\n data: ScanData;\n}\n\ninterface ScanData {\n dependencies?: Dependency[];\n}\n\ninterface Dependency {\n latest_version: string;\n org: string;\n name: string;\n type: string;\n package: string;\n version: string;\n scope: string;\n requirement: string;\n file: string;\n outdated_version: OutdatedVersion;\n dependencies: Dependency[];\n}\n\ninterface OutdatedVersion {\n major_behind: number;\n minor_behind: number;\n patch_behind: number;\n}\n\ninterface ContextualizedDependency extends Dependency {\n parentDependencies: string[];\n}\n\n// ---- Helpers ----\n\nfunction extractAllDependencies(dep: Dependency): ContextualizedDependency[] {\n const result: ContextualizedDependency[] = [\n { ...dep, parentDependencies: [] },\n ];\n if (Array.isArray(dep.dependencies)) {\n for (const sub of dep.dependencies) {\n result.push(...extractAllDependencies(sub));\n }\n }\n return result;\n}\n\nfunction buildDependencyGraph(deps: Dependency[]): ContextualizedDependency[] {\n const graph = new Map<string, ContextualizedDependency>();\n\n // Flatten all dependencies\n for (const topLevel of deps) {\n for (const flat of extractAllDependencies(topLevel)) {\n const key = `${flat.org}/${flat.name}`;\n if (!graph.has(key)) {\n graph.set(key, flat);\n }\n }\n }\n\n // Associate parent relationships\n for (const dep of graph.values()) {\n if (Array.isArray(dep.dependencies)) {\n for (const sub of dep.dependencies) {\n const subKey = `${sub.org}/${sub.name}`;\n const child = graph.get(subKey);\n if (child) {\n const parentKey = `${dep.org}/${dep.name}`;\n child.parentDependencies.push(parentKey);\n }\n }\n }\n }\n\n return Array.from(graph.values());\n}\n\nfunction buildTitle(dep: Dependency): string {\n // Python editable install special case\n if (dep.type === 'pypi' && dep.package === 'egg' && dep.name === '-e') {\n return `Python requirements file ${dep.file}`;\n }\n\n let title = `Dependency ${dep.name} `;\n if (dep.org && dep.org.toLowerCase() !== 'n/a') {\n title += `from ${dep.org} `;\n }\n if (dep.version && dep.version.toLowerCase() !== 'n/a') {\n title += `@ ${dep.version} `;\n }\n if (dep.requirement && dep.requirement.toLowerCase() !== 'n/a') {\n title += `(Required ${dep.requirement}) `;\n }\n return title.trim();\n}\n\nfunction buildTags(\n dep: ContextualizedDependency,\n): Record<string, unknown> {\n const nist = DEFAULT_COMPONENT_MANAGEMENT_NIST_TAGS;\n const cciTags = nistToCci(nist);\n\n const extras: Record<string, unknown> = {\n org: dep.org,\n name: dep.name,\n type: dep.type,\n version: dep.version,\n latest_version: dep.latest_version,\n scope: dep.scope,\n requirement: dep.requirement,\n file: dep.file,\n };\n\n if (Array.isArray(dep.dependencies) && dep.dependencies.length > 0) {\n extras.dependencies = dep.dependencies.map((sub) => sub.name);\n }\n\n if (dep.parentDependencies.length > 0) {\n extras.parentDependencies = dep.parentDependencies;\n }\n\n return buildNistCciTags(nist, cciTags, extras);\n}\n\n// ---- Main converter ----\n\nexport async function convertIonchannelToHdf(input: string): Promise<string> {\n if (!input?.trim()) {\n throw new Error('Empty input');\n }\n\n validateInputSize(input, 'ionchannel');\n\n const analysis = parseJSON<IonChannelAnalysis>(input);\n\n if (!Array.isArray(analysis.scan_summaries)) {\n throw new Error(\n `Ion Channel scan_summaries invalid summary data (expecting array, got ${typeof analysis.scan_summaries})`,\n );\n }\n\n // Extract dependencies from dependency scan\n let allDeps: Dependency[] = [];\n for (const scan of analysis.scan_summaries) {\n if (scan.name === 'dependency') {\n allDeps = scan.results?.data?.dependencies ?? [];\n break;\n }\n }\n\n // Flatten and contextualize\n const contextDeps = buildDependencyGraph(allDeps);\n\n // Build requirements\n const requirements: EvaluatedRequirement[] = contextDeps.map((dep) => {\n const depId = `dependency-${dep.org}/${dep.name}`;\n const title = buildTitle(dep);\n const tags = buildTags(dep);\n const code = JSON.stringify(\n {\n latest_version: dep.latest_version,\n org: dep.org,\n name: dep.name,\n type: dep.type,\n package: dep.package,\n version: dep.version,\n scope: dep.scope,\n requirement: dep.requirement,\n file: dep.file,\n outdated_version: dep.outdated_version,\n dependencies: dep.dependencies,\n } as Dependency,\n null,\n 2,\n );\n\n const descriptions = [\n createDescription('default', `Dependency ${dep.org}/${dep.name}`),\n ];\n const results = [\n createResult(ResultStatus.NotReviewed, 'Dependency inventory item', {\n codeDesc: 'Dependency inventory item',\n startTime: new Date('0001-01-01T00:00:00Z'),\n }),\n ];\n\n const req = createRequirement(depId, title, descriptions, 0.0, results, {\n tags,\n }) as EvaluatedRequirement;\n req.code = code;\n return req;\n });\n\n const resultsChecksum: Checksum = await inputChecksum(input);\n\n const baseline = createMinimalBaseline(\n 'Ion Channel SBOM Analysis',\n requirements,\n {\n title: `Ion Channel Analysis of ${analysis.source}`,\n summary: analysis.summary,\n integrity: { algorithm: resultsChecksum.algorithm, checksum: resultsChecksum.value },\n status: 'loaded',\n },\n ) as EvaluatedBaseline;\n\n return buildHdfResults({\n generatorName: 'ionchannel-to-hdf',\n converterVersion: '1.0.0',\n toolName: 'Ion Channel',\n toolFormat: 'JSON',\n baselines: [baseline],\n timestamp: new Date(),\n });\n}\n","/**\n * OSCAL document type detection.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/detect.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport type { Oscal } from './types.js';\n\n/** The 7 valid OSCAL document type strings. */\nexport type OscalDocumentType =\n | 'catalog'\n | 'profile'\n | 'component-definition'\n | 'system-security-plan'\n | 'assessment-plan'\n | 'assessment-results'\n | 'plan-of-action-and-milestones';\n\n/**\n * Parses the input JSON just enough to determine which OSCAL document type\n * it contains. Returns one of the 7 OSCAL root key strings.\n *\n * @throws Error if the input is not valid OSCAL\n */\nexport function detectOscalDocumentType(input: string): OscalDocumentType {\n const doc = parseJSON<Oscal>(input);\n\n if (doc.catalog) return 'catalog';\n if (doc.profile) return 'profile';\n if (doc['component-definition']) return 'component-definition';\n if (doc['system-security-plan']) return 'system-security-plan';\n if (doc['assessment-plan']) return 'assessment-plan';\n if (doc['assessment-results']) return 'assessment-results';\n if (doc['plan-of-action-and-milestones']) return 'plan-of-action-and-milestones';\n\n throw new Error(\n 'unrecognized OSCAL document: expected one of catalog, profile, ' +\n 'component-definition, system-security-plan, assessment-plan, ' +\n 'assessment-results, plan-of-action-and-milestones as root key',\n );\n}\n","/**\n * OSCAL Catalog to HDF Baseline converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_catalog.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfBaseline, BaselineRequirement } from '@mitre/hdf-schema';\nimport type { Description, RequirementGroup } from '@mitre/hdf-schema';\nimport type { Oscal, Catalog, Control } from './types.js';\nimport {\n controlIdToNistTag,\n extractPropValue,\n flattenPartsByName,\n extractMetadata,\n toKebabCase,\n} from './shared.js';\n\n/**\n * Converts an OSCAL Catalog document to HDF Baseline JSON.\n *\n * @param input - Raw JSON string containing an OSCAL catalog\n * @returns HDF Baseline JSON string\n */\nexport async function convertOscalCatalogToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-catalog');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc.catalog) {\n throw new Error(\n \"oscal-catalog: input is not a catalog document (root key is not 'catalog')\",\n );\n }\n\n const baseline = await catalogToBaseline(doc.catalog, input);\n return JSON.stringify(baseline, null, 2);\n}\n\n/**\n * Shared logic: converts a parsed Catalog to HDFBaseline.\n * Also used by the profile converter after resolving.\n */\nexport async function catalogToBaseline(\n catalog: Catalog,\n rawInput: string,\n): Promise<HdfBaseline> {\n const integrity = await inputIntegrity(rawInput);\n const meta = extractMetadata(catalog.metadata);\n\n const requirements: BaselineRequirement[] = [];\n const groups: RequirementGroup[] = [];\n\n for (const group of catalog.groups ?? []) {\n const reqIDs: string[] = [];\n\n for (const ctrl of group.controls ?? []) {\n const req = controlToBaselineRequirement(ctrl);\n requirements.push(req);\n reqIDs.push(req.id);\n\n // Include control enhancements\n for (const enh of ctrl.controls ?? []) {\n const enhReq = controlToBaselineRequirement(enh);\n requirements.push(enhReq);\n reqIDs.push(enhReq.id);\n }\n }\n\n if (reqIDs.length > 0) {\n groups.push({\n id: group.id ?? '',\n title: group.title,\n requirements: reqIDs,\n });\n }\n }\n\n // Top-level controls (outside groups)\n for (const ctrl of catalog.controls ?? []) {\n const req = controlToBaselineRequirement(ctrl);\n requirements.push(req);\n\n for (const enh of ctrl.controls ?? []) {\n const enhReq = controlToBaselineRequirement(enh);\n requirements.push(enhReq);\n }\n }\n\n const baseline: HdfBaseline = {\n name: catalogBaselineName(catalog),\n title: meta.title,\n version: meta.version,\n status: 'loaded',\n integrity,\n requirements,\n groups,\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n };\n\n return baseline;\n}\n\n/** Converts a single OSCAL Control to an HDF BaselineRequirement. */\nfunction controlToBaselineRequirement(ctrl: Control): BaselineRequirement {\n const nistTag = controlIdToNistTag(ctrl.id);\n const descriptions = buildCatalogDescriptions(ctrl);\n const tags = buildCatalogTags(ctrl);\n\n return {\n id: nistTag,\n title: ctrl.title,\n impact: 0.5, // default for catalog controls\n descriptions,\n tags,\n };\n}\n\n/** Creates HDF Description entries from control parts. */\nfunction buildCatalogDescriptions(ctrl: Control): Description[] {\n const descriptions: Description[] = [];\n\n // Statement -> default description\n const statement = flattenPartsByName(ctrl.parts, 'statement');\n descriptions.push({\n label: 'default',\n data: statement || '',\n });\n\n // Guidance -> rationale\n const guidance = flattenPartsByName(ctrl.parts, 'guidance');\n if (guidance) {\n descriptions.push({ label: 'rationale', data: guidance });\n }\n\n // Assessment objective -> check\n const check = flattenPartsByName(ctrl.parts, 'assessment-objective');\n if (check) {\n descriptions.push({ label: 'check', data: check });\n }\n\n return descriptions;\n}\n\n/** Builds the tags map for an OSCAL catalog control. */\nfunction buildCatalogTags(ctrl: Control): Record<string, unknown> {\n const tags: Record<string, unknown> = {};\n\n const nistTag = controlIdToNistTag(ctrl.id);\n tags['nist'] = [nistTag];\n\n const label = extractPropValue(ctrl.props, 'label');\n if (label !== undefined) {\n tags['label'] = label;\n }\n\n const sortId = extractPropValue(ctrl.props, 'sort-id');\n if (sortId !== undefined) {\n tags['sort-id'] = sortId;\n }\n\n return tags;\n}\n\n/** Derives a baseline name from catalog metadata. */\nfunction catalogBaselineName(catalog: Catalog): string {\n return toKebabCase(catalog.metadata.title, 'oscal-catalog');\n}\n","/**\n * OSCAL Profile to HDF Baseline converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_profile.go.\n *\n * This implements the \"simple resolver\" -- it handles:\n * - A single catalog import\n * - include-controls with with-ids filtering\n * - set-parameters from modify section\n * - merge as-is (preserve catalog structure)\n *\n * It does NOT handle:\n * - Multiple imports\n * - Nested profile imports\n * - alter directives\n * - Complex merge strategies\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n Oscal,\n Catalog,\n Control,\n CatalogControlGroup,\n ImportResource,\n Part,\n ParameterSetting,\n} from './types.js';\nimport { catalogToBaseline } from './converter-catalog.js';\n\n/**\n * Converts an OSCAL Profile against a provided catalog to HDF Baseline JSON.\n *\n * @param profileInput - Raw JSON string containing an OSCAL profile\n * @param catalogInput - Raw JSON string containing an OSCAL catalog\n * @returns HDF Baseline JSON string\n */\nexport async function convertOscalProfileToHdf(\n profileInput: string,\n catalogInput: string,\n): Promise<string> {\n validateInputSize(profileInput, 'oscal-profile');\n\n if (!profileInput || profileInput.trim().length === 0) {\n throw new Error('empty profile input');\n }\n if (!catalogInput || catalogInput.trim().length === 0) {\n throw new Error('empty catalog input');\n }\n\n // Parse profile\n const profileDoc = parseJSON<Oscal>(profileInput);\n if (!profileDoc.profile) {\n throw new Error(\n \"oscal-profile: input is not a profile document (root key is not 'profile')\",\n );\n }\n const profile = profileDoc.profile;\n\n // Parse catalog\n const catalogDoc = parseJSON<Oscal>(catalogInput);\n if (!catalogDoc.catalog) {\n throw new Error(\n \"oscal-profile: catalog input is not a catalog document (root key is not 'catalog')\",\n );\n }\n const catalog = catalogDoc.catalog;\n\n // Validate: single import only\n if (!profile.imports || profile.imports.length === 0) {\n throw new Error('oscal-profile: profile has no imports');\n }\n if (profile.imports.length > 1) {\n throw new Error(\n `oscal-profile: profile has ${profile.imports.length} imports -- this converter only supports single-catalog imports. Use NIST's oscal-cli to resolve complex profiles, or use a pre-resolved catalog`,\n );\n }\n\n // Validate: no alter directives\n if (profile.modify?.alters && profile.modify.alters.length > 0) {\n throw new Error(\n `oscal-profile: profile contains ${profile.modify.alters.length} alter directives -- this converter only supports parameter overrides. Use NIST's oscal-cli to resolve profiles with alter directives, or use a pre-resolved catalog`,\n );\n }\n\n // Collect included/excluded control IDs\n const imp = profile.imports[0]!;\n const includedIDs = collectIncludedIDs(imp);\n const excludedIDs = collectExcludedIDs(imp);\n\n // Filter catalog\n const resolvedCatalog = filterCatalog(catalog, includedIDs, excludedIDs);\n\n // Apply parameter overrides\n if (profile.modify?.['set-parameters']) {\n applyParameterOverrides(resolvedCatalog, profile.modify['set-parameters']);\n }\n\n // Override metadata from profile\n resolvedCatalog.metadata = profile.metadata;\n resolvedCatalog.uuid = profile.uuid;\n\n const baseline = await catalogToBaseline(resolvedCatalog, profileInput);\n\n // Override the integrity to be based on the profile input\n baseline.integrity = await inputIntegrity(profileInput);\n\n return JSON.stringify(baseline, null, 2);\n}\n\n/** Extracts all control IDs from an import's include-controls. Returns null if include all. */\nfunction collectIncludedIDs(imp: ImportResource): Set<string> | null {\n const includeControls = imp['include-controls'];\n if (!includeControls || includeControls.length === 0) {\n return null; // include all\n }\n\n const ids = new Set<string>();\n for (const ic of includeControls) {\n for (const id of ic['with-ids'] ?? []) {\n ids.add(id);\n }\n }\n return ids;\n}\n\n/** Extracts all control IDs from an import's exclude-controls. */\nfunction collectExcludedIDs(imp: ImportResource): Set<string> | null {\n const excludeControls = imp['exclude-controls'];\n if (!excludeControls || excludeControls.length === 0) {\n return null;\n }\n\n const ids = new Set<string>();\n for (const ec of excludeControls) {\n for (const id of ec['with-ids'] ?? []) {\n ids.add(id);\n }\n }\n return ids;\n}\n\n/** Creates a new catalog containing only the controls matching filters. */\nfunction filterCatalog(\n catalog: Catalog,\n includedIDs: Set<string> | null,\n excludedIDs: Set<string> | null,\n): Catalog {\n const includeAll = includedIDs === null;\n\n const result: Catalog = {\n uuid: catalog.uuid,\n metadata: catalog.metadata,\n 'back-matter': catalog['back-matter'],\n groups: [],\n controls: [],\n };\n\n for (const group of catalog.groups ?? []) {\n const filtered = filterGroupControls(group, includedIDs, excludedIDs, includeAll);\n if (filtered.controls && filtered.controls.length > 0) {\n result.groups!.push(filtered);\n }\n }\n\n for (const ctrl of catalog.controls ?? []) {\n if (shouldIncludeControl(ctrl.id, includedIDs, excludedIDs, includeAll)) {\n const filteredCtrl = filterControlEnhancements(ctrl, includedIDs, excludedIDs, includeAll);\n result.controls!.push(filteredCtrl);\n }\n }\n\n return result;\n}\n\nfunction filterGroupControls(\n group: CatalogControlGroup,\n includedIDs: Set<string> | null,\n excludedIDs: Set<string> | null,\n includeAll: boolean,\n): CatalogControlGroup {\n const filtered: CatalogControlGroup = {\n id: group.id,\n class: group.class,\n title: group.title,\n props: group.props,\n parts: group.parts,\n controls: [],\n };\n\n for (const ctrl of group.controls ?? []) {\n if (shouldIncludeControl(ctrl.id, includedIDs, excludedIDs, includeAll)) {\n const filteredCtrl = filterControlEnhancements(ctrl, includedIDs, excludedIDs, includeAll);\n filtered.controls!.push(filteredCtrl);\n }\n }\n\n return filtered;\n}\n\nfunction filterControlEnhancements(\n ctrl: Control,\n includedIDs: Set<string> | null,\n excludedIDs: Set<string> | null,\n includeAll: boolean,\n): Control {\n const result: Control = {\n id: ctrl.id,\n class: ctrl.class,\n title: ctrl.title,\n params: ctrl.params,\n props: ctrl.props,\n links: ctrl.links,\n parts: ctrl.parts,\n controls: [],\n };\n\n for (const enh of ctrl.controls ?? []) {\n if (shouldIncludeControl(enh.id, includedIDs, excludedIDs, includeAll)) {\n result.controls!.push(enh);\n }\n }\n\n return result;\n}\n\nfunction shouldIncludeControl(\n id: string,\n includedIDs: Set<string> | null,\n excludedIDs: Set<string> | null,\n includeAll: boolean,\n): boolean {\n if (excludedIDs !== null && excludedIDs.has(id)) {\n return false;\n }\n if (includeAll) {\n return true;\n }\n return includedIDs !== null && includedIDs.has(id);\n}\n\n/** Applies set-parameters from the profile's modify section to the resolved catalog. */\nfunction applyParameterOverrides(\n catalog: Catalog,\n setParams: ParameterSetting[],\n): void {\n if (setParams.length === 0) return;\n\n // Build param-id -> values lookup\n const overrides = new Map<string, string[]>();\n for (const sp of setParams) {\n if (sp['param-id']) {\n overrides.set(sp['param-id'], sp.values ?? []);\n }\n }\n\n // Apply to all controls in groups\n for (const group of catalog.groups ?? []) {\n for (const ctrl of group.controls ?? []) {\n applyParamOverridesToControl(ctrl, overrides);\n for (const enh of ctrl.controls ?? []) {\n applyParamOverridesToControl(enh, overrides);\n }\n }\n }\n\n // Apply to top-level controls\n for (const ctrl of catalog.controls ?? []) {\n applyParamOverridesToControl(ctrl, overrides);\n for (const enh of ctrl.controls ?? []) {\n applyParamOverridesToControl(enh, overrides);\n }\n }\n}\n\nfunction applyParamOverridesToControl(\n ctrl: Control,\n overrides: Map<string, string[]>,\n): void {\n if (ctrl.params) {\n for (const param of ctrl.params) {\n if (!param.id) continue;\n const values = overrides.get(param.id);\n if (values) {\n param.label = values.join(', ');\n }\n }\n }\n\n // Replace parameter insertions in prose\n if (ctrl.parts) {\n for (const part of ctrl.parts) {\n replaceParamInsertions(part, overrides);\n }\n }\n}\n\nfunction replaceParamInsertions(part: Part, overrides: Map<string, string[]>): void {\n if (part.prose) {\n part.prose = substituteParams(part.prose, overrides);\n }\n if (part.parts) {\n for (const child of part.parts) {\n replaceParamInsertions(child, overrides);\n }\n }\n}\n\n/** Replaces OSCAL parameter insertion patterns: {{ insert: param, <param-id> }} */\nfunction substituteParams(text: string, overrides: Map<string, string[]>): string {\n let result = text;\n for (const [paramId, values] of overrides) {\n const placeholder = `{{ insert: param, ${paramId} }}`;\n const replacement = values.join(', ');\n result = result.split(placeholder).join(replacement);\n }\n return result;\n}\n","/**\n * OSCAL Component Definition to HDF Baseline converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_component.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfBaseline, BaselineRequirement } from '@mitre/hdf-schema';\nimport type { Description } from '@mitre/hdf-schema';\nimport type { Oscal, ImplementedRequirementElement, ComponentDefinitionComponent, ComponentDefinition } from './types.js';\nimport { controlIdToNistTag, extractMetadata, toKebabCase } from './shared.js';\n\n/**\n * Converts an OSCAL Component Definition document to HDF Baseline JSON.\n *\n * @param input - Raw JSON string containing an OSCAL component-definition\n * @returns HDF Baseline JSON string\n */\nexport async function convertOscalComponentToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-component-definition');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc['component-definition']) {\n throw new Error(\n \"oscal-component-definition: input is not a component-definition document (root key is not 'component-definition')\",\n );\n }\n\n const compDef = doc['component-definition'];\n\n if (!compDef.components || compDef.components.length === 0) {\n throw new Error('oscal-component-definition: document contains no components');\n }\n\n const integrity = await inputIntegrity(input);\n const meta = extractMetadata(compDef.metadata);\n\n // Use the first component to build the baseline\n const comp = compDef.components[0]!;\n\n const requirements: BaselineRequirement[] = [];\n for (const ci of comp['control-implementations'] ?? []) {\n for (const ir of ci['implemented-requirements'] ?? []) {\n requirements.push(implementedRequirementToBaselineRequirement(ir));\n }\n }\n\n const baseline: HdfBaseline = {\n name: componentBaselineName(comp, compDef),\n title: meta.title,\n version: meta.version,\n status: 'loaded',\n integrity,\n requirements,\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n };\n\n return JSON.stringify(baseline, null, 2);\n}\n\n/** Converts a single ImplementedRequirement to a BaselineRequirement. */\nfunction implementedRequirementToBaselineRequirement(\n ir: ImplementedRequirementElement,\n): BaselineRequirement {\n const nistTag = controlIdToNistTag(ir['control-id']);\n\n const descriptions: Description[] = [];\n\n // Primary description\n descriptions.push({\n label: 'default',\n data: ir.description ?? '',\n });\n\n // Add statement prose as additional descriptions\n for (const stmt of ir.statements ?? []) {\n if (stmt.description) {\n descriptions.push({\n label: stmt['statement-id'],\n data: stmt.description,\n });\n }\n if (stmt.remarks) {\n descriptions.push({\n label: stmt['statement-id'] + '-remarks',\n data: stmt.remarks,\n });\n }\n }\n\n const tags: Record<string, unknown> = {\n nist: [nistTag],\n };\n\n return {\n id: nistTag,\n title: nistTag,\n impact: 0.5,\n descriptions,\n tags,\n };\n}\n\n/** Derives a baseline name from the component or component-definition metadata. */\nfunction componentBaselineName(\n comp: ComponentDefinitionComponent,\n compDef: ComponentDefinition,\n): string {\n const name = comp.title || compDef.metadata.title;\n return toKebabCase(name, 'oscal-component-definition');\n}\n","/**\n * OSCAL System Security Plan (SSP) to HDF System converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_ssp.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type { HdfSystem } from '@mitre/hdf-schema';\nimport {\n AuthorizationStatus,\n CategorizationLevel,\n BoundaryDescription,\n} from '@mitre/hdf-schema';\n// Import Component from system types to avoid type incompatibility with results Component\nimport type { Component as HdfComponent } from '@mitre/hdf-schema/hdf-system';\nimport type {\n Oscal,\n SystemSecurityPlanSSP,\n SecurityImpactLevel,\n AssessmentAssetsComponent,\n ControlImplementationClass,\n} from './types.js';\nimport { controlIdToNistTag, extractMetadata } from './shared.js';\n\n/**\n * Converts an OSCAL System Security Plan document to HDF System JSON.\n *\n * @param input - Raw JSON string containing an OSCAL SSP\n * @returns HDF System JSON string\n */\nexport async function convertOscalSspToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-ssp');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc['system-security-plan']) {\n throw new Error(\n \"oscal-ssp: input is not a system-security-plan document (root key is not 'system-security-plan')\",\n );\n }\n\n const ssp = doc['system-security-plan'];\n const integrity = await inputIntegrity(input);\n\n const system: HdfSystem = {\n name: sspSystemName(ssp),\n integrity,\n components: [],\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n };\n\n // Map system characteristics\n const sc = ssp['system-characteristics'];\n if (sc) {\n if (sc.description) {\n let desc = sc.description;\n if (sc['authorization-boundary']?.description) {\n desc += '\\n\\nAuthorization Boundary: ' + sc['authorization-boundary'].description;\n }\n system.description = desc;\n }\n\n // Map categorization level from security impact level\n const sil = sc['security-impact-level'];\n if (sil) {\n system.categorizationLevel = sspCategorizationLevel(sil) ?? undefined;\n } else if (sc['security-sensitivity-level']) {\n system.categorizationLevel = mapSensitivityToCategorizationLevel(sc['security-sensitivity-level']) ?? undefined;\n }\n\n // Map authorization status from system status\n if (sc.status) {\n system.authorizationStatus = sspAuthorizationStatus(sc.status.state) ?? undefined;\n }\n\n // Map boundary description\n if (sc['authorization-boundary']?.description) {\n system.boundaryDescription = sc['authorization-boundary'].description;\n }\n\n // Map system identifier\n const systemIds = sc['system-ids'];\n if (systemIds && systemIds.length > 0) {\n system.identifier = systemIds[0]!.id;\n if (systemIds[0]!['identifier-type']) {\n system.identifierScheme = systemIds[0]!['identifier-type'];\n }\n }\n }\n\n // Map version from metadata\n const meta = extractMetadata(ssp.metadata);\n if (meta.version) {\n system.version = meta.version;\n }\n\n // Build component-UUID -> control-ID mapping\n const componentControls = buildComponentControlMap(ssp['control-implementation']);\n\n // Map system-implementation components to HDF Components\n const si = ssp['system-implementation'];\n if (si?.components) {\n for (const comp of si.components) {\n system.components.push(sspComponentToHDFComponent(comp, componentControls));\n }\n }\n\n return JSON.stringify(system, null, 2);\n}\n\nfunction sspSystemName(ssp: SystemSecurityPlanSSP): string {\n const sc = ssp['system-characteristics'];\n if (sc?.['system-name']) {\n return sc['system-name'];\n }\n if (ssp.metadata.title) {\n return ssp.metadata.title;\n }\n return 'oscal-ssp';\n}\n\nfunction sspCategorizationLevel(\n sil: SecurityImpactLevel,\n): CategorizationLevel | null {\n const levels = [\n sil['security-objective-confidentiality'] ?? '',\n sil['security-objective-integrity'] ?? '',\n sil['security-objective-availability'] ?? '',\n ];\n\n let highest = '';\n for (const l of levels) {\n const normalized = normalizeFIPSLevel(l);\n if (fipsLevelRank(normalized) > fipsLevelRank(highest)) {\n highest = normalized;\n }\n }\n\n if (!highest) return null;\n\n switch (highest) {\n case 'high':\n return CategorizationLevel.High;\n case 'moderate':\n return CategorizationLevel.Moderate;\n case 'low':\n return CategorizationLevel.Low;\n default:\n return null;\n }\n}\n\nfunction normalizeFIPSLevel(level: string): string {\n let lower = level.toLowerCase();\n lower = lower.replace(/^fips-199-/, '');\n switch (lower) {\n case 'high':\n return 'high';\n case 'moderate':\n case 'medium':\n return 'moderate';\n case 'low':\n return 'low';\n default:\n return '';\n }\n}\n\nfunction fipsLevelRank(level: string): number {\n switch (level) {\n case 'high':\n return 3;\n case 'moderate':\n return 2;\n case 'low':\n return 1;\n default:\n return 0;\n }\n}\n\nfunction mapSensitivityToCategorizationLevel(\n level: string,\n): CategorizationLevel | null {\n const normalized = normalizeFIPSLevel(level);\n if (!normalized) return null;\n\n switch (normalized) {\n case 'high':\n return CategorizationLevel.High;\n case 'moderate':\n return CategorizationLevel.Moderate;\n case 'low':\n return CategorizationLevel.Low;\n default:\n return null;\n }\n}\n\nfunction sspAuthorizationStatus(state: string): AuthorizationStatus | null {\n switch (state.toLowerCase()) {\n case 'operational':\n return AuthorizationStatus.Authorized;\n case 'under-development':\n return AuthorizationStatus.PendingAuthorization;\n case 'disposition':\n return AuthorizationStatus.Revoked;\n case 'other':\n return AuthorizationStatus.NotYetRequested;\n default:\n return null;\n }\n}\n\nfunction buildComponentControlMap(\n ci: ControlImplementationClass | undefined,\n): Map<string, Set<string>> {\n const result = new Map<string, Set<string>>();\n if (!ci) return result;\n\n for (const ir of ci['implemented-requirements'] ?? []) {\n const controlId = ir['control-id'];\n\n // Direct by-components on the implemented-requirement\n for (const bc of ir['by-components'] ?? []) {\n addComponentControl(result, bc['component-uuid'], controlId);\n }\n\n // by-components within statements\n for (const stmt of ir.statements ?? []) {\n for (const bc of stmt['by-components'] ?? []) {\n addComponentControl(result, bc['component-uuid'], controlId);\n }\n }\n }\n\n return result;\n}\n\nfunction addComponentControl(\n m: Map<string, Set<string>>,\n compUUID: string,\n controlId: string,\n): void {\n let controls = m.get(compUUID);\n if (!controls) {\n controls = new Set<string>();\n m.set(compUUID, controls);\n }\n controls.add(controlId);\n}\n\nfunction sspComponentToHDFComponent(\n sc: AssessmentAssetsComponent,\n componentControls: Map<string, Set<string>>,\n): HdfComponent {\n const comp: HdfComponent = {\n name: sc.title,\n type: mapOSCALComponentType(sc.type),\n };\n\n if (sc.description) {\n comp.description = sc.description;\n }\n\n // Add control IDs as baseline refs (NIST notation)\n const controls = componentControls.get(sc.uuid);\n if (controls && controls.size > 0) {\n const refs: string[] = [];\n for (const controlId of controls) {\n refs.push(controlIdToNistTag(controlId));\n }\n if (refs.length > 0) {\n comp.baselineRefs = refs;\n }\n }\n\n return comp;\n}\n\nfunction mapOSCALComponentType(oscalType: string): BoundaryDescription {\n switch (oscalType.toLowerCase()) {\n case 'software':\n case 'this-system':\n return BoundaryDescription.Application;\n case 'service':\n return BoundaryDescription.Application;\n case 'hardware':\n return BoundaryDescription.Host;\n case 'network':\n return BoundaryDescription.Network;\n case 'database':\n return BoundaryDescription.Database;\n case 'storage':\n return BoundaryDescription.Artifact;\n default:\n return BoundaryDescription.Application;\n }\n}\n","/**\n * OSCAL Assessment Plan (SAP) to HDF Plan converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_sap.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfPlan,\n Assessment,\n RunnerConfig,\n} from '@mitre/hdf-schema';\nimport { PlanType } from '@mitre/hdf-schema';\nimport type {\n Oscal,\n SecurityAssessmentPlanSAP,\n AssessedControls,\n ReferencedControlObjectives,\n} from './types.js';\nimport {\n controlIdToNistTag,\n controlIdsToNistTags,\n extractControlIdFromObjectiveId,\n extractPropValue,\n flattenParts,\n extractMetadata,\n toKebabCase,\n} from './shared.js';\n\n/**\n * Converts an OSCAL Assessment Plan document to HDF Plan JSON.\n *\n * @param input - Raw JSON string containing an OSCAL assessment-plan\n * @returns HDF Plan JSON string\n */\nexport async function convertOscalSapToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-assessment-plan');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc['assessment-plan']) {\n throw new Error(\n \"oscal-assessment-plan: input is not an assessment-plan document (root key is not 'assessment-plan')\",\n );\n }\n\n const ap = doc['assessment-plan'];\n const integrity = await inputIntegrity(input);\n const meta = extractMetadata(ap.metadata);\n\n // Build assessments from reviewed-controls\n const assessments = buildAssessments(ap);\n\n // Extract systemRef from import-ssp\n const systemRef = ap['import-ssp']?.href || undefined;\n\n // Determine plan type from assessment-assets/tasks\n const planType = determinePlanType(ap);\n\n // Build description from metadata remarks and terms-and-conditions\n const description = buildPlanDescription(ap);\n\n const plan: HdfPlan = {\n name: toKebabCase(ap.metadata.title, 'oscal-assessment-plan'),\n assessments,\n integrity,\n systemRef,\n version: meta.version,\n type: planType,\n description,\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n };\n\n return JSON.stringify(plan, null, 2);\n}\n\nfunction buildAssessments(ap: SecurityAssessmentPlanSAP): Assessment[] {\n if (!ap['reviewed-controls']) {\n return [{ baselineRef: 'oscal-assessment-plan' }];\n }\n\n const assessments: Assessment[] = [];\n\n for (const cs of ap['reviewed-controls']['control-selections'] ?? []) {\n const assessment: Assessment = {\n baselineRef: deriveBaselineRef(ap, cs),\n };\n\n if (cs.description) {\n assessment.description = cs.description;\n }\n\n assessment.runner = extractRunnerConfig(ap) ?? undefined;\n assessment.targetSelector = buildTargetSelector(ap) ?? undefined;\n\n assessments.push(assessment);\n }\n\n // If no control selections but there are control-objective-selections\n if (assessments.length === 0 && (ap['reviewed-controls']['control-objective-selections']?.length ?? 0) > 0) {\n for (const co of ap['reviewed-controls']['control-objective-selections']!) {\n const assessment: Assessment = {\n baselineRef: deriveBaselineRefFromObjectives(ap, co),\n runner: extractRunnerConfig(ap) ?? undefined,\n };\n if (co.description) {\n assessment.description = co.description;\n }\n assessments.push(assessment);\n }\n }\n\n // Ensure at least one assessment exists\n if (assessments.length === 0) {\n assessments.push({ baselineRef: 'oscal-assessment-plan' });\n }\n\n return assessments;\n}\n\nfunction deriveBaselineRef(ap: SecurityAssessmentPlanSAP, cs: AssessedControls): string {\n if (cs['include-all'] !== undefined) {\n if (ap['import-ssp']?.href) {\n return ap['import-ssp'].href;\n }\n return 'all-controls';\n }\n\n if (cs['include-controls'] && cs['include-controls'].length > 0) {\n const ids = cs['include-controls'].map(sc => controlIdToNistTag(sc['control-id']));\n return ids.join(',');\n }\n\n if (ap['import-ssp']?.href) {\n return ap['import-ssp'].href;\n }\n\n return 'oscal-assessment-plan';\n}\n\nfunction deriveBaselineRefFromObjectives(\n ap: SecurityAssessmentPlanSAP,\n co: ReferencedControlObjectives,\n): string {\n if (co['include-all'] !== undefined) {\n if (ap['import-ssp']?.href) {\n return ap['import-ssp'].href;\n }\n return 'all-objectives';\n }\n\n if (co['include-objectives'] && co['include-objectives'].length > 0) {\n const ids = co['include-objectives'].map(sc =>\n extractControlIdFromObjectiveId(sc['objective-id']),\n );\n return controlIdsToNistTags(ids).join(',');\n }\n\n return 'oscal-assessment-plan';\n}\n\nfunction extractRunnerConfig(ap: SecurityAssessmentPlanSAP): RunnerConfig | null {\n const assets = ap['assessment-assets'];\n if (!assets) return null;\n\n // Look for the first assessment platform\n const platforms = assets['assessment-platforms'];\n if (platforms && platforms.length > 0) {\n const platform = platforms[0]!;\n const config: RunnerConfig = {};\n if (platform.title) {\n config.name = platform.title;\n }\n return config;\n }\n\n // Fall back to components\n if (assets.components && assets.components.length > 0) {\n const comp = assets.components[0]!;\n const config: RunnerConfig = {\n name: comp.title,\n };\n const version = extractPropValue(comp.props, 'version');\n if (version) {\n config.version = version;\n }\n return config;\n }\n\n return null;\n}\n\nfunction buildTargetSelector(\n ap: SecurityAssessmentPlanSAP,\n): Record<string, string> | null {\n const subjects = ap['assessment-subjects'];\n if (!subjects || subjects.length === 0) return null;\n\n const selector: Record<string, string> = {};\n for (const subject of subjects) {\n if (subject.type) {\n const key = 'subject-type';\n if (selector[key] !== undefined) {\n selector[key] += ',' + subject.type;\n } else {\n selector[key] = subject.type;\n }\n }\n if (subject['include-all'] !== undefined) {\n selector['include-' + subject.type] = 'all';\n }\n }\n\n if (Object.keys(selector).length === 0) return null;\n return selector;\n}\n\nfunction determinePlanType(ap: SecurityAssessmentPlanSAP): PlanType | undefined {\n const aType = extractPropValue(ap.metadata.props, 'assessment-type');\n if (aType) {\n switch (aType.toLowerCase()) {\n case 'automated':\n return PlanType.Automated;\n case 'manual':\n return PlanType.Manual;\n }\n }\n\n if (ap.tasks && ap.tasks.length > 0) {\n return PlanType.Hybrid;\n }\n\n return undefined;\n}\n\nfunction buildPlanDescription(ap: SecurityAssessmentPlanSAP): string | undefined {\n const parts: string[] = [];\n\n if (ap.metadata.remarks) {\n parts.push(ap.metadata.remarks);\n }\n\n if (ap['terms-and-conditions']?.parts && ap['terms-and-conditions'].parts.length > 0) {\n const terms = flattenParts(ap['terms-and-conditions'].parts);\n if (terms) {\n parts.push('Terms and Conditions: ' + terms);\n }\n }\n\n if (parts.length === 0) return undefined;\n return parts.join('\\n\\n');\n}\n","/**\n * OSCAL Plan of Action and Milestones (POA&M) to HDF Amendments converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_poam.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfAmendments,\n StandaloneOverride,\n Milestone as HdfMilestone,\n} from '@mitre/hdf-schema';\nimport {\n OverrideType,\n} from '@mitre/hdf-schema';\n\n// The hdf-amendments schema defines its own ResultStatus, AppliedByType, and\n// milestone Status enums that conflict with hdf-results enums of the same name.\n// They aren't re-exported from the @mitre/hdf-schema barrel to avoid collisions.\n// We use string literals with type casts for these fields.\n/* eslint-disable @typescript-eslint/no-explicit-any */\nimport type {\n Oscal,\n PlanOfActionAndMilestonesPOAM,\n POAMItem,\n IdentifiedRisk,\n DocumentMetadata,\n} from './types.js';\nimport {\n controlIdToNistTag,\n extractPropValue,\n oscalStatusToHdf,\n extractMetadata,\n toKebabCase,\n} from './shared.js';\n\n/**\n * Converts an OSCAL POA&M document to HDF Amendments JSON.\n *\n * @param input - Raw JSON string containing an OSCAL POA&M\n * @returns HDF Amendments JSON string\n */\nexport async function convertOscalPoamToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-poam');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc['plan-of-action-and-milestones']) {\n throw new Error(\n \"oscal-poam: input is not a plan-of-action-and-milestones document (root key is not 'plan-of-action-and-milestones')\",\n );\n }\n\n const poam = doc['plan-of-action-and-milestones'];\n const integrity = await inputIntegrity(input);\n const meta = extractMetadata(poam.metadata);\n\n // Build risk lookup map\n const riskMap = buildRiskMap(poam.risks ?? []);\n\n // Convert poam-items to StandaloneOverrides\n const overrides: StandaloneOverride[] = [];\n for (const item of poam['poam-items']) {\n overrides.push(poamItemToOverride(item, riskMap, poam));\n }\n\n // Extract systemRef from import-ssp\n const systemRef = poam['import-ssp']?.href || undefined;\n\n // Build appliedBy from metadata responsible-parties\n const appliedBy = extractAppliedBy(poam.metadata);\n\n const amendments: HdfAmendments = {\n name: toKebabCase(poam.metadata.title, 'oscal-poam'),\n overrides,\n integrity,\n systemRef,\n version: meta.version,\n appliedBy,\n generator: {\n name: 'hdf-converters',\n version: '1.0.0',\n },\n };\n\n return JSON.stringify(amendments, null, 2);\n}\n\nfunction buildRiskMap(risks: IdentifiedRisk[]): Map<string, IdentifiedRisk> {\n const m = new Map<string, IdentifiedRisk>();\n for (const risk of risks) {\n m.set(risk.uuid, risk);\n }\n return m;\n}\n\nfunction poamItemToOverride(\n item: POAMItem,\n riskMap: Map<string, IdentifiedRisk>,\n poam: PlanOfActionAndMilestonesPOAM,\n): StandaloneOverride {\n return {\n type: OverrideType.Poam,\n requirementId: extractRequirementIdFromPOAMItem(item, riskMap),\n reason: poamItemReason(item),\n status: poamItemStatus(item, riskMap),\n appliedBy: poamItemAppliedBy(poam),\n appliedAt: poamItemAppliedAt(poam),\n expiresAt: poamItemExpiresAt(),\n milestones: extractMilestones(item, riskMap) as any,\n };\n}\n\nfunction extractRequirementIdFromPOAMItem(\n item: POAMItem,\n riskMap: Map<string, IdentifiedRisk>,\n): string {\n // Check related risks for impacted-control-id\n for (const rr of item['related-risks'] ?? []) {\n const riskUuid = rr['risk-uuid'];\n if (riskUuid) {\n const risk = riskMap.get(riskUuid);\n if (risk) {\n const controlId = extractPropValue(risk.props, 'impacted-control-id');\n if (controlId) {\n return controlIdToNistTag(controlId);\n }\n }\n }\n }\n\n // Check poam-item props for POAM-ID\n const poamId = extractPropValue(item.props, 'POAM-ID');\n if (poamId) return poamId;\n\n // Fall back to the title\n if (item.title) return item.title;\n\n return 'unknown';\n}\n\nfunction poamItemReason(item: POAMItem): string {\n if (item.description) return item.description;\n if (item.title) return item.title;\n return 'POA&M item';\n}\n\nfunction poamItemStatus(\n item: POAMItem,\n riskMap: Map<string, IdentifiedRisk>,\n): any {\n for (const rr of item['related-risks'] ?? []) {\n const riskUuid = rr['risk-uuid'];\n if (riskUuid) {\n const risk = riskMap.get(riskUuid);\n if (risk) {\n const status = oscalStatusToHdf(risk.status);\n if (status === 'passed') return 'passed' as any;\n if (status === 'failed') return 'failed' as any;\n }\n }\n }\n\n // Default: POA&M items typically represent open/failed findings\n return 'failed' as any;\n}\n\nfunction poamItemAppliedBy(\n poam: PlanOfActionAndMilestonesPOAM,\n): StandaloneOverride['appliedBy'] {\n // Look for prepared-by in responsible-parties\n const rps = poam.metadata['responsible-parties'];\n if (rps) {\n for (const rp of rps) {\n if (rp['role-id'] === 'prepared-by' && rp['party-uuids'].length > 0) {\n return {\n type: 'simple' as any,\n identifier: rp['party-uuids'][0]!,\n };\n }\n }\n\n // Fall back to any responsible party\n if (rps.length > 0 && rps[0]!['party-uuids'].length > 0) {\n return {\n type: 'simple' as any,\n identifier: rps[0]!['party-uuids'][0]!,\n };\n }\n }\n\n return {\n type: 'system' as any,\n identifier: 'oscal-poam-converter',\n };\n}\n\nfunction poamItemAppliedAt(poam: PlanOfActionAndMilestonesPOAM): Date {\n if (poam.metadata['last-modified']) {\n const t = new Date(poam.metadata['last-modified']);\n if (!isNaN(t.getTime())) {\n return t;\n }\n }\n return new Date();\n}\n\nfunction poamItemExpiresAt(): Date {\n // Default: 1 year from now\n const d = new Date();\n d.setFullYear(d.getFullYear() + 1);\n return d;\n}\n\nfunction extractMilestones(\n item: POAMItem,\n riskMap: Map<string, IdentifiedRisk>,\n): HdfMilestone[] {\n const milestones: HdfMilestone[] = [];\n\n for (const rr of item['related-risks'] ?? []) {\n const riskUuid = rr['risk-uuid'];\n if (!riskUuid) continue;\n const risk = riskMap.get(riskUuid);\n if (!risk) continue;\n\n for (const rem of risk.remediations ?? []) {\n if (rem.lifecycle !== 'planned') continue;\n\n const estimatedCompletion = new Date();\n estimatedCompletion.setMonth(estimatedCompletion.getMonth() + 3);\n\n milestones.push({\n description: rem.title + ': ' + rem.description,\n estimatedCompletion,\n status: 'pending' as any,\n });\n }\n }\n\n return milestones;\n}\n\nfunction extractAppliedBy(\n meta: DocumentMetadata,\n): HdfAmendments['appliedBy'] {\n const rps = meta['responsible-parties'];\n if (rps) {\n for (const rp of rps) {\n if (rp['role-id'] === 'prepared-by' && rp['party-uuids'].length > 0) {\n return {\n type: 'simple' as any,\n identifier: rp['party-uuids'][0]!,\n };\n }\n }\n }\n return undefined;\n}\n","/**\n * OSCAL Assessment Results (SAR) to HDF Results converter.\n *\n * Mirrors the Go implementation in converters/oscal-to-hdf/go/converter_sar.go.\n */\n\nimport { parseJSON } from '@mitre/hdf-utilities';\nimport { inputChecksum, inputIntegrity, validateInputSize } from '../../../shared/typescript/converterutil.js';\nimport type {\n HdfResults,\n EvaluatedBaseline,\n EvaluatedRequirement,\n RequirementResult,\n} from '@mitre/hdf-schema';\nimport {\n ResultStatus,\n createMinimalBaseline,\n createRequirement,\n createResult,\n type Description,\n} from '@mitre/hdf-schema';\nimport type {\n Oscal,\n SecurityAssessmentResultsSAR,\n AssessmentResult,\n Finding,\n Observation,\n IdentifiedRisk,\n} from './types.js';\nimport {\n controlIdToNistTag,\n extractControlIdFromObjectiveId,\n oscalStatusToHdf,\n extractRiskSeverity,\n extractMetadata,\n toKebabCase,\n} from './shared.js';\n\n/**\n * Converts an OSCAL Assessment Results (SAR) document to HDF Results JSON.\n *\n * @param input - Raw JSON string containing OSCAL assessment-results\n * @returns HDF Results JSON string\n */\nexport async function convertOscalSarToHdf(input: string): Promise<string> {\n validateInputSize(input, 'oscal-assessment-results');\n\n if (!input || input.trim().length === 0) {\n throw new Error('empty input');\n }\n\n const doc = parseJSON<Oscal>(input);\n if (!doc['assessment-results']) {\n throw new Error(\n \"oscal-assessment-results: input is not an assessment-results document (root key is not 'assessment-results')\",\n );\n }\n\n const sar = doc['assessment-results'];\n const meta = extractMetadata(sar.metadata);\n\n const baselines: EvaluatedBaseline[] = [];\n for (const result of sar.results) {\n const baseline = await resultToEvaluatedBaseline(result, sar, input);\n baselines.push(baseline);\n }\n\n // Extract planRef from import-ap\n const planRef = sar['import-ap']?.href || undefined;\n\n // Parse timestamp from metadata\n let timestamp: Date | undefined;\n if (meta.lastModified) {\n const t = new Date(meta.lastModified);\n if (!isNaN(t.getTime())) {\n timestamp = t;\n }\n }\n\n const hdf: HdfResults = {\n baselines,\n generator: {\n name: 'oscal-assessment-results-to-hdf',\n version: '1.0.0',\n },\n tool: {\n name: 'OSCAL Assessment Results',\n format: 'OSCAL',\n },\n timestamp: timestamp ?? new Date(),\n planRef,\n };\n\n return JSON.stringify(hdf, null, 2);\n}\n\nasync function resultToEvaluatedBaseline(\n result: AssessmentResult,\n sar: SecurityAssessmentResultsSAR,\n rawInput: string,\n): Promise<EvaluatedBaseline> {\n const checksum = await inputChecksum(rawInput);\n\n // Build lookup maps for observations and risks\n const obsMap = buildObservationMap(result.observations ?? []);\n const riskMap = buildRiskMap(result.risks ?? []);\n\n // Group findings by control ID, preserving insertion order\n const controlOrder: string[] = [];\n const controlMap = new Map<string, Finding[]>();\n\n for (const f of result.findings ?? []) {\n const controlId = extractControlIdFromFinding(f);\n const existing = controlMap.get(controlId);\n if (existing) {\n existing.push(f);\n } else {\n controlOrder.push(controlId);\n controlMap.set(controlId, [f]);\n }\n }\n\n // Build requirements in insertion order\n const requirements: EvaluatedRequirement[] = [];\n for (const controlId of controlOrder) {\n const findings = controlMap.get(controlId)!;\n const req = findingsToEvaluatedRequirement(controlId, findings, obsMap, riskMap, result);\n requirements.push(req);\n }\n\n // Derive baseline name\n const name = sarBaselineName(result, sar);\n\n const baseline = createMinimalBaseline(name, requirements, {\n resultsChecksum: checksum,\n integrity: await inputIntegrity(rawInput),\n status: 'loaded',\n title: result.title,\n }) as EvaluatedBaseline;\n\n if (result.description) {\n (baseline as Record<string, unknown>).description = result.description;\n }\n\n return baseline;\n}\n\nfunction findingsToEvaluatedRequirement(\n controlId: string,\n findings: Finding[],\n obsMap: Map<string, Observation>,\n riskMap: Map<string, IdentifiedRisk>,\n result: AssessmentResult,\n): EvaluatedRequirement {\n const nistTag = controlIdToNistTag(controlId);\n\n // Use the first finding for title\n const firstFinding = findings[0]!;\n const title = firstFinding.title || nistTag;\n\n // Determine impact from related risks\n const impact = sarFindingsImpact(findings, riskMap);\n\n // Build descriptions from findings and observations\n const descriptions = sarBuildDescriptions(findings, obsMap);\n\n // Build results from each finding\n const results: RequirementResult[] = [];\n for (const f of findings) {\n results.push(findingToRequirementResult(f, obsMap, riskMap, result));\n }\n\n const tags: Record<string, unknown> = {\n nist: [nistTag],\n };\n\n return createRequirement(nistTag, title, descriptions, impact, results, { tags });\n}\n\nfunction findingToRequirementResult(\n f: Finding,\n obsMap: Map<string, Observation>,\n riskMap: Map<string, IdentifiedRisk>,\n result: AssessmentResult,\n): RequirementResult {\n const status = mapFindingStatus(f);\n const codeDesc = buildCodeDesc(f, obsMap);\n const message = buildRiskMessage(f, riskMap);\n const startTime = parseResultStartTime(result);\n\n return createResult(status, message || undefined, {\n codeDesc,\n startTime: startTime.getTime() > 0 ? startTime : undefined,\n });\n}\n\nfunction extractControlIdFromFinding(f: Finding): string {\n const targetId = f.target['target-id'];\n if (!targetId) return 'unknown';\n\n // For objective-id and statement-id, extract the base control ID\n let controlId = extractControlIdFromObjectiveId(targetId);\n\n // Handle statement-id format: \"au-1_smt.a\" -> \"au-1\"\n const idx = controlId.indexOf('_');\n if (idx > 0) {\n controlId = controlId.slice(0, idx);\n }\n\n return controlId;\n}\n\nfunction mapFindingStatus(f: Finding): ResultStatus {\n const status = oscalStatusToHdf(f.target.status.state);\n if (status === 'passed') return ResultStatus.Passed;\n if (status === 'failed') return ResultStatus.Failed;\n return ResultStatus.NotReviewed;\n}\n\nfunction buildCodeDesc(f: Finding, obsMap: Map<string, Observation>): string {\n const parts: string[] = [];\n\n for (const ref of f['related-observations'] ?? []) {\n const obsUuid = ref['observation-uuid'];\n if (!obsUuid) continue;\n const obs = obsMap.get(obsUuid);\n if (!obs) continue;\n\n if (obs.methods && obs.methods.length > 0) {\n parts.push('Methods: ' + obs.methods.join(', '));\n }\n\n for (const subj of obs.subjects ?? []) {\n let subjDesc = subj.type;\n if (subj.title) {\n subjDesc = subj.title + ' (' + subj.type + ')';\n }\n parts.push('Subject: ' + subjDesc);\n }\n }\n\n if (parts.length === 0) return f.title;\n\n return parts.join('; ');\n}\n\nfunction buildRiskMessage(f: Finding, riskMap: Map<string, IdentifiedRisk>): string {\n const messages: string[] = [];\n\n for (const ref of f['related-risks'] ?? []) {\n const riskUuid = ref['risk-uuid'];\n if (!riskUuid) continue;\n const risk = riskMap.get(riskUuid);\n if (!risk) continue;\n\n let msg = risk.title;\n if (risk.description) {\n msg += ': ' + risk.description;\n }\n messages.push(msg);\n }\n\n return messages.join('\\n');\n}\n\nfunction sarFindingsImpact(\n findings: Finding[],\n riskMap: Map<string, IdentifiedRisk>,\n): number {\n let highestImpact = -1.0;\n\n for (const f of findings) {\n for (const ref of f['related-risks'] ?? []) {\n const riskUuid = ref['risk-uuid'];\n if (!riskUuid) continue;\n const risk = riskMap.get(riskUuid);\n if (!risk) continue;\n const impact = extractRiskSeverity(risk.characterizations, -1.0);\n if (impact > highestImpact) {\n highestImpact = impact;\n }\n }\n }\n\n if (highestImpact < 0) return 0.5; // default medium impact\n return highestImpact;\n}\n\nfunction sarBuildDescriptions(\n findings: Finding[],\n obsMap: Map<string, Observation>,\n): Description[] {\n const descriptions: Description[] = [];\n\n // Default description from finding descriptions\n const findingDescs: string[] = [];\n for (const f of findings) {\n if (f.description) {\n findingDescs.push(f.description);\n }\n }\n descriptions.push({\n label: 'default',\n data: findingDescs.join('\\n') || '',\n });\n\n // Rationale from observation descriptions\n const obsDescs: string[] = [];\n const seen = new Set<string>();\n for (const f of findings) {\n for (const ref of f['related-observations'] ?? []) {\n const obsUuid = ref['observation-uuid'];\n if (!obsUuid || seen.has(obsUuid)) continue;\n seen.add(obsUuid);\n const obs = obsMap.get(obsUuid);\n if (obs?.description) {\n obsDescs.push(obs.description);\n }\n }\n }\n if (obsDescs.length > 0) {\n descriptions.push({\n label: 'rationale',\n data: obsDescs.join('\\n'),\n });\n }\n\n return descriptions;\n}\n\nfunction buildObservationMap(observations: Observation[]): Map<string, Observation> {\n const m = new Map<string, Observation>();\n for (const obs of observations) {\n m.set(obs.uuid, obs);\n }\n return m;\n}\n\nfunction buildRiskMap(risks: IdentifiedRisk[]): Map<string, IdentifiedRisk> {\n const m = new Map<string, IdentifiedRisk>();\n for (const risk of risks) {\n m.set(risk.uuid, risk);\n }\n return m;\n}\n\nfunction parseResultStartTime(result: AssessmentResult): Date {\n if (result.start) {\n const t = new Date(result.start);\n if (!isNaN(t.getTime())) {\n return t;\n }\n }\n return new Date(0);\n}\n\nfunction sarBaselineName(result: AssessmentResult, sar: SecurityAssessmentResultsSAR): string {\n const title = result.title || sar.metadata.title;\n return toKebabCase(title, 'oscal-assessment-results');\n}\n"],"mappings":"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"}
|