From 75854c6dcbec3da9ed6d7f9262d4e2677b23a028 Mon Sep 17 00:00:00 2001 From: "Piotr P. Karwasz" Date: Fri, 17 Apr 2026 11:38:22 +0200 Subject: [PATCH] feat: Add reusable `scorecards-analysis-reusable.yml` workflow Similar to #699, adds a reusable Scorecard analysis workflow and refactors `scorecards-analysis.yml` to call it. Unlike the CodeQL workflow, which only relies on actions from GitHub-owned organisations (`github` and `actions`), this one uses a third-party action (`ossf/scorecard-action`) that needs to be upgraded in a timely manner. The usual process is: 1. A new version of the action is released. 2. The action is reviewed in `infrastructure-actions` and the new SHA is added to the authorized ones. 3. The old SHA is scheduled for removal. We need to perform the upgrade between steps 2 and 3, so we should configure Dependabot to bump this action weekly with a 7-day cooldown (step 2 occurs within 7 days of a new release). --- .github/workflows/README.md | 71 +++++++++++++++++++ .../scorecards-analysis-reusable.yml | 62 ++++++++++++++++ .github/workflows/scorecards-analysis.yml | 49 +++---------- 3 files changed, 142 insertions(+), 40 deletions(-) create mode 100644 .github/workflows/README.md create mode 100644 .github/workflows/scorecards-analysis-reusable.yml diff --git a/.github/workflows/README.md b/.github/workflows/README.md new file mode 100644 index 000000000..d3479c978 --- /dev/null +++ b/.github/workflows/README.md @@ -0,0 +1,71 @@ + + +# Reusable Workflows + +This directory contains +[reusable GitHub Actions workflows](https://docs.github.com/en/actions/how-tos/reuse-automations/reuse-workflows) +shared across Apache Commons projects. They provide a consistent and secure CI setup without duplicating configuration in each repository. + +## Scorecards (`scorecards-analysis-reusable.yml`) + +Runs an [OpenSSF Scorecard](https://securityscorecards.dev/) analysis and uploads the results to +GitHub's code-scanning dashboard. +For public repositories, the results are also published to the Scorecard API, enabling the +Scorecard badge. + +This workflow has no inputs. + +### Required permissions + +In addition to uploading results to the code-scanning dashboard (`security-events: write`), +the workflow authenticates with securityscorecards.dev using an OIDC token (`id-token: write`). +The caller job must grant: + +```yaml +permissions: + actions: read + contents: read + security-events: write + id-token: write +``` + +### Usage example + +```yaml +name: Scorecards + +on: + branch_protection_rule: + schedule: + - cron: '30 1 * * 6' # Randomize this expression + push: + branches: [ "master" ] + +# Explicitly drop all permissions for security. +permissions: { } + +jobs: + scorecards: + # Intentionally not pinned: maintained by the same PMC. + uses: apache/commons-parent/.github/workflows/scorecards-analysis-reusable.yml@master + permissions: + actions: read + contents: read + security-events: write + id-token: write +``` diff --git a/.github/workflows/scorecards-analysis-reusable.yml b/.github/workflows/scorecards-analysis-reusable.yml new file mode 100644 index 000000000..7c86b21d7 --- /dev/null +++ b/.github/workflows/scorecards-analysis-reusable.yml @@ -0,0 +1,62 @@ +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache license, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# https://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the license for the specific language governing permissions and +# limitations under the license. + +name: Scorecards + +on: + workflow_call: { } + +# Explicitly drop all permissions inherited from the caller for security. +permissions: { } + +jobs: + + scorecards-analysis: + runs-on: ubuntu-latest + permissions: + actions: read + contents: read + # Needed to upload the results to the code-scanning dashboard. + security-events: write + # Needed to sign the results using Fulcio + id-token: write + + steps: + + - name: "Checkout code" + uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # 6.0.2 + with: + persist-credentials: false + + - name: "Run analysis" + uses: ossf/scorecard-action@4eaacf0543bb3f2c246792bd56e8cdeffafb205a # 2.4.3 + with: + results_file: results.sarif + results_format: sarif + repo_token: ${{ github.token }} + # Publish the results for public repositories to enable scorecard badges. + publish_results: true + + - name: "Upload artifact" + uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 + with: + name: SARIF file + path: results.sarif + retention-days: 5 + + - name: "Upload to code-scanning" + uses: github/codeql-action/upload-sarif@95e58e9a2cdfd71adc6e0353d5c52f41a045d225 # v4.35.2 + with: + sarif_file: results.sarif diff --git a/.github/workflows/scorecards-analysis.yml b/.github/workflows/scorecards-analysis.yml index 16e37f605..120e3a7f1 100644 --- a/.github/workflows/scorecards-analysis.yml +++ b/.github/workflows/scorecards-analysis.yml @@ -21,49 +21,18 @@ on: - cron: "30 1 * * 6" # Weekly on Saturdays push: branches: [ "master" ] + # For testing purposes + workflow_dispatch: { } -permissions: read-all +# Explicitly drop all permissions for security. +permissions: { } jobs: - analysis: - - name: "Scorecards analysis" - runs-on: ubuntu-latest + scorecards-analysis: + uses: ./.github/workflows/scorecards-analysis-reusable.yml permissions: - # Needed to upload the results to the code-scanning dashboard. - security-events: write actions: read - id-token: write # This is required for requesting the JWT - contents: read # This is required for actions/checkout - - steps: - - - name: "Checkout code" - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # 6.0.2 - with: - persist-credentials: false - - - name: "Run analysis" - uses: ossf/scorecard-action@4eaacf0543bb3f2c246792bd56e8cdeffafb205a # 2.4.3 - with: - results_file: results.sarif - results_format: sarif - # A read-only PAT token, which is sufficient for the action to function. - # The relevant discussion: https://github.com/ossf/scorecard-action/issues/188 - repo_token: ${{ secrets.GITHUB_TOKEN }} - # Publish the results for public repositories to enable scorecard badges. - # For more details: https://github.com/ossf/scorecard-action#publishing-results - publish_results: true - - - name: "Upload artifact" - uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 - with: - name: SARIF file - path: results.sarif - retention-days: 5 - - - name: "Upload to code-scanning" - uses: github/codeql-action/upload-sarif@95e58e9a2cdfd71adc6e0353d5c52f41a045d225 # v4.35.2 - with: - sarif_file: results.sarif + contents: read + security-events: write + id-token: write