Skip to content

fix(ci): plumb expected version through env so smoke-windows passes reliably#160

Merged
thiagoralves merged 1 commit into
developmentfrom
fix/smoke-test-expected-version
Jun 2, 2026
Merged

fix(ci): plumb expected version through env so smoke-windows passes reliably#160
thiagoralves merged 1 commit into
developmentfrom
fix/smoke-test-expected-version

Conversation

@thiagoralves
Copy link
Copy Markdown
Contributor

Summary

The smoke-test reads its expected version from package.json on disk. This works in the build-* jobs (the Inject version step bumps package.json on the same runner before smoke runs) but breaks in smoke-windows: that job is on a separate Windows runner because the Windows binary is cross-built on Linux and can't execute there. It does a fresh actions/checkout@v4 at the tag ref with no Inject version step, so its package.json still holds whatever was committed at the tagged commit. If the tag's commit didn't pre-bump package.json (no chore(release): vX.Y.Z PR), the binary correctly reports the injected version while smoke-windows compares against the stale committed string and fails.

This is exactly what happened on the first attempt at v0.5.1 — binary reported 0.5.1, package.json on Windows runner still said 0.5.0, smoke failed, release aborted.

Fix

  • scripts/smoke-test.mjs — prefer STRUCPP_EXPECTED_VERSION env var over the package.json fallback. Logs which source the version came from for traceability.
  • .github/workflows/release.yml — every smoke step exports STRUCPP_EXPECTED_VERSION: ${{ needs.prepare.outputs.version }}. The prepare job derives this value once from github.ref_name (stripping v), so it's the same source of truth all build jobs feed into npm version. smoke-windows now also lists prepare in its needs: array to access the output.

The Inject version steps in the build jobs stay — they're still load-bearing for baking the version into the bundle/binary itself. They're just no longer the only way smoke-test learns what version to expect.

Validation plan

Once merged to development and main, v0.5.2 will be tagged WITHOUT a preceding chore(release): v0.5.2 bump. That's the explicit test: with package.json still saying 0.5.1 at the tag commit, the build jobs will inject 0.5.2 into their package.json copies and bake 0.5.2 into the binary, and smoke-windows will compare its fresh-checkout binary against STRUCPP_EXPECTED_VERSION=0.5.2 rather than the stale 0.5.1 from disk. If that passes, the fix is verified end-to-end.

Side benefit

The assertion now actually tests what it claims to test ("the binary reports the version we asked the pipeline to build"), not "the binary version matches whatever npm version happened to mutate package.json to in the same runner" (which was a tautology in every build-job smoke step).

Test plan

  • Local sanity: env override path passes; package.json fallback correctly fails when binary disagrees.
  • Local CI-equivalent: lint (0 errors), prettier, typecheck, 1913/1920 tests pass (7 pre-existing skips).
  • CI on this PR green.
  • After merge: v0.5.2 release runs end-to-end without a chore(release) bump — proves the fix.

🤖 Generated with Claude Code

Smoke-test was reading expected version from package.json on disk.
Worked in build-* jobs because their `Inject version` step bumps
package.json in the same runner before smoke runs.  Broke in
smoke-windows: that job is on a separate Windows runner (the .exe is
cross-built on Linux and can't execute there), does a fresh
actions/checkout at the tag ref, and has no `Inject version` step —
so package.json on its disk still holds whatever value was committed
at the tagged commit.  When the tag's commit didn't pre-bump
package.json (no chore(release): vX.Y.Z), the binary reported the
injected version while smoke-windows compared against the stale
committed string and failed.

Fix: have smoke-test prefer `STRUCPP_EXPECTED_VERSION` env var over
the package.json fallback, and have every smoke step in release.yml
export `${{ needs.prepare.outputs.version }}` into that env.  The
prepare job derives the version from `github.ref_name` (stripping
the leading `v`), so it's the same source of truth all build jobs
feed into `npm version`.  smoke-windows now also lists `prepare` in
its `needs:` array to access that output.

Side benefit: the assertion now actually tests what it claims to
test ("the binary reports the version we asked the pipeline to
build"), not "the binary version matches whatever npm version
happened to mutate package.json to" (which was a tautology in every
build-job smoke step).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@thiagoralves thiagoralves merged commit 7226bf1 into development Jun 2, 2026
@thiagoralves thiagoralves deleted the fix/smoke-test-expected-version branch June 2, 2026 18:08
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant