Skip to content

Preview Publish Workflow

The preview-publish workflow lets a ux-prototype developer ship a real, installable build of an in-progress branch to GitHub Packages. Consumers can then npm install that preview, validate against it, and feed bugs/feedback back to the design-system PR before it merges.

  • A design-system change needs consumer validation before it lands on main.
  • You want CI fidelity: the consumer tests against the actual published artifact (no symlinks, no local builds).
  • The change isn’t tightly coupled enough to justify coordinated multi-PR (i.e. the consumer doesn’t need to gate the design-system PR on its own CI passing).
  1. Branch off main: git checkout -b <username>/<description>.
  2. Implement the change.
  3. Add a pre-release CHANGELOG entry: ## [x.y.z-<author>-<id>] - YYYY-MM-DD under the appropriate category. Examples:
    • 4.12.0-alice-FD42 — Alice’s work on ticket FD-42, targeting eventual stable 4.12.0.
    • 4.12.0-bob-spike-grid-virt — Bob’s spike for grid virtualization, no formal ticket.
    • The <author> and <id> together form the dist-tag consumers will install by; pick something the consumer will recognize.
  4. Push. The publish-preview.yml workflow:
    • Detects that CHANGELOG.md was modified.
    • Validates the entry is a CLQ pre-release.
    • Derives dist-tag = everything after the first -. For 4.12.0-alice-FD42, the dist-tag is alice-FD42.
    • Appends github.run_number for uniqueness. Final published version: 4.12.0-alice-FD42-7.
    • Publishes to GitHub Packages with npm publish --tag alice-FD42 (so latest is never disturbed).
  5. Iterate. Each push that modifies CHANGELOG.md publishes a new preview; the alice-FD42 dist-tag advances to point at the newest. Concurrency is keyed by branch with cancel-in-progress: true, so out-of-order pushes can’t leave the dist-tag pointing at older code.
  6. Open a PR to main (still with the pre-release entry). The validate-release job will fail on this PR — that’s expected; it blocks accidental merge of a preview as stable.
  7. Before merging, swap the changelog entry to a stable x.y.z. validate-release then passes; publish-preview.yml correctly skips the publish (status no longer prereleased); on merge, publish.yml ships the stable version.
  1. Configure auth if not already done — see auth-and-tokens.
  2. Install the preview:
    Terminal window
    npm install @arda-cards/design-system@alice-FD42
    This installs whatever version the dist-tag currently points at and pins it in package.json / package-lock.json.
  3. Validate locally and via your normal CI.
  4. Iterate: when Alice pushes new preview commits, re-run the same install command to pick up the latest. The lockfile updates with the new exact version.
  5. Switch back to stable before the consumer PR merges:
    Terminal window
    npm install @arda-cards/design-system@latest
    or pin to the specific stable that the design-system PR landed as.
  • Preview consumer’s responsibility: do not merge a consumer PR to your own main while it still references a preview dist-tag. Stable release is the merge contract.
  • Cleanup: previews are deleted by the cleanup workflow once the stable base ships, with a 24h grace period. Don’t leave consumer PRs using a preview series open across that boundary.
  • dist-tag stability: re-running npm install @arda-cards/design-system@alice-FD42 on different days may resolve to different exact versions. Use --save-exact only if you need that day’s exact build for reproducibility.
  • latest is sacred: publish-preview.yml always uses --tag <derived>. A consumer doing npm install @arda-cards/design-system (no tag) will never accidentally pull a preview.
ProCon
Real artifact, real CI fidelityLockfile churn on every preview bump
No local-environment setup needed for consumerConsumer must remember to swap to stable before merging
Multiple independent previews can coexist (one per dist-tag)Cleanup may purge a preview while a consumer PR is still using it (24h grace mitigates)
Decoupled iteration cadencesSlightly slower than local-side-by-side (must push + wait for CI per iteration)
  • Two devs, same dist-tag: the dist-tag is derived from the changelog entry, not the branch name. Two devs both writing 4.12.0-alice-FD42 would clobber each other. The <author>-<id> convention with <id> being a unique ticket number prevents this in practice.
  • Stable shipping while preview consumer PR is open: cleanup will purge the preview within 24h. Consumer should bump to the stable version (or pin to the last-known preview exact version) before the cleanup window closes.
  • Pre-release that is not your branch’s: if you npm install @arda-cards/design-system@alice-FD42 and Alice pushes a new commit, the next install picks up her new code automatically. This is desired but worth knowing.