From e5a36ed41a03983a3b8863a2694fe634deb7b0d3 Mon Sep 17 00:00:00 2001 From: piekstra Date: Fri, 14 Aug 2026 07:07:24 -0400 Subject: [PATCH 1/3] ci: INT-726 let scoped PRs satisfy their required checks Branch protection requires the six per-tool jobs, but they were gated at the job level on paths-filter output, so a PR touching one tool skipped the other tool's jobs. GitHub does not accept a skipped check as a satisfied required check, so every single-tool PR was unmergeable without an administrator bypass. #464 and #474 both hit it. The cost is not the inconvenience. Branch protection works because merging over an unmet gate is deliberate and visible; when ordinary work cannot merge without a bypass, the bypass stops being remarkable and a real unmet gate looks like the routine ones before it. The six required jobs now run on every PR and gate their steps instead. A job with nothing to do reports success rather than skipping, which is the honest result -- the check ran and found no work -- and the required checks are satisfied without changing repository settings. build-test-shared and lint-shared keep their job-level condition; neither is a required check. [INT-726] --- .github/workflows/ci.yml | 58 +++++++++++++++++++++++++++++++++++----- 1 file changed, 52 insertions(+), 6 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 139907a5..757aca8b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -40,18 +40,27 @@ jobs: build-test-cfl: needs: detect-changes - if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 + if: env.RELEVANT == 'true' with: go-version: '1.26' - name: Tidy cfl + if: env.RELEVANT == 'true' run: cd tools/cfl && go mod tidy && git diff --exit-code go.mod go.sum - name: Build cfl + if: env.RELEVANT == 'true' run: go build -v ./tools/cfl/... - name: Static release build guard cfl + if: env.RELEVANT == 'true' run: | set -euo pipefail cd tools/cfl @@ -70,22 +79,32 @@ jobs: fi done - name: Test cfl + if: env.RELEVANT == 'true' run: go test -v -race -coverprofile=coverage-cfl.out ./tools/cfl/... build-test-jtk: needs: detect-changes - if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 + if: env.RELEVANT == 'true' with: go-version: '1.26' - name: Tidy jtk + if: env.RELEVANT == 'true' run: cd tools/jtk && go mod tidy && git diff --exit-code go.mod go.sum - name: Build jtk + if: env.RELEVANT == 'true' run: go build -v ./tools/jtk/... - name: Static release build guard jtk + if: env.RELEVANT == 'true' run: | set -euo pipefail cd tools/jtk @@ -104,32 +123,47 @@ jobs: fi done - name: Test jtk + if: env.RELEVANT == 'true' run: go test -v -race -coverprofile=coverage-jtk.out ./tools/jtk/... lint-cfl: needs: detect-changes - if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 + if: env.RELEVANT == 'true' with: go-version: '1.26' - uses: golangci/golangci-lint-action@v7 + if: env.RELEVANT == 'true' with: working-directory: tools/cfl version: v2.12.2 lint-jtk: needs: detect-changes - if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 + if: env.RELEVANT == 'true' with: go-version: '1.26' - uses: golangci/golangci-lint-action@v7 + if: env.RELEVANT == 'true' with: working-directory: tools/jtk version: v2.12.2 @@ -182,21 +216,33 @@ jobs: # goreleaser_config resolves (distribution.md §8.3 / .github#15). identity-check-cfl: needs: detect-changes - if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: open-cli-collective/.github/actions/identity-check@v1 + if: env.RELEVANT == 'true' with: working-directory: tools/cfl identity-check-jtk: needs: detect-changes - if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' + # Runs on every PR so the check reports a conclusion; branch + # protection requires it, and a skipped check never satisfies that. + # The work itself is gated per step (INT-726). + env: + RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 + if: env.RELEVANT == 'true' - uses: open-cli-collective/.github/actions/identity-check@v1 + if: env.RELEVANT == 'true' with: working-directory: tools/jtk From feeb554d53fbf707e2c0eb2f21fb3b5ea1188297 Mon Sep 17 00:00:00 2001 From: piekstra Date: Fri, 14 Aug 2026 07:13:23 -0400 Subject: [PATCH 2/3] ci: INT-726 report required checks from wrappers, not per-step guards Review round. Gating every step duplicated the condition six times with nothing enforcing that a step added later carried it, and since actions/checkout was itself gated, an unguarded step on an irrelevant PR would have run against an unchecked-out workspace and failed for a reason that had nothing to do with the change. The work now stays in -run, which keeps its job-level condition and may skip freely with no per-step guards at all. The protected check name lives on a wrapper that always runs and reports the outcome of the job that did the work, treating skipped as a pass because there was nothing to verify. The guard exists once per job rather than once per step, so adding a step to a -run job needs no thought. Branch protection is untouched: the required names are unchanged, they are just produced by the wrappers now. [INT-726] --- .github/workflows/ci.yml | 173 ++++++++++++++++++++++++++------------- 1 file changed, 115 insertions(+), 58 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 757aca8b..bdcd250e 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -38,29 +38,20 @@ jobs: - 'Makefile' - '.github/workflows/ci.yml' - build-test-cfl: + build-test-cfl-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 - if: env.RELEVANT == 'true' with: go-version: '1.26' - name: Tidy cfl - if: env.RELEVANT == 'true' run: cd tools/cfl && go mod tidy && git diff --exit-code go.mod go.sum - name: Build cfl - if: env.RELEVANT == 'true' run: go build -v ./tools/cfl/... - name: Static release build guard cfl - if: env.RELEVANT == 'true' run: | set -euo pipefail cd tools/cfl @@ -79,32 +70,22 @@ jobs: fi done - name: Test cfl - if: env.RELEVANT == 'true' run: go test -v -race -coverprofile=coverage-cfl.out ./tools/cfl/... - build-test-jtk: + build-test-jtk-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 - if: env.RELEVANT == 'true' with: go-version: '1.26' - name: Tidy jtk - if: env.RELEVANT == 'true' run: cd tools/jtk && go mod tidy && git diff --exit-code go.mod go.sum - name: Build jtk - if: env.RELEVANT == 'true' run: go build -v ./tools/jtk/... - name: Static release build guard jtk - if: env.RELEVANT == 'true' run: | set -euo pipefail cd tools/jtk @@ -123,47 +104,32 @@ jobs: fi done - name: Test jtk - if: env.RELEVANT == 'true' run: go test -v -race -coverprofile=coverage-jtk.out ./tools/jtk/... - lint-cfl: + lint-cfl-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 - if: env.RELEVANT == 'true' with: go-version: '1.26' - uses: golangci/golangci-lint-action@v7 - if: env.RELEVANT == 'true' with: working-directory: tools/cfl version: v2.12.2 - lint-jtk: + lint-jtk-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: actions/setup-go@v5 - if: env.RELEVANT == 'true' with: go-version: '1.26' - uses: golangci/golangci-lint-action@v7 - if: env.RELEVANT == 'true' with: working-directory: tools/jtk version: v2.12.2 @@ -214,35 +180,23 @@ jobs: # packaging/identity.yml matches its tool-native files. working-directory is # the tool root; repo-root defaults to "." so the root-relative # goreleaser_config resolves (distribution.md §8.3 / .github#15). - identity-check-cfl: + identity-check-cfl-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.cfl == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: open-cli-collective/.github/actions/identity-check@v1 - if: env.RELEVANT == 'true' with: working-directory: tools/cfl - identity-check-jtk: + identity-check-jtk-run: needs: detect-changes - # Runs on every PR so the check reports a conclusion; branch - # protection requires it, and a skipped check never satisfies that. - # The work itself is gated per step (INT-726). - env: - RELEVANT: ${{ needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' }} + if: needs.detect-changes.outputs.jtk == 'true' || needs.detect-changes.outputs.shared == 'true' runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - if: env.RELEVANT == 'true' - uses: open-cli-collective/.github/actions/identity-check@v1 - if: env.RELEVANT == 'true' with: working-directory: tools/jtk @@ -253,3 +207,106 @@ jobs: - uses: open-cli-collective/.github/actions/pr-title@v1 with: title: ${{ github.event.pull_request.title }} + + # Required-check wrappers (INT-726). Branch protection requires these + # names, and GitHub does not accept a skipped check as satisfied, so a + # PR touching one tool could not merge without an admin bypass. Each + # wrapper always runs and reports the outcome of the job that does the + # work, treating "skipped" as a pass because there was nothing to do. + # The guard lives here alone, so steps added to the -run jobs need no + # per-step condition. + build-test-cfl: + needs: build-test-cfl-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report build-test-cfl-run outcome + env: + RESULT: ${{ needs.build-test-cfl-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac + + build-test-jtk: + needs: build-test-jtk-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report build-test-jtk-run outcome + env: + RESULT: ${{ needs.build-test-jtk-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac + + lint-cfl: + needs: lint-cfl-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report lint-cfl-run outcome + env: + RESULT: ${{ needs.lint-cfl-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac + + lint-jtk: + needs: lint-jtk-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report lint-jtk-run outcome + env: + RESULT: ${{ needs.lint-jtk-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac + + identity-check-cfl: + needs: identity-check-cfl-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report identity-check-cfl-run outcome + env: + RESULT: ${{ needs.identity-check-cfl-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac + + identity-check-jtk: + needs: identity-check-jtk-run + if: always() + runs-on: ubuntu-latest + steps: + - name: Report identity-check-jtk-run outcome + env: + RESULT: ${{ needs.identity-check-jtk-run.result }} + run: | + set -euo pipefail + case "$RESULT" in + success) echo "ran and passed" ;; + skipped) echo "no changes for this tool; nothing to verify" ;; + *) echo "job result: $RESULT"; exit 1 ;; + esac From 578f101d76a43ca5378acb76d4242d1857ab5c35 Mon Sep 17 00:00:00 2001 From: piekstra Date: Fri, 14 Aug 2026 07:19:07 -0400 Subject: [PATCH 3/3] ci: INT-726 fail required checks when change detection does not succeed Review round, and the first finding was a hole this change introduced. A -run job is skipped whenever its condition is false, and the condition reads detect-changes outputs. If detect-changes fails, those outputs are empty, every condition evaluates false, and all six jobs skip -- so a wrapper treating skipped as a pass reported every required check green with nothing verified at all. That is the failure this PR exists to prevent, reintroduced one level up. Wrappers now take detect-changes in needs and fail unless it succeeded, so a skip only passes when it genuinely means there was no work. The case statement was also repeated once per wrapper and would grow with each tool the repo adds. It moves into a local composite action, so a wrapper is now four lines and the logic exists once. The decision table is verified directly: success and skipped pass only when change detection succeeded; failure, cancellation, and any non-success gate all fail. [INT-726] --- .github/actions/required-check/action.yml | 47 +++++++++ .github/workflows/ci.yml | 122 +++++++++------------- 2 files changed, 97 insertions(+), 72 deletions(-) create mode 100644 .github/actions/required-check/action.yml diff --git a/.github/actions/required-check/action.yml b/.github/actions/required-check/action.yml new file mode 100644 index 00000000..f10359e7 --- /dev/null +++ b/.github/actions/required-check/action.yml @@ -0,0 +1,47 @@ +name: Required check +description: >- + Report a protected check from the job that did the work. Branch protection + does not accept a skipped check as satisfied, so a tool-scoped PR cannot + merge while the other tool's jobs skip. A wrapper using this action always + runs and passes on that job's behalf. + +inputs: + job: + description: Name of the job whose outcome is being reported. + required: true + result: + description: result of that job (needs..result). + required: true + gate-result: + description: >- + result of the job whose outputs decide whether the work runs. A skip is + only meaningful if this succeeded; when it did not, the work was skipped + for an unrelated reason and nothing was verified. + required: true + +runs: + using: composite + steps: + - shell: bash + env: + JOB: ${{ inputs.job }} + RESULT: ${{ inputs.result }} + GATE: ${{ inputs.gate-result }} + run: | + set -euo pipefail + if [ "$GATE" != "success" ]; then + echo "::error::change detection did not succeed (result: $GATE), so $JOB was skipped for an unrelated reason and nothing was verified" + exit 1 + fi + case "$RESULT" in + success) + echo "$JOB ran and passed" + ;; + skipped) + echo "$JOB had no relevant changes; nothing to verify" + ;; + *) + echo "::error::$JOB result: $RESULT" + exit 1 + ;; + esac diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index bdcd250e..519de37e 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -209,104 +209,82 @@ jobs: title: ${{ github.event.pull_request.title }} # Required-check wrappers (INT-726). Branch protection requires these - # names, and GitHub does not accept a skipped check as satisfied, so a - # PR touching one tool could not merge without an admin bypass. Each - # wrapper always runs and reports the outcome of the job that does the - # work, treating "skipped" as a pass because there was nothing to do. - # The guard lives here alone, so steps added to the -run jobs need no - # per-step condition. + # names, and GitHub does not accept a skipped check as satisfied, so a PR + # touching one tool could not merge without an admin bypass. Each wrapper + # always runs and reports on behalf of the job that does the work, so the + # -run jobs stay free of per-step guards. + # + # detect-changes is in needs so a skip can be told apart from a skip + # caused by change detection failing, which would otherwise pass every + # required check with nothing verified. build-test-cfl: - needs: build-test-cfl-run + needs: [detect-changes, build-test-cfl-run] if: always() runs-on: ubuntu-latest steps: - - name: Report build-test-cfl-run outcome - env: - RESULT: ${{ needs.build-test-cfl-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: build-test-cfl-run + result: ${{ needs.build-test-cfl-run.result }} + gate-result: ${{ needs.detect-changes.result }} build-test-jtk: - needs: build-test-jtk-run + needs: [detect-changes, build-test-jtk-run] if: always() runs-on: ubuntu-latest steps: - - name: Report build-test-jtk-run outcome - env: - RESULT: ${{ needs.build-test-jtk-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: build-test-jtk-run + result: ${{ needs.build-test-jtk-run.result }} + gate-result: ${{ needs.detect-changes.result }} lint-cfl: - needs: lint-cfl-run + needs: [detect-changes, lint-cfl-run] if: always() runs-on: ubuntu-latest steps: - - name: Report lint-cfl-run outcome - env: - RESULT: ${{ needs.lint-cfl-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: lint-cfl-run + result: ${{ needs.lint-cfl-run.result }} + gate-result: ${{ needs.detect-changes.result }} lint-jtk: - needs: lint-jtk-run + needs: [detect-changes, lint-jtk-run] if: always() runs-on: ubuntu-latest steps: - - name: Report lint-jtk-run outcome - env: - RESULT: ${{ needs.lint-jtk-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: lint-jtk-run + result: ${{ needs.lint-jtk-run.result }} + gate-result: ${{ needs.detect-changes.result }} identity-check-cfl: - needs: identity-check-cfl-run + needs: [detect-changes, identity-check-cfl-run] if: always() runs-on: ubuntu-latest steps: - - name: Report identity-check-cfl-run outcome - env: - RESULT: ${{ needs.identity-check-cfl-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: identity-check-cfl-run + result: ${{ needs.identity-check-cfl-run.result }} + gate-result: ${{ needs.detect-changes.result }} identity-check-jtk: - needs: identity-check-jtk-run + needs: [detect-changes, identity-check-jtk-run] if: always() runs-on: ubuntu-latest steps: - - name: Report identity-check-jtk-run outcome - env: - RESULT: ${{ needs.identity-check-jtk-run.result }} - run: | - set -euo pipefail - case "$RESULT" in - success) echo "ran and passed" ;; - skipped) echo "no changes for this tool; nothing to verify" ;; - *) echo "job result: $RESULT"; exit 1 ;; - esac + - uses: actions/checkout@v4 + - uses: ./.github/actions/required-check + with: + job: identity-check-jtk-run + result: ${{ needs.identity-check-jtk-run.result }} + gate-result: ${{ needs.detect-changes.result }}