mirror of
https://github.com/max-sixty/worktrunk.git
synced 2026-09-14 20:00:38 +08:00
126f022416
## Summary `windows-2022` was deliberately held back, and the reason recorded in `ci.yaml`'s header no longer holds. The comment reads "Pinned because windows-2025 lacks D: drive" — but GitHub reversed that removal: [actions/runner-images#12744](https://github.com/actions/runner-images/issues/12744) announced that from 2025-08-18 the Windows Server 2025 image again exposes a `D:\` drive, with the working directory back on `D:\`, explicitly reversing [#12416](https://github.com/actions/runner-images/issues/12416). `windows-2022` has also fallen off the `windows-latest` label, so the pin is due on the ordinary weekly rule too. This moves the four `windows-2022` matrix entries to `windows-2025` and rewrites the header comment, which no longer needs a hold-back line. Split from the week's other pin bumps ([#3971](https://github.com/max-sixty/worktrunk/pull/3971)) so a red Windows matrix decides only this bump. The `D:\` drive is what prompted the change because the workflows use it: `ci.yaml`, `affected.yaml`, and `nightly.yaml` each run a `Use fast D: drive for temp files (Windows)` step that creates `D:\tmp` and points `TEMP`/`TMP` at it. Those steps are unchanged and keep working, since #12744 restored exactly that drive. ## The label also swaps the MSVC toolset `D:\` is not the only variable this bump moves. `windows-2025` is no longer the Visual Studio 2022 image: [actions/runner-images#14017](https://github.com/actions/runner-images/issues/14017) moved `windows-latest` and `windows-2025` onto the Windows Server 2025 + VS 2026 image in June 2026. The availability table now carries a single Windows Server 2025 row whose three labels — `windows-latest`, `windows-2025`, `windows-2025-vs2026` — all resolve to `Windows2025-VS2026-Readme.md`. So CI's Windows legs compile with the VS 2026 toolset after this PR. The second-order effect is that CI and the release build no longer share a toolset. `dist` computes the release matrix itself and is untouched here: v0.69.2 built `x86_64-pc-windows-msvc` on `build-local-artifacts (windows-2022, …)`, and `windows-2022` is not deprecated, so `dist` keeps picking it. Nothing now exercises the toolset the shipped binary is compiled and linked with. That is a real gap, but a low-risk one and a separate decision from this bump — nothing in the tree pins a VS path (`build.rs` is vergen-only; the `cc` / `find-msvc-tools` route discovers VS through vswhere), and `affected tests (windows, advisory)` is green on this head. Aligning the release runner is a release-matrix change that belongs in its own PR. ## Verification This PR's own `test (windows)`, `full-tests (windows-2025, windows)`, and `affected tests (windows, advisory)` legs are the only place this gets tested — the weekly runner is Linux. Two failure shapes to look for if Windows goes red, not one: - **`D:`-shaped** — the `D:\tmp` step fails to create the directory, meaning #12744's restoration doesn't apply to this repo's runners and the pin should go back. - **Toolset-shaped** — a compile or link failure from the VS 2026 move. [#14004](https://github.com/actions/runner-images/issues/14004) is an open report of this same label swap breaking hardcoded VS 2022 paths; nothing here hardcodes one, but a future Windows-only break is as likely to be this shape as the first. The throughput question this description originally left open is answered: no measurable regression. Every Windows leg here lands inside the same-day `windows-2022` spread from the sibling pin PRs, and the advisory leg is the fastest of the five — durations are tabulated in [the first review](https://github.com/max-sixty/worktrunk/pull/3974#pullrequestreview-5064565794). The remaining bias runs against this PR, not for it: `save-if` gates the rust-cache write to `main`, so this run restored a cache written on `windows-2022`. [#12647](https://github.com/actions/runner-images/issues/12647)'s reported slowdown does not reproduce here. `ci.yaml`'s header comment now keeps each pin on its own line, so this PR's edit and [#3973](https://github.com/max-sixty/worktrunk/pull/3973)'s `macos-15` → `macos-26` edit stay on separate lines. They are still adjacent lines, so whichever lands second needs a one-hunk resolution keeping both — details in [this comment](https://github.com/max-sixty/worktrunk/pull/3974#issuecomment-5476167137). The three matrix files auto-merge clean. <details><summary>Availability table rows this reads from</summary> From `actions/runner-images` `README.md`: - Windows Server 2025 — `windows-latest`, `windows-2025`, `windows-2025-vs2026`; Included Software links `images/windows/Windows2025-VS2026-Readme.md` - Windows Server 2022 — `windows-2022` (no `-latest`), linking `images/windows/Windows2022-Readme.md` `windows-2022` is not badged `deprecated` yet, but it is now the older of the two GA images, which the weekly rule treats as next due. That it is undeprecated is also why `dist` still selects it for the release build. </details> --------- Co-authored-by: worktrunk-bot <254187624+worktrunk-bot@users.noreply.github.com>
234 lines
7.7 KiB
YAML
234 lines
7.7 KiB
YAML
name: ci
|
|
|
|
# Runner versions are pinned to avoid surprise breaking changes from -latest migrations.
|
|
# The tend-weekly workflow checks for updates and opens bump PRs (see
|
|
# .claude/skills/running-tend/SKILL.md → "Weekly Maintenance: CI Pin Bumps").
|
|
# - windows-2025: Pinned to current -latest equivalent
|
|
# - ubuntu-24.04, macos-26: Pinned to current -latest equivalents
|
|
|
|
on:
|
|
push:
|
|
branches: [ main ]
|
|
pull_request:
|
|
branches: [ main ]
|
|
workflow_dispatch:
|
|
|
|
concurrency:
|
|
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
|
cancel-in-progress: ${{ github.event_name == 'pull_request' }}
|
|
|
|
env:
|
|
CARGO_TERM_COLOR: always
|
|
# CI does clean builds, so incremental compilation tracking adds I/O overhead
|
|
# with no benefit. Especially impactful on Windows where I/O is the bottleneck.
|
|
CARGO_INCREMENTAL: 0
|
|
RUSTFLAGS: -C debuginfo=0
|
|
|
|
jobs:
|
|
lint:
|
|
runs-on: ubuntu-24.04
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- name: 💰 Cache
|
|
uses: Swatinem/rust-cache@v2
|
|
with:
|
|
# Own cache (clippy builds check artifacts the shared test cache can't
|
|
# supply), gated to main so PRs restore but never write.
|
|
cache-bin: "false"
|
|
save-if: ${{ github.ref == 'refs/heads/main' }}
|
|
|
|
- name: 🔍 Pre-commit hooks
|
|
uses: pre-commit/action@v3.0.1
|
|
|
|
feature-check:
|
|
# Guards the library/CLI cleave: the `cli` feature gates clap, skim,
|
|
# crossterm, termimad, env_logger, humantime. If anything reachable from
|
|
# `pub mod` in src/lib.rs starts using one of those crates, library
|
|
# consumers (e.g. worktrunk-sync) would silently regain the transitive
|
|
# dependency graph. These checks fail before that can ship.
|
|
runs-on: ubuntu-24.04
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- name: 💰 Cache
|
|
uses: Swatinem/rust-cache@v2
|
|
with:
|
|
# Own cache (its `--no-default-features` builds want a smaller dep set
|
|
# than the shared test cache), gated to main.
|
|
cache-bin: "false"
|
|
save-if: ${{ github.ref == 'refs/heads/main' }}
|
|
|
|
- name: Library builds without any features
|
|
run: cargo check --lib --no-default-features
|
|
|
|
- name: Library builds with syntax-highlighting only
|
|
run: cargo check --lib --no-default-features --features syntax-highlighting
|
|
|
|
- name: Binary builds without syntax-highlighting
|
|
run: cargo check --bin wt --no-default-features --features cli
|
|
|
|
test:
|
|
strategy:
|
|
fail-fast: false
|
|
matrix:
|
|
include:
|
|
- os: ubuntu-24.04
|
|
name: linux
|
|
- os: macos-26
|
|
name: macos
|
|
- os: windows-2025
|
|
name: windows
|
|
name: test (${{ matrix.name }})
|
|
runs-on: ${{ matrix.os }}
|
|
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- uses: ./.github/actions/test-setup
|
|
|
|
- name: Install wt
|
|
uses: baptiste0928/cargo-install@v3
|
|
with:
|
|
crate: worktrunk
|
|
version: "=0.75.0"
|
|
|
|
- name: "Use fast D: drive for temp files (Windows)"
|
|
if: runner.os == 'Windows'
|
|
shell: pwsh
|
|
run: |
|
|
New-Item -ItemType Directory -Force -Path "D:\tmp" | Out-Null
|
|
echo "TEMP=D:\tmp" >> $env:GITHUB_ENV
|
|
echo "TMP=D:\tmp" >> $env:GITHUB_ENV
|
|
|
|
# The full nextest suite (snapshots included) — CI's long-pole. The fast
|
|
# pre-merge gates (lockfile/doctest/rustdoc) live in the `fast-checks` job,
|
|
# so this job is now just the suite and can later be swapped for the
|
|
# cargo-affected legs on PRs without disturbing those gates. The `insta`
|
|
# step runs `--unreferenced reject` on Linux (orphan-snapshot detection) —
|
|
# an intrinsically full-suite check that rides this job on push-to-main and,
|
|
# after the flip, stays there.
|
|
- name: 🧪 Full test suite
|
|
run: wt hook pre-merge --yes insta
|
|
|
|
# Anything tests leave behind in the working tree is a leak we want to see
|
|
# before it lands. `target/` is gitignored, so a normal run is clean —
|
|
# untracked files here mean a test wrote outside its sandbox (the
|
|
# `default_*.profraw` stray that prompted this guard is the canonical case).
|
|
- name: 🧹 Verify clean working tree
|
|
shell: bash
|
|
run: |
|
|
if [ -n "$(git status --porcelain)" ]; then
|
|
echo "::error::tests left files behind in the working tree:"
|
|
git status --porcelain
|
|
exit 1
|
|
fi
|
|
|
|
- name: 📊 Upload test timing
|
|
if: always()
|
|
uses: actions/upload-artifact@v7
|
|
with:
|
|
name: junit-${{ matrix.name }}
|
|
path: target/nextest/default/junit.xml
|
|
|
|
- name: 📊 Upload test results to Codecov
|
|
if: ${{ !cancelled() }}
|
|
uses: codecov/codecov-action@v7.0.0
|
|
with:
|
|
token: ${{ secrets.CODECOV_TOKEN }}
|
|
files: target/nextest/default/junit.xml
|
|
report_type: test_results
|
|
|
|
# The pre-merge gates that aren't the nextest suite: Cargo.lock freshness,
|
|
# doctests, and the rustdoc `-Dwarnings` build. Split out of `test` so the
|
|
# full suite (the long-pole) can later be replaced on PRs by the
|
|
# cargo-affected legs without dropping these — they stay required and
|
|
# untouched by that flip. Linux-only: all three are platform-independent. The
|
|
# one blind spot is doc/doctest inside `#[cfg(windows)]` / `#[cfg(target_os
|
|
# = …)]` code, which only the full `test` matrix compiles; acceptable for a
|
|
# gate whose job is broken links and stale locks, not platform behavior.
|
|
fast-checks:
|
|
runs-on: ubuntu-24.04
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- uses: ./.github/actions/test-setup
|
|
|
|
- name: Install wt
|
|
uses: baptiste0928/cargo-install@v3
|
|
with:
|
|
crate: worktrunk
|
|
version: "=0.75.0"
|
|
|
|
- name: 🧪 Lockfile, doctests, rustdoc
|
|
run: wt hook pre-merge --yes lockfile doctest doc
|
|
|
|
# Check if Cargo/CI files changed (for conditional jobs below)
|
|
changes:
|
|
runs-on: ubuntu-24.04
|
|
permissions:
|
|
contents: read
|
|
pull-requests: read
|
|
outputs:
|
|
cargo: ${{ steps.filter.outputs.cargo }}
|
|
docs: ${{ steps.filter.outputs.docs }}
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
- uses: dorny/paths-filter@v4
|
|
id: filter
|
|
with:
|
|
filters: |
|
|
cargo:
|
|
- 'Cargo.toml'
|
|
- 'Cargo.lock'
|
|
- 'rust-toolchain.toml'
|
|
- '.github/workflows/ci.yaml'
|
|
docs:
|
|
- 'docs/**'
|
|
- 'src/cli/mod.rs'
|
|
- '.github/actions/docs-build/**'
|
|
- '.github/workflows/ci.yaml'
|
|
- '.github/workflows/nightly.yaml'
|
|
- '.github/workflows/publish-docs.yaml'
|
|
|
|
msrv:
|
|
runs-on: ubuntu-24.04
|
|
needs: changes
|
|
if: needs.changes.outputs.cargo == 'true' || github.event_name == 'workflow_dispatch'
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- name: 💰 Cache
|
|
uses: Swatinem/rust-cache@v2
|
|
with:
|
|
# Own cache — `cargo msrv verify` builds with older toolchains whose
|
|
# rustc hash never matches the shared (stable) test cache. Gated to
|
|
# main; this job only runs when Cargo/toolchain files change.
|
|
cache-bin: "false"
|
|
save-if: ${{ github.ref == 'refs/heads/main' }}
|
|
|
|
- uses: baptiste0928/cargo-install@v3
|
|
with:
|
|
crate: cargo-msrv
|
|
version: "=0.19.3"
|
|
|
|
- name: Verify minimum rust version
|
|
run: cargo msrv verify
|
|
|
|
check-docs:
|
|
runs-on: ubuntu-24.04
|
|
needs: changes
|
|
if: needs.changes.outputs.docs == 'true' || github.event_name == 'workflow_dispatch'
|
|
steps:
|
|
- name: 📂 Checkout code
|
|
uses: actions/checkout@v7
|
|
|
|
- name: 🕷️ Check and build docs
|
|
uses: ./.github/actions/docs-build
|