Skip to content

Latest commit

 

History

History
123 lines (87 loc) · 5.02 KB

File metadata and controls

123 lines (87 loc) · 5.02 KB

Release Policy

Arco ships as one product snapshot with one shared semantic version.

Every release version is shared across:

  • Cargo.toml workspace version
  • bindings/python/pyproject.toml project version
  • bindings/python/uv.lock package entry for arco
  • GitHub tag (vX.Y.Z)
  • GitHub Release

Goals

  • Keep release identity simple, one product version everywhere.
  • Build once, publish the exact built artifacts.
  • Keep release automation retryable and safe when failures happen.
  • Ship everything together or nothing: GitHub Release and PyPI publish atomically.

Release Ownership

  • release-please owns changelog generation, version bump PRs (across Cargo.toml, pyproject.toml, and uv.lock), tag creation, and draft GitHub Release creation (bookkeeping only — invisible to users).
  • cargo-dist owns cross-platform CLI binaries, installers, checksums, dist manifests, and publishing the GitHub Release (uploads artifacts to the draft and undrafts it).
  • ci.yaml owns pre-merge validation: version consistency checks, code quality, and tests. cargo-dist also validates artifact builds on PRs via pr-run-mode.

Workflow Topology

Workflow Trigger Purpose
release-please.yaml push to main Maintains release PRs, creates tag + draft release, dispatches cargo-dist-release.yml, then builds and publishes Python package to PyPI
cargo-dist-release.yml workflow_dispatch from release-please.yaml (with tag) or pull_request (dry-run) Builds CLI artifacts via cargo-dist, uploads them to the draft release, and publishes it

Reusable workflow call

release-please.yaml calls cargo-dist-release.yml as a reusable workflow (workflow_call) because tags created with GITHUB_TOKEN do not trigger tag workflows. The call passes the release tag as an input and GitHub Actions natively waits for the called workflow to complete.

cargo-dist-release.yml job graph

cargo-dist-release.yml is generated by cargo-dist. When called with a tag (publishing mode), it runs these jobs in order:

plan
  -> build-local-artifacts (matrix across target platforms)
  -> build-global-artifacts (installers, checksums)
  -> host (upload artifacts to draft + undraft with gh release edit)
  -> announce

On pull_request triggers the workflow runs in dry-run mode: it plans and builds artifacts but does not upload or create a release.

Release atomicity

The py-build and publish-pypi jobs in release-please.yaml depend on the cargo-dist job. This ensures the Python package is only published to PyPI after cargo-dist has successfully published the GitHub Release. If cargo-dist fails, nothing is published.

Release Notes

release-please is the source of truth for release notes and changelog content. Changelog sections are configured in .release-please-config.json.

Failure Handling

On any failure in cargo-dist-release.yml:

  • The GitHub Release stays as a draft (invisible to users).
  • Workflow artifacts are preserved for inspection and retries.
  • No downstream jobs run after the failed step.
  • Python package is not published to PyPI.

Retries rerun the workflow dispatch with the same tag. gh release upload --clobber ensures artifact uploads are idempotent.

Maintenance Notes

cargo-dist-release.yml is auto-generated by cargo dist init. After regeneration, manually re-apply:

  1. The workflow_call trigger with inputs.tag (required for reusable workflow call from release-please.yaml).
  2. The timeout-minutes values on all jobs.
  3. The paths filter on the pull_request trigger.
  4. The host job patch: replace gh release create with gh release upload + gh release edit --draft=false. Look for the # MODIFIED: comment.

Future First-Party Bindings

New first-party bindings should join the shared product version stream unless explicitly declared as a separate product line.

If they join the stream, their build and publish steps should be added to the release workflow before the release is made public.

Commit Conventions

  • Use Conventional Commits (feat:, fix:, perf:, refactor:, docs:, build:, ci:).
  • Non-conventional commits may be omitted or misclassified in release notes.

Forcing A Release Version

Use Release-As only when an explicit one-off version override is necessary:

chore(release): force 0.3.0

Release-As: 0.3.0

Close stale release PRs and remove stale draft releases for old forced tags before rerunning automation.