Skip to content

Commit

Permalink
feat: add support for cyclonedx and cyclonedx-json output-formats (#396)
Browse files Browse the repository at this point in the history
Signed-off-by: Piotr Solarczyk <[email protected]>
Signed-off-by: Keith Zantow <[email protected]>
Co-authored-by: Keith Zantow <[email protected]>
  • Loading branch information
ps-e and kzantow authored Dec 11, 2024
1 parent e374579 commit 763018a
Show file tree
Hide file tree
Showing 7 changed files with 106 additions and 13 deletions.
4 changes: 1 addition & 3 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,4 @@ typings/
/grype-db

# Action temporary files
results.sarif
vulnerabilities.json
results.json
/results.*
12 changes: 7 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ The inputs `image`, `path`, and `sbom` are mutually exclusive to specify the sou
| `registry-username` | The registry username to use when authenticating to an external registry | |
| `registry-password` | The registry password to use when authenticating to an external registry | |
| `fail-build` | Fail the build if a vulnerability is found with a higher severity. That severity defaults to `medium` and can be set with `severity-cutoff`. | `true` |
| `output-format` | Set the output parameter after successful action execution. Valid choices are `json`, `sarif`, and `table`, where `table` output will print to the console instead of generating a file. | `sarif` |
| `output-format` | Set the output parameter after successful action execution. Valid choices are `json`, `sarif`, `cyclonedx-xml`, `cyclonedx-json`, and `table`; where `table` output will also display in the logs. | `sarif` |
| `output-file` | File to output the Grype scan results to. Defaults to a file in the system temp directory, available in the action outputs | |
| `severity-cutoff` | Optionally specify the minimum vulnerability severity to trigger a failure. Valid choices are "negligible", "low", "medium", "high" and "critical". Any vulnerability with a severity less than this value will lead to a "warning" result. Default is "medium". | `medium` |
| `only-fixed` | Specify whether to only report vulnerabilities that have a fix available. | `false` |
Expand All @@ -139,10 +139,12 @@ The inputs `image`, `path`, and `sbom` are mutually exclusive to specify the sou

### Action Outputs

| Output Name | Description | Type |
| ----------- | ------------------------------------------------------------ | ------ |
| `sarif` | Path to the SARIF report file, if `output-format` is `sarif` | string |
| `json` | Path to the report file , if `output-format` is `json` | string |
| Output Name | Description | Type |
|------------------|--------------------------------------------------------------------------------|--------|
| `sarif` | Path to the SARIF report file, if `output-format` is `sarif` | string |
| `json` | Path to the report file , if `output-format` is `json` | string |
| `cyclonedx-xml` | Path to the CycloneDX report file, if `output-format` is `cyclonedx` | string |
| `cyclonedx-json` | Path to the CycloneDX JSON report file, if `output-format` is `cyclonedx-json` | string |

### Example Workflows

Expand Down
10 changes: 7 additions & 3 deletions action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ inputs:
required: false
default: "true"
output-format:
description: 'Set the output parameter after successful action execution. Valid choices are "json", "sarif", and "table".'
description: 'Set the output parameter after successful action execution. Valid choices are "json", "sarif", "cyclonedx", "cyclonedx-json" and "table".'
required: false
default: "sarif"
output-file:
Expand Down Expand Up @@ -51,9 +51,13 @@ inputs:
required: false
outputs:
sarif:
description: "Path to a SARIF report file for the image"
description: "Path to a SARIF report file for the scan"
json:
description: "Path to a JSON report file for the image"
description: "Path to a JSON report file for the scan"
cyclonedx-xml:
description: "Path to a CycloneDX XML report file for the scan"
cyclonedx-json:
description: "Path to a CycloneDX JSON report file for the scan"
runs:
using: "node20"
main: "dist/index.js"
8 changes: 7 additions & 1 deletion dist/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -329,7 +329,13 @@ async function runScan({
}

const SEVERITY_LIST = ["negligible", "low", "medium", "high", "critical"];
const FORMAT_LIST = ["sarif", "json", "table"];
const FORMAT_LIST = [
"sarif",
"json",
"table",
"cyclonedx-xml",
"cyclonedx-json",
];
let cmdArgs = [];

if (core.isDebug()) {
Expand Down
8 changes: 7 additions & 1 deletion index.js
Original file line number Diff line number Diff line change
Expand Up @@ -315,7 +315,13 @@ async function runScan({
}

const SEVERITY_LIST = ["negligible", "low", "medium", "high", "critical"];
const FORMAT_LIST = ["sarif", "json", "table"];
const FORMAT_LIST = [
"sarif",
"json",
"table",
"cyclonedx-xml",
"cyclonedx-json",
];
let cmdArgs = [];

if (core.isDebug()) {
Expand Down
31 changes: 31 additions & 0 deletions tests/action.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,37 @@ describe("Github action", () => {
expect(outputs["json"]).toBeFalsy();
});

it("runs with cyclonedx-xml output", async () => {
const outputs = mockIO({
image: "",
path: "tests/fixtures/npm-project",
"fail-build": "true",
"output-format": "cyclonedx-xml",
"output-file": "./results.cdx.xml",
"severity-cutoff": "medium",
"add-cpes-if-none": "true",
});

await run();

expect(outputs["cyclonedx-xml"]).toBe("./results.cdx.xml");
});

it("runs with cyclonedx-json output", async () => {
const outputs = mockIO({
image: "",
path: "tests/fixtures/npm-project",
"fail-build": "true",
"output-format": "cyclonedx-json",
"severity-cutoff": "medium",
"add-cpes-if-none": "true",
});

await run();

expect(outputs["cyclonedx-json"]).toBeDefined();
});

it("runs with environment variables", async () => {
mockIO({
path: "tests/fixtures/npm-project",
Expand Down
46 changes: 46 additions & 0 deletions tests/grype_command.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,52 @@ describe("Grype command args", () => {
]);
});

it("is invoked with cyclonedx output", async () => {
const args = await mockRun({
source: "dir:.",
"fail-build": "false",
"output-file": "the-output-file",
"output-format": "cyclonedx-xml",
"severity-cutoff": "high",
version: "0.6.0",
"only-fixed": "false",
"add-cpes-if-none": "false",
"by-cve": "false",
});
expect(args).toEqual([
"-o",
"cyclonedx-xml",
"--file",
"the-output-file",
"--fail-on",
"high",
"dir:.",
]);
});

it("is invoked with cyclonedx-json output", async () => {
const args = await mockRun({
source: "dir:.",
"fail-build": "false",
"output-file": "the-output-file",
"output-format": "cyclonedx-json",
"severity-cutoff": "high",
version: "0.6.0",
"only-fixed": "false",
"add-cpes-if-none": "false",
"by-cve": "false",
});
expect(args).toEqual([
"-o",
"cyclonedx-json",
"--file",
"the-output-file",
"--fail-on",
"high",
"dir:.",
]);
});

it("is invoked with values", async () => {
const args = await mockRun({
image: "asdf",
Expand Down

0 comments on commit 763018a

Please sign in to comment.