GitHub Actions CI での trivy config 検証設定例
本記事は以下の8日目のエントリです。
シフトレフト、大事ですよね。
terraform での IaC における misconfiguration チェックを CI にやらせたい、と考え、以前から個人的に採用していた tfsec でのチェックを、今年はついに trivy へ移行しました。
昨年から 管理単位を小さくして運用する terraform の考え方をベースに、変更された箇所のみをチェックする設定を使っています。
実際の設定と、自身の工夫ポイントを紹介します。
変更箇所のみをチェックする設定
以下のような設定ファイル群を .github 配下に置いています
trivy conf CI の設定 yaml
# refs https://zenn.dev/yokoo_an209/articles/trivy-for-terraform
name: trivy-scan (pjx_acr)
on:
# push:
# paths:
# - 'tg/terragrunt.hcl'
# - 'tg/aws/envs/acr/**'
pull_request:
paths:
- 'tg/terragrunt.hcl'
- 'tg/aws/envs/acr/**'
env:
ENVIRONMENTS_DIR: 'tg/aws/envs'
jobs:
determine-workdir:
runs-on: ubuntu-latest
permissions:
pull-requests: read
contents: read
outputs:
workdirs: ${{ steps.filter.outputs.workdirs }}
steps:
- name: Checkout
uses: actions/checkout@v4
- uses: dorny/paths-filter@v3
id: changes
with:
filters: .github/pjx_acr.yml
- name: filter
id: filter
run: |
WORKDIRS=$(echo '${{ toJSON(steps.changes.outputs) }}' | jq '. | to_entries[] | select(.value == "true") | .key')
echo "workdirs=$(echo $WORKDIRS | jq -sc '.')" >> $GITHUB_OUTPUT
# trivy config scan
trivy-scan:
needs: determine-workdir
runs-on: ubuntu-latest
permissions:
id-token: write
contents: write
pull-requests: write
if: needs.determine-workdir.outputs.workdirs != '[]'
strategy:
matrix:
workdir: ${{ fromJSON(needs.determine-workdir.outputs.workdirs) }}
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Trivy Scan
uses: aquasecurity/trivy-action@master
with:
scan-type: "config"
#severity: "HIGH,CRITICAL"
#exit-code: '1'
scan-ref: '${{ github.workspace }}/${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }}'
#trivyignores: ${{ github.workspace }}/.configs/.trivyignore
output: trivy-scan-result.txt
- name: Format Trivy Scan Result
run: |
if [ -s trivy-scan-result.txt ]; then
# ファイルに内容がある場合
echo -e "## :warning: trivy config 結果 :warning: (${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }})\n<details><summary>詳細</summary>\n\n\`\`\`\n$(cat trivy-scan-result.txt)\n\`\`\`\n</details>" > formatted-trivy-result.md
else
# ファイルが空の場合
echo -e "## trivy config 結果 (${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }})\n脆弱性が検知されませんでした。" > formatted-trivy-result.md
fi
- name: Comment PR with Trivy scan results
uses: marocchino/sticky-pull-request-comment@v2
with:
recreate: true
GITHUB_TOKEN: ${{ secrets.github_token }}
path: formatted-trivy-result.md
dorny/paths-filter が見ている、変更箇所だけ CI を走らせる設定はこんな感じです。
acr/iam/oidc-role:
- 'tg/terragrunt.hcl'
- 'tg/aws/envs/acr/iam/oidc-role/**'
- 'tg/tf-modules/tgp-oidc/**'
acr/res/sops-key:
- 'tg/terragrunt.hcl'
- 'tg/aws/envs/acr/res/sops-key/**'
acr/res/ecr:
- 'tg/terragrunt.hcl'
- 'tg/aws/envs/acr/res/ecr/**'
acr/mng/secrets:
- 'tg/terragrunt.hcl'
- 'tg/aws/envs/acr/mng/secrets/**'
なお、ディレクトリ構成は以下のようにしています。
ディレクトリ構成
tg
├── aws
│ └── envs
│ └── acr
│ ├── iam
│ │ └── oidc-role
│ ├── mng
│ │ └── secrets
│ └── res
│ ├── ecr
│ └── sops-key
└── tf-modules
└── tgp-oidc
GitHub Actions には label 設定 API に文字数制限(50)あることを8月に知った[3]ので、以来、収まるように独自定義の略称を用いています。
across を acr、manage を mng、resource を res とかです。
独自に工夫しているポイント
- name: Trivy Scan
uses: aquasecurity/trivy-action@master
with:
scan-type: "config"
#severity: "HIGH,CRITICAL"
#exit-code: '1'
scan-ref: '${{ github.workspace }}/${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }}'
#trivyignores: ${{ github.workspace }}/.configs/.trivyignore
output: trivy-scan-result.txt
- name: Format Trivy Scan Result
run: |
if [ -s trivy-scan-result.txt ]; then
# ファイルに内容がある場合
echo -e "## :warning: trivy config 結果 :warning: (${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }})\n<details><summary>詳細</summary>\n\n\`\`\`\n$(cat trivy-scan-result.txt)\n\`\`\`\n</details>" > formatted-trivy-result.md
else
# ファイルが空の場合
echo -e "## trivy config 結果 (${{ env.ENVIRONMENTS_DIR }}/${{ matrix.workdir }})\n脆弱性が検知されませんでした。" > formatted-trivy-result.md
fi
- name: Comment PR with Trivy scan results
uses: marocchino/sticky-pull-request-comment@v2
with:
recreate: true
GITHUB_TOKEN: ${{ secrets.github_token }}
path: formatted-trivy-result.md
個人的な方針で、以下2つを意図的にそうしてます。
exit-code: '1'
をコメントアウトしている
1. これ、有効にしておくと、misconfig を検出したときに CI が止まっちゃって、どこにどういう問題があるかわからなくなっちゃうんですよね。。。
ということで、コメントアウトして、Format Trivy Scan Result
のところで「ファイルに内容がある場合」に来るので、 :warning: で目立つようにするというやり方をしてます。
2. trivyignores をまとめない
理由あって ignore する、は各現場であり得るものだと思っていて、何を ignore しているのかを方針的に明確化するために ${{ github.workspace }}/.configs/.trivyignore
に集約するのも1つの考え方、と思います。
が、自分は集約ファイルを使わず、問題箇所に1つ1つ
#trivy:ignore:AVD-AWS-0098 # (LOW): Secret explicitly uses the default key.
のように ignore 指定を入れるようにしています。「ここにはこういう misconfiguration がある」がわかるようにしておく意図です。
これには賛否あると思いますが、自分はこうしています。
こんな感じで検出
(ひとまず記事公開したいので、あとでスクショ貼ります。)
最後まで読んでいただきありがとうございました。
明日9日目の予定は以下になっています。お楽しみに。
- Metaps Advent Calendar 2024 : 「エンジニアなら知っておくべきファイル操作の基礎」by Jimmy Jin さん
- GitHub Actions Advent Calendar 2024 : ・・・12/8 3:30 時点で未定です。
-
7日目は fumiken さんの Fargate接続ツール(MP社製)のご紹介 でした。 ↩︎
-
7日目は @roulgonzaress さんの GHAをKEDAで動かす でした。 ↩︎
Discussion