Publishing @asteby/metacore-* packages
End-to-end guide for releasing packages from this monorepo and propagating updates to consumer apps. The pipeline is fully automated with Changesets + a single GitHub Actions workflow.
Table of contents
- TL;DR
- Prerequisites
- The release workflow
- Authoring a changeset
- Pre-releases (next / beta / rc)
- Linked and ignored packages
- Troubleshooting
- References
TL;DR
- Change code in
packages/*. - Run
pnpm changesetand pick the bump (patch / minor / major) per affected package. - Commit the generated
.changeset/*.mdalongside your code in a PR. - When your PR merges to
main, the Release npm packages workflow opens (or updates) achore(release): version packagesPR. - Merging that "Version Packages" PR bumps versions, regenerates changelogs, and triggers
changeset publishto npm under the@astebyscope. - Renovate bots in consumer host apps pick up the new versions and open PRs. Patch / minor bumps auto-merge; majors await human review.
Prerequisites
NPM_TOKENrepo secret inasteby/metacore-sdk— a Granular Access Token with publish permission on the@astebyscope and the "Bypass 2FA" option enabled. Generate it under https://www.npmjs.com/settings/asteby/tokens.- Repo permissions: the workflow declares
contents: write,pull-requests: write, andid-token: write. Make sure "Allow GitHub Actions to create and approve pull requests" is enabled in repo Settings → Actions → General. - pnpm 10+ locally (matches CI). The root
packageManagerfield is authoritative. - Node.js 20+ locally.
The release workflow
File: .github/workflows/release-npm.yml.
It runs on every push to main:
- If the push contains
.changeset/*.mdfiles not yet versioned,changesets/action@v1opens or updates a single PR titledchore(release): version packageswhose diff bumpspackage.jsonversions and moves the changesets intoCHANGELOG.md. - If the push is that PR being merged (so no changesets are left), the action runs
pnpm exec changeset publish, which executesturbo run build --filter=./packages/*followed bychangeset publish, pushing any packages whose versions bumped to npm.
The action reads .changeset/config.json for scope, access (public), linked packages, and base branch.
Authoring a changeset
pnpm changesetPick:
- Which packages changed. Space to toggle, enter to confirm.
- Bump level.
patch— bug fix, docs, internal refactor with no API change.minor— new backwards-compatible feature.major— breaking change. Triggers consumer-side human review via Renovate.
- Summary. Goes straight into the CHANGELOG. Write it for humans, not for git history. Imperative voice ("add", "fix", "remove"), one line, ideally under 80 chars.
Commit the generated .changeset/*.md in the same PR as your code. Reviewers eyeball both the change and the bump.
Pre-releases (next / beta / rc)
Use the pre mode when you want to ship from main without going stable:
pnpm changeset pre enter next
pnpm changeset # author changeset as usual
# ...merge PRs to main, each publishes as e.g. 0.3.0-next.0, 0.3.0-next.1
pnpm changeset pre exitWhile in pre mode the release workflow publishes with the next dist-tag, so pnpm add @asteby/metacore-ui@next opts in. Exit pre mode before the stable release PR.
For an isolated channel (e.g., beta), use pnpm changeset pre enter beta.
Linked and ignored packages
.changeset/config.json configures two important constraints:
linked: [["@asteby/metacore-ui", "@asteby/metacore-theme"]]— UI and theme must version together. They share a design contract; bumping one alone breaks consumers.ignore: ["@asteby/metacore-starter-core", "create-metacore-app"]— these packages are private / internal and excluded from the publish flow. Their changesets are still generated but never trigger npm publishes.
Do not edit these without understanding the downstream effect on consumers.
Troubleshooting
- "Version Packages" PR never opens. No unversioned
.changeset/*.mdfiles onmain. Runpnpm changesetand push. - Publish step fails with 401 / 403.
NPM_TOKENmissing, expired, or lacks publish rights on@asteby. Regenerate as a Granular Access Token with "Bypass 2FA" enabled and update the repo secret. - Publish succeeds for some packages but skips others. Check the package's
"private": trueflag and that.changeset/config.jsonignorearray doesn't list it. - Linked packages drifted.
@asteby/metacore-uiand@asteby/metacore-thememust bump together. Thelinkedarray enforces this — don't remove it without understanding the downstream effect on consumers. pnpm installfails in CI withERR_PNPM_LOCKFILE_BROKEN. The lockfile is regenerated via--frozen-lockfile=false. If it persists, deletepnpm-lock.yamllocally, reinstall, commit.- Version Packages PR has merge conflicts with
pnpm-lock.yaml. Close it. The next push tomainregenerates a clean one. - Consumer app didn't get a Renovate PR. Confirm the consumer's
renovate.jsonmatchesrenovate-consumer-template.jsonand that Renovate is installed on the consumer repo (github.com/apps/renovate).
References
- Changesets docs: https://github.com/changesets/changesets
- changesets/action: https://github.com/changesets/action
- Consumer Renovate template:
renovate-consumer-template.json - Consumer integration guide:
consumer-guide.md