From 333803ed04efe657f9117b5018e8e952dd54fd0d Mon Sep 17 00:00:00 2001 From: Michael Bolin Date: Thu, 14 Aug 2025 17:00:19 -0700 Subject: [PATCH] fix: ensure rust-ci always "runs" when a PR is submitted (#2324) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Our existing path filters for `rust-ci.yml`: https://github.com/openai/codex/blob/235987843c3d6647c0819c1071f9b9f064673e9c/.github/workflows/rust-ci.yml#L1-L11 made it so that PRs that touch only `README.md` would not trigger those builds, which is a problem because our branch protection rules are set as follows: Screenshot 2025-08-14 at 4 45
59 PM With the existing setup, a change to `README.md` would get stuck in limbo because not all the CI jobs required to merge would get run. It turns out that we need to "run" all the jobs, but make them no-ops when the `codex-rs` and `.github` folders are untouched to get the best of both worlds. I asked chat how to fix this, as we want CI to be fast for documentation-only changes. It had two suggestions: - Use https://github.com/dorny/paths-filter or some other third-party action. - Write an inline Bash script to avoid a third-party dependency. This PR takes the latter approach so that we are clear about what we're running in CI. --- .github/workflows/rust-ci.yml | 63 ++++++++++++++++++++++++++--------- 1 file changed, 48 insertions(+), 15 deletions(-) diff --git a/.github/workflows/rust-ci.yml b/.github/workflows/rust-ci.yml index 735a187a..1861233a 100644 --- a/.github/workflows/rust-ci.yml +++ b/.github/workflows/rust-ci.yml @@ -1,29 +1,60 @@ name: rust-ci on: - pull_request: - branches: - - main - paths: - - "codex-rs/**" - - ".github/**" + pull_request: {} push: branches: - main - workflow_dispatch: -# For CI, we build in debug (`--profile dev`) rather than release mode so we -# get signal faster. +# CI builds in debug (dev) for faster signal. jobs: - # CI that don't need specific targets + # --- Detect what changed (always runs) ------------------------------------- + changed: + name: Detect changed areas + runs-on: ubuntu-24.04 + outputs: + codex: ${{ steps.detect.outputs.codex }} + workflows: ${{ steps.detect.outputs.workflows }} + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Detect changed paths (no external action) + id: detect + shell: bash + run: | + set -euo pipefail + + if [[ "${{ github.event_name }}" == "pull_request" ]]; then + BASE_SHA='${{ github.event.pull_request.base.sha }}' + echo "Base SHA: $BASE_SHA" + # List files changed between base and current HEAD (merge-base aware) + mapfile -t files < <(git diff --name-only --no-renames "$BASE_SHA"...HEAD) + else + # On push / manual runs, default to running everything + files=("codex-rs/force" ".github/force") + fi + + codex=false + workflows=false + for f in "${files[@]}"; do + [[ $f == codex-rs/* ]] && codex=true + [[ $f == .github/* ]] && workflows=true + done + + echo "codex=$codex" >> "$GITHUB_OUTPUT" + echo "workflows=$workflows" >> "$GITHUB_OUTPUT" + + # --- CI that doesn't need specific targets --------------------------------- general: name: Format / etc runs-on: ubuntu-24.04 + needs: changed + if: ${{ needs.changed.outputs.codex == 'true' || needs.changed.outputs.workflows == 'true' || github.event_name == 'push' }} defaults: run: working-directory: codex-rs - steps: - uses: actions/checkout@v4 - uses: dtolnay/rust-toolchain@1.88 @@ -32,11 +63,13 @@ jobs: - name: cargo fmt run: cargo fmt -- --config imports_granularity=Item --check - # CI to validate on different os/targets + # --- CI to validate on different os/targets -------------------------------- lint_build_test: name: ${{ matrix.runner }} - ${{ matrix.target }}${{ matrix.profile == 'release' && ' (release)' || '' }} runs-on: ${{ matrix.runner }} timeout-minutes: 30 + needs: changed + if: ${{ needs.changed.outputs.codex == 'true' || needs.changed.outputs.workflows == 'true' || github.event_name == 'push' }} defaults: run: working-directory: codex-rs @@ -44,8 +77,6 @@ jobs: strategy: fail-fast: false matrix: - # Note: While Codex CLI does not support Windows today, we include - # Windows in CI to ensure the code at least builds there. include: - runner: macos-14 target: aarch64-apple-darwin @@ -113,7 +144,9 @@ jobs: id: build if: ${{ matrix.target == 'x86_64-unknown-linux-gnu' && matrix.profile != 'release' }} continue-on-error: true - run: find . -name Cargo.toml -mindepth 2 -maxdepth 2 -print0 | xargs -0 -n1 -I{} bash -c 'cd "$(dirname "{}")" && cargo build --profile ${{ matrix.profile }}' + run: | + find . -name Cargo.toml -mindepth 2 -maxdepth 2 -print0 \ + | xargs -0 -n1 -I{} bash -c 'cd "$(dirname "{}")" && cargo build --profile ${{ matrix.profile }}' - name: cargo test id: test