Skip to content

v0.109.0

Choose a tag to compare

@smm-h smm-h released this 19 Jul 17:46
· 3779 commits to main since this release

Structured external checks, declarative dead-module exclusions, check-name --json, launcher shim generation, and deterministic check verdicts

Context

Check verdicts no longer depend on which tools a machine has installed: missing tools now hard-fail instead of silently skipping, both in checks and in release test runners.
external_checks gained an explicit structured/freeform schema with rlsbl-composed argv and competing-scope guards (breaking: the kind key is now required).
dead-modules gained a reason-gated committed exclusion list.
check-name gained --json plus a fix making multi-target checks actually check every target.
The launcher pipeline kind is now end-to-end functional with checksum-verified download shims.
rename-releasable crash recovery and batch-archival guards were hardened, and the release preflight now prints a positive success summary.

Breaking

  • Structured external checks. external_checks entries now require an explicit kind marker (structured or freeform); missing/unknown kind and unknown keys are hard errors. Structured entries (mypy, ruff-check, ruff-format) run via rlsbl-composed, shell-free uv run argv, honor the configured check timeout, and emit a competing-scope guard that rejects tool config which would silently override or narrow the declared paths.

Features

  • Releases now confirm which preflight checks passed. The release log prints a positive summary ("Preflight: N checks passed (...)") for every check that ran, including config-declared external checks, so a green preflight is visible rather than silent.
  • Launcher packages now ship working download logic. npm and PyPI artifact: "launcher" pipelines generate platform-aware shims that download the wrapped binary from its GitHub Release, SHA-256-verify it against the release's checksums.txt before installing, and fail loudly on tampering or a missing asset. Scaffold fills the launcher manifest's non-name fields once (never inventing the package name), and a publish workflow verify step probes both the binary asset and checksums.txt so goreleaser naming drift becomes a red CI job instead of broken installs.
  • Declarative dead-module exclusions. Files that are legitimately unreachable by design (demo apps, tool configs) can be listed in .rlsbl/dead-modules.toml with a mandatory reason; entries never act as entry points (no laundering), and stale entries hard-fail a new dead-modules-stale check.

Fixes

  • rename-releasable crash recovery. A crash mid-rename no longer lets a re-run push the alias tag over an uncommitted rename with a stale publish gate; re-runs now heal completely. The command also asks for confirmation before pushing (bypass with --yes) and no longer demands gh auth for renames that create no tag.
  • Batch release safety. A failed push no longer lets the batch repair pass archive the batch as complete on local-only tag evidence; a batch with an unfinished (in-progress) release is left intact for resume or rollback.
  • Checks no longer lie on misconfigured machines. github-release, workspace-unbuildable, and ruff-lint now hard-fail when their tool is missing (or gh is unauthenticated) instead of silently skipping; ruff-lint reports exact violation counts (was ~10x inflated line counts) and enforces a minimum ruff version.
  • Releases no longer silently skip tests. When a required test tool (uv, pytest, npm, mvn) is missing, or a package.json/pom.xml manifest is corrupt or absent for a declared target, the test step now hard-fails instead of passing silently.
  • rlsbl check-name --target npm --target pypi now checks every target, not just the first. Multi-target name checks previously stopped after the first registry.