Skip to content

Commit d51106e

Browse files
committed
Stop using the upstream Trivy action
It lacks sufficient settings to control its cache and setup steps. Issue: PGO-1893
1 parent 2112c3c commit d51106e

File tree

2 files changed

+116
-57
lines changed

2 files changed

+116
-57
lines changed

.github/actions/trivy/action.yaml

Lines changed: 95 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,95 @@
1+
name: Trivy
2+
description: Scan this project using Trivy
3+
4+
# The Trivy team maintains an action, but it has trouble caching its vulnerability data:
5+
# https://github.com/aquasecurity/trivy-action/issues/389
6+
#
7+
# The action below uses any recent cache matching `cache-prefix` and calculates a cache key
8+
# derived from the data Trivy downloads.
9+
10+
inputs:
11+
cache:
12+
default: restore,success,use
13+
description: >
14+
What Trivy data to cache; one or more of restore, save, success, or use.
15+
16+
setup:
17+
default: v0.57.0,cache
18+
description: >
19+
How to install Trivy; one or more of version, none, or cache.
20+
21+
cache-directory:
22+
default: ${{ github.workspace }}/.cache/trivy
23+
24+
cache-prefix:
25+
default: cache-trivy
26+
27+
scan-target:
28+
default: .
29+
30+
scan-type:
31+
default: filesystem
32+
33+
runs:
34+
using: composite
35+
steps:
36+
# Parse list inputs as separated by commas and spaces.
37+
# Select the maximum version-looking string from `inputs.setup`.
38+
- name: Validate inputs
39+
id: parsed
40+
shell: bash
41+
run: |
42+
( <<< '${{ inputs.cache }}' jq -rRsS '"cache=\(split("[,\\s]+"; "") - [""])"'
43+
<<< '${{ inputs.setup }}' jq -rRsS '
44+
"setup=\(split("[,\\s]+"; "") - [""])",
45+
"version=\(split("[,\\s]+"; "") | max_by(split("[v.]"; "") | map(tonumber?)))"
46+
'
47+
) | tee --append $GITHUB_OUTPUT
48+
49+
# Install Trivy as requested.
50+
- if: ${{ ! contains(fromJSON(steps.parsed.outputs.setup), 'none') }}
51+
uses: aquasecurity/[email protected]
52+
with:
53+
cache: ${{ contains(fromJSON(steps.parsed.outputs.setup), 'cache') }}
54+
version: ${{ steps.parsed.outputs.version }}
55+
56+
# Restore a recent cache beginning with the prefix.
57+
- id: restore
58+
if: ${{ contains(fromJSON(steps.parsed.outputs.cache), 'restore') }}
59+
uses: actions/cache/restore@v4
60+
with:
61+
path: ${{ inputs.cache-directory }}
62+
key: ${{ inputs.cache-prefix }}-
63+
64+
- name: Run Trivy
65+
id: trivy
66+
shell: bash
67+
env:
68+
TRIVY_CACHE_DIR: >
69+
${{ contains(fromJSON(steps.parsed.outputs.cache), 'use') && inputs.cache-directory || '' }}
70+
run: |
71+
trivy '${{ inputs.scan-type }}' '${{ inputs.scan-target }}' ||
72+
result=$?
73+
74+
[[ -z "${TRIVY_CACHE_DIR}" ]] ||
75+
cat "${TRIVY_CACHE_DIR}/"*/metadata.json | sha256sum | read -r checksum -
76+
77+
<<< 'cache-key=${{ inputs.cache-prefix }}-'"${checksum-}" tee --append $GITHUB_OUTPUT
78+
exit "${result-0}"
79+
80+
# Save updated data to the cache when requested.
81+
- if: ${{ steps.trivy.outputs.cache-key == steps.restore.outputs.cache-matched-key }}
82+
shell: bash
83+
run: echo 'cache hit on ${{ steps.restore.outputs.cache-matched-key }}'
84+
- if: >
85+
${{
86+
steps.trivy.outputs.cache-key != steps.restore.outputs.cache-matched-key &&
87+
(
88+
(contains(fromJSON(steps.parsed.outputs.cache), 'save') && !cancelled()) ||
89+
(contains(fromJSON(steps.parsed.outputs.cache), 'success') && success())
90+
)
91+
}}
92+
uses: actions/cache/save@v4
93+
with:
94+
key: ${{ steps.trivy.outputs.cache-key }}
95+
path: ${{ inputs.cache-directory }}

.github/workflows/trivy.yaml

Lines changed: 21 additions & 57 deletions
Original file line numberDiff line numberDiff line change
@@ -12,55 +12,16 @@ env:
1212
# https://github.com/actions/setup-go/issues/457
1313
GOTOOLCHAIN: local
1414

15-
# Manage the Trivy data directory until upstream can do it reliably
16-
# https://github.com/aquasecurity/trivy-action/issues/389
17-
#
18-
# NOTE: This must match the default "cache-dir" upstream:
19-
# https://github.com/aquasecurity/trivy-action/blob/-/action.yaml
20-
TRIVY_CACHE_DIR: ${{ github.workspace }}/.cache/trivy
21-
2215
jobs:
2316
cache:
2417
runs-on: ubuntu-latest
2518
steps:
26-
- uses: aquasecurity/[email protected]
27-
with:
28-
cache: true
29-
version: v0.57.0
30-
31-
# The "aquasecurity/trivy-action" looks for data in the GitHub action
32-
# cache under a key with today's date.
33-
# - https://github.com/actions/cache/blob/-/restore#readme
34-
# - https://github.com/aquasecurity/trivy-action/blob/-/action.yaml
35-
- id: values
36-
run: |
37-
(
38-
date +'date=%Y-%m-%d'
39-
echo "glob=${TRIVY_CACHE_DIR}/*/metadata.json"
40-
) |
41-
tee --append $GITHUB_OUTPUT
42-
- id: restore
43-
uses: actions/cache/restore@v4
44-
with:
45-
key: cache-trivy-${{ steps.values.outputs.date }}
46-
path: ${{ env.TRIVY_CACHE_DIR }}
47-
restore-keys: cache-trivy-
48-
49-
# Validate or update the Trivy data cache.
50-
- id: validate
19+
- uses: actions/checkout@v4
20+
- uses: ./.github/actions/trivy
5121
env:
52-
METADATA_HASH: ${{ hashFiles(steps.values.outputs.glob) }}
53-
run: |
54-
<<< "before=${METADATA_HASH}" tee --append $GITHUB_OUTPUT
55-
trivy filesystem --download-db-only --scanners license,secret,vuln --quiet
56-
57-
# Save any successful changes back to the GitHub action cache.
58-
# - https://github.com/actions/cache/blob/-/save#readme
59-
- if: ${{ hashFiles(steps.values.outputs.glob) != steps.validate.outputs.before }}
60-
uses: actions/cache/save@v4
61-
with:
62-
key: ${{ steps.restore.outputs.cache-primary-key }}
63-
path: ${{ env.TRIVY_CACHE_DIR }}
22+
TRIVY_DB_DOWNLOAD_ONLY: true
23+
TRIVY_QUIET: true
24+
TRIVY_SCANNERS: license,secret,vuln
6425

6526
licenses:
6627
needs: [cache]
@@ -75,13 +36,13 @@ jobs:
7536

7637
# Report success only when detected licenses are listed in [/trivy.yaml].
7738
- name: Scan licenses
78-
uses: aquasecurity/[email protected]
39+
uses: ./.github/actions/trivy
7940
env:
8041
TRIVY_DEBUG: true
42+
TRIVY_EXIT_CODE: 1
43+
TRIVY_SCANNERS: license
8144
with:
82-
scan-type: filesystem
83-
scanners: license
84-
exit-code: 1
45+
cache: restore,use
8546

8647
vulnerabilities:
8748
if: ${{ github.repository == 'CrunchyData/postgres-operator' }}
@@ -97,21 +58,24 @@ jobs:
9758
# human consumption. This step fails only when Trivy is unable to scan.
9859
# A later step uploads results to GitHub as a pull request check.
9960
- name: Log detected vulnerabilities
100-
uses: aquasecurity/[email protected]
61+
uses: ./.github/actions/trivy
62+
env:
63+
TRIVY_SCANNERS: secret,vuln
10164
with:
102-
scan-type: filesystem
103-
scanners: secret,vuln
65+
cache: restore,use
10466

10567
# Produce a SARIF report of actionable results. This step fails only when
10668
# Trivy is unable to scan.
10769
- name: Report actionable vulnerabilities
108-
uses: aquasecurity/[email protected]
70+
uses: ./.github/actions/trivy
71+
env:
72+
TRIVY_IGNORE_UNFIXED: true
73+
TRIVY_FORMAT: 'sarif'
74+
TRIVY_OUTPUT: 'trivy-results.sarif'
75+
TRIVY_SCANNERS: secret,vuln
10976
with:
110-
scan-type: filesystem
111-
ignore-unfixed: true
112-
format: 'sarif'
113-
output: 'trivy-results.sarif'
114-
scanners: secret,vuln
77+
cache: use
78+
setup: none
11579

11680
# Submit the SARIF report to GitHub code scanning. Pull requests checks
11781
# succeed or fail according to branch protection rules.

0 commit comments

Comments
 (0)