feat: publish zero to npm via release-please#367
Conversation
Adds release-please to automate versioning and releases from conventional commits on main: - release-please-config.json / .release-please-manifest.json: node release type (package.json is the version source of truth), plain v-prefixed tags, bootstrap-sha at current HEAD, and release-as 0.1.0 to pin the first release (remove after v0.1.0 ships). - .github/workflows/release-please.yml: maintains the release PR; on merge it tags + creates the GitHub Release, then dispatches release-artifacts.yml at the tag (GITHUB_TOKEN-created tags cannot fire on-push-tags workflows). - .github/workflows/release-artifacts.yml: tag-gated steps now match the ref instead of the push event so the dispatched-at-tag run publishes assets, and a new publish-npm job publishes @gitlawb/zero after verifying every postinstall asset URL is publicly downloadable (also blocks publishing while the repo is private).
Zero automated PR reviewVerdict: No blockers found Blockers
Validation
ScopeHead: This deterministic review checks validation status and basic diff hygiene. A human reviewer still owns product judgment and design quality. |
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (1)
🚧 Files skipped from review as they are similar to previous changes (1)
WalkthroughAdds Release Please automation for main-branch release creation, updates release artifact gating to use tag refs, and adds an npm publish job that checks GitHub Release asset availability before publishing. ChangesRelease automation pipeline
Estimated code review effort: 3 (Moderate) | ~25 minutes Sequence Diagram(s)sequenceDiagram
participant Main as main branch push
participant ReleasePlease as release-please.yml
participant GH as GitHub API
participant ReleaseArtifacts as release-artifacts.yml
participant Npm as npm registry
Main->>ReleasePlease: push event
ReleasePlease->>GH: create release PR/tag
GH-->>ReleasePlease: tag_name output
ReleasePlease->>ReleaseArtifacts: gh workflow run (tag)
ReleaseArtifacts->>GH: create/upload GitHub Release assets
ReleaseArtifacts->>ReleaseArtifacts: curl-check binary + .sha256 URLs
ReleaseArtifacts->>Npm: npm publish --access public
Possibly related PRs
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🧹 Nitpick comments (2)
.github/workflows/release-artifacts.yml (1)
113-114: 🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick winDisable credential persistence on the publish-npm checkout.
This checkout only needs to read
package.json; it never pushes. Defaultpersist-credentials: trueleaves the GITHUB_TOKEN in the local git config for the rest of the job, which is unnecessary exposure in a job that also handlesNPM_TOKENand OIDC provenance credentials.🔧 Suggested fix
- name: Checkout uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4 + with: + persist-credentials: false🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In @.github/workflows/release-artifacts.yml around lines 113 - 114, The publish-npm checkout in the release-artifacts workflow is leaving GitHub credentials persisted unnecessarily; update the Checkout step that uses actions/checkout to disable credential persistence. Set persist-credentials to false on that checkout so the job only reads package.json without storing GITHUB_TOKEN in git config alongside NPM_TOKEN and OIDC credentials.Source: Linters/SAST tools
.github/workflows/release-please.yml (1)
27-34: 🔒 Security & Privacy | 🔵 Trivial | ⚡ Quick winHarden the tag_name interpolation against template injection.
--ref "${{ steps.release.outputs.tag_name }}"is expanded directly into the shell script rather than passed through an env var, which zizmor flags as template-injection-prone.tag_nameis release-please-generated (low real exploitability here), but routing it through an env var is the standard mitigation and costs nothing.🔧 Suggested fix
- name: Build and publish release artifacts if: ${{ steps.release.outputs.release_created }} env: GH_TOKEN: ${{ github.token }} + TAG_NAME: ${{ steps.release.outputs.tag_name }} run: | gh workflow run release-artifacts.yml \ --repo "$GITHUB_REPOSITORY" \ - --ref "${{ steps.release.outputs.tag_name }}" + --ref "$TAG_NAME"🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In @.github/workflows/release-please.yml around lines 27 - 34, The release-artifacts trigger in the `Build and publish release artifacts` step interpolates `steps.release.outputs.tag_name` directly inside the shell script, which is template-injection-prone. Move the tag value into an environment variable in this job, then reference that variable in the `gh workflow run release-artifacts.yml` command instead of expanding `steps.release.outputs.tag_name` inline. Keep the change localized to the workflow step using `release.outputs.tag_name`.Source: Linters/SAST tools
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In @.github/workflows/release-please.yml:
- Around line 8-11: The release workflow permissions are missing the Issues
scope needed by release-please-action to apply release-tracking labels on the
release PR. Update the permissions block in the release-please workflow to
include issues: write alongside the existing contents, pull-requests, and
actions permissions so the action can manage labels successfully.
---
Nitpick comments:
In @.github/workflows/release-artifacts.yml:
- Around line 113-114: The publish-npm checkout in the release-artifacts
workflow is leaving GitHub credentials persisted unnecessarily; update the
Checkout step that uses actions/checkout to disable credential persistence. Set
persist-credentials to false on that checkout so the job only reads package.json
without storing GITHUB_TOKEN in git config alongside NPM_TOKEN and OIDC
credentials.
In @.github/workflows/release-please.yml:
- Around line 27-34: The release-artifacts trigger in the `Build and publish
release artifacts` step interpolates `steps.release.outputs.tag_name` directly
inside the shell script, which is template-injection-prone. Move the tag value
into an environment variable in this job, then reference that variable in the
`gh workflow run release-artifacts.yml` command instead of expanding
`steps.release.outputs.tag_name` inline. Keep the change localized to the
workflow step using `release.outputs.tag_name`.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 75fa4bf8-b04d-4879-98d5-fbdbfd32c4b7
📒 Files selected for processing (4)
.github/workflows/release-artifacts.yml.github/workflows/release-please.yml.release-please-manifest.jsonrelease-please-config.json
Co-authored-by: coderabbitai[bot] <136622811+coderabbitai[bot]@users.noreply.github.com>
npm's trusted publishing exchanges the workflow's OIDC token for publish auth, so no long-lived NPM_TOKEN secret exists to leak, and provenance is generated automatically. Drops registry-url from setup-node (its .npmrc line hard-fails on the unset NODE_AUTH_TOKEN) and updates npm first (OIDC needs npm >= 11.5.1). One-time caveat: npm only lets you configure a trusted publisher on an existing package, so the first @gitlawb/zero publish is a manual bootstrap.
There was a problem hiding this comment.
Actionable comments posted: 1
Caution
Some comments are outside the diff and can’t be posted inline due to platform limitations.
⚠️ Outside diff range comments (1)
.github/workflows/release-artifacts.yml (1)
149-153: 🩺 Stability & Availability | 🟡 Minor | ⚡ Quick winRetry release asset probes before failing publish.
The publish job runs immediately after matrix uploads; a single transient 404/5xx can block npm publishing even though the asset becomes public moments later.
Proposed fix
"zero-v${version}-windows-x64.zip"; do for url in "${base}/${asset}" "${base}/${asset}.sha256"; do - if ! curl -fsSLI -o /dev/null "$url"; then + ok=false + for attempt in {1..6}; do + if curl -fsSLI -o /dev/null "$url"; then + ok=true + break + fi + sleep 10 + done + if [ "$ok" != true ]; then echo "::error::${url} is not publicly downloadable — npm postinstall would fail. Is the repo public and are all assets uploaded?" >&2 exit 1 fi🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In @.github/workflows/release-artifacts.yml around lines 149 - 153, The release artifact probe in the publish workflow fails immediately on a single transient 404/5xx, which can block npm publishing even when the asset appears moments later. Update the URL check loop in the release-artifacts workflow to retry the HEAD request for each asset and its .sha256 before exiting, using the existing curl-based probe around the `${base}/${asset}` and `${base}/${asset}.sha256` checks. Keep the final failure path and error message, but only emit it after the retry attempts are exhausted.
🧹 Nitpick comments (1)
.github/workflows/release-artifacts.yml (1)
119-120: 🔒 Security & Privacy | 🔵 Trivial | 💤 Low valueSet
persist-credentials: falseon checkout. This job doesn’t use git after checkout, so there’s no need to leaveGITHUB_TOKENin.git/config.🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In @.github/workflows/release-artifacts.yml around lines 119 - 120, The Checkout step in the release-artifacts workflow should disable persisted git credentials. Update the actions/checkout usage for the Checkout job to set persist-credentials to false so GITHUB_TOKEN is not left in .git/config, and keep the change localized to that checkout step.Source: Linters/SAST tools
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In @.github/workflows/release-artifacts.yml:
- Around line 125-132: The trusted-publishing job currently upgrades npm with
npm@latest, which introduces unnecessary supply-chain risk. Update the npm
bootstrap step in the release workflow to use a pinned npm version that
satisfies the OIDC requirement, or replace it with a fast version check in the
setup step so the job fails if the bundled npm is too old. Refer to the Setup
Node and Update npm for trusted publishing steps in the workflow when making the
change.
---
Outside diff comments:
In @.github/workflows/release-artifacts.yml:
- Around line 149-153: The release artifact probe in the publish workflow fails
immediately on a single transient 404/5xx, which can block npm publishing even
when the asset appears moments later. Update the URL check loop in the
release-artifacts workflow to retry the HEAD request for each asset and its
.sha256 before exiting, using the existing curl-based probe around the
`${base}/${asset}` and `${base}/${asset}.sha256` checks. Keep the final failure
path and error message, but only emit it after the retry attempts are exhausted.
---
Nitpick comments:
In @.github/workflows/release-artifacts.yml:
- Around line 119-120: The Checkout step in the release-artifacts workflow
should disable persisted git credentials. Update the actions/checkout usage for
the Checkout job to set persist-credentials to false so GITHUB_TOKEN is not left
in .git/config, and keep the change localized to that checkout step.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 27f3fbe8-7391-49fe-8447-ab94ea2ead42
📒 Files selected for processing (1)
.github/workflows/release-artifacts.yml
Rely on the npm bundled with the pinned Node 24 toolchain (>= 11.5.1, the trusted-publishing minimum) instead of pulling an unpinned npm@latest from the registry inside the publish job, and fail fast with a clear error if a future toolchain change regresses it.
Summary
Automates versioning and publishing with release-please so
npm install -g @gitlawb/zerocan go live and stay live without manual release steps.release-please-config.json/.release-please-manifest.json—noderelease type (package.jsonis Zero's version source of truth, read byinternal/release/release.go), plainv*tags,bootstrap-shaat current HEAD so the first changelog starts clean, andrelease-as: 0.1.0to pin the first release (remove after v0.1.0 ships)..github/workflows/release-please.yml(new) — maintains the release PR from conventional commits onmain; when merged, creates the tag + GitHub Release, then dispatchesrelease-artifacts.ymlat the tag. The explicit dispatch is required because tags created with the defaultGITHUB_TOKENnever triggeron: push: tagsworkflows; API-invokedworkflow_dispatchis exempt from that suppression..github/workflows/release-artifacts.yml— tag-gated steps now match the ref (refs/tags/v*) instead of requiring apushevent, so the dispatched-at-tag run packages and publishes identically to a manual tag push. Adds apublish-npmjob that runs after all five platform artifacts upload: it probes every asset URLscripts/postinstall.mjsbuilds (verified against dry-runs for all platform/arch combos) as an anonymous client, thennpm publish --access public --provenance. The probe doubly acts as a gate: while the repo is private, assets 404 anonymously, so a broken npm package cannot ship.Resulting flow: conventional commit lands on
main→ release-please updates its release PR → merge → tag + Release → 5-platform artifacts build/upload → npm wrapper publishes.Follow-ups tracked outside this PR: enable "Allow GitHub Actions to create and approve pull requests" in repo settings, add the
NPM_TOKENsecret, make the repo public, and droprelease-asafter v0.1.0.Checklist
issue-approvedlabel.go build ./...,go vet ./..., andgo test ./...pass locally.gofmtclean.-racewhere relevant). — N/A: no Go code changed; workflows/config validated via YAML/JSON parsing, pinned-action SHA verification against the GitHub API, andpostinstall.mjsdry-runs for every platform/arch.Summary by CodeRabbit
v*tag refs (not limited to specific event types).v*tags that validates expected GitHub Release asset URLs before publishing@gitlawb/zeropublicly.