From 140852918920023252c06264d45678fc8c5e1433 Mon Sep 17 00:00:00 2001 From: Lorenz Junglas <4759511+lolleko@users.noreply.github.com> Date: Mon, 1 Dec 2025 11:43:11 +0100 Subject: [PATCH] PR triage requires checks to pass (#3503) * Add formatting workflow to git filter-repo path rename * Verify checks pass before triaging --- .github/workflows/pull_request.yml | 58 +++++++++++++++++-- .github/workflows/pull_request_checks.yml | 2 +- .../workflows/pull_request_formatting.yml | 0 .../Tools/SboxBuild/Steps/SyncPublicRepo.cs | 1 + 4 files changed, 54 insertions(+), 7 deletions(-) rename public/.github/workflows/formatting.yml => .github/workflows/pull_request_formatting.yml (100%) diff --git a/.github/workflows/pull_request.yml b/.github/workflows/pull_request.yml index 5e14a489..a8606a25 100644 --- a/.github/workflows/pull_request.yml +++ b/.github/workflows/pull_request.yml @@ -8,10 +8,56 @@ jobs: runs-on: ubuntu-latest if: github.event.label.name == 'triaged' steps: - - name: Repository Dispatch - uses: peter-evans/repository-dispatch@v4 + - name: Ensure PR checks passed + uses: actions/github-script@v7 with: - token: ${{ secrets.SBOXBOT_TOKEN }} - repository: Facepunch/sbox - event-type: pr-triaged - client-payload: '{"github": ${{ toJson(github) }}}' + github-token: ${{ secrets.GITHUB_TOKEN }} + script: | + const requiredChecks = ['Tests', 'Formatting']; + + const pr = context.payload.pull_request; + if (!pr) { + throw new Error('No pull request found in event payload.'); + } + + const { data } = await github.rest.checks.listForRef({ + owner: context.repo.owner, + repo: context.repo.repo, + ref: pr.head.sha, + per_page: 100 + }); + + const checkRuns = data.check_runs ?? []; + for (const requiredCheck of requiredChecks) { + const match = checkRuns.find(run => (run.name ?? '') === requiredCheck); + + if (!match || match.conclusion !== 'success') { + const status = match ? (match.conclusion ?? match.status ?? 'unknown') : 'missing'; + core.warning(`Required check '${requiredCheck}' did not pass (${status}). Removing triaged label.`); + + await github.rest.issues.removeLabel({ + owner: context.repo.owner, + repo: context.repo.repo, + issue_number: pr.number, + name: 'triaged' + }); + + throw new Error('Cannot triage until required checks succeed.'); + } + } + + - name: Repository Dispatch + uses: actions/github-script@v7 + env: + DISPATCH_CONTEXT: ${{ toJson(github) }} + with: + github-token: ${{ secrets.SBOXBOT_TOKEN }} + script: | + const clientPayload = JSON.parse(process.env.DISPATCH_CONTEXT); + + await github.rest.repos.createDispatchEvent({ + owner: 'Facepunch', + repo: 'sbox', + event_type: 'pr-triaged', + client_payload: { github: clientPayload } + }); diff --git a/.github/workflows/pull_request_checks.yml b/.github/workflows/pull_request_checks.yml index 5dfc9539..ff71a49c 100644 --- a/.github/workflows/pull_request_checks.yml +++ b/.github/workflows/pull_request_checks.yml @@ -1,4 +1,4 @@ -name: Pull Request Checks +name: Tests on: pull_request: diff --git a/public/.github/workflows/formatting.yml b/.github/workflows/pull_request_formatting.yml similarity index 100% rename from public/.github/workflows/formatting.yml rename to .github/workflows/pull_request_formatting.yml diff --git a/engine/Tools/SboxBuild/Steps/SyncPublicRepo.cs b/engine/Tools/SboxBuild/Steps/SyncPublicRepo.cs index 48cd630d..94064afe 100644 --- a/engine/Tools/SboxBuild/Steps/SyncPublicRepo.cs +++ b/engine/Tools/SboxBuild/Steps/SyncPublicRepo.cs @@ -95,6 +95,7 @@ internal class SyncPublicRepo( string name, bool dryRun = false ) : Step( name ) { "public/.gitattributes", ".gitattributes" }, { "public/.github/workflows/pull_request.yml", ".github/workflows/pull_request.yml" }, { "public/.github/workflows/pull_request_checks.yml", ".github/workflows/pull_request_checks.yml" }, + { "public/.github/workflows/pull_request_formatting.yml", ".github/workflows/pull_request_formatting.yml" }, { "public/README.md", "README.md" }, { "public/LICENSE.md", "LICENSE.md" }, { "public/CONTRIBUTING.md", "CONTRIBUTING.md" },