Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ jobs:
run: devbox run --config=shells/devbox-fast.json release
env:
GH_TOKEN: ${{ github.token }}
GITHUB_REF: refs/heads/beta

- name: Release (production)
if: inputs.type == 'production'
Expand Down
4 changes: 0 additions & 4 deletions release.config.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
const changelogFile = 'CHANGELOG.md';

module.exports = {
branches: ['master', { name: 'beta', prerelease: true }],
tagFormat: '${name}-v${version}',
Expand All @@ -9,10 +7,8 @@ module.exports = {
'@semantic-release/release-notes-generator',
{ preset: 'conventionalcommits' },
],
['@semantic-release/changelog', { changelogFile }],
['@semantic-release/npm', { npmPublish: true, provenance: true }],
['@semantic-release/github', { successComment: false }],
['@semantic-release/git', { assets: [changelogFile, 'package.json'] }],
],
debug: true,
};
43 changes: 43 additions & 0 deletions scripts/sync-versions.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
#!/usr/bin/env bash
set -euo pipefail

# Syncs package.json version fields with the latest published npm versions.
# Run via: devbox run sync-versions

PROJECT_ROOT="${PROJECT_ROOT:-$(git rev-parse --show-toplevel)}"

updated=0
skipped=0

for pkg_json in "$PROJECT_ROOT"/packages/*/package.json "$PROJECT_ROOT"/packages/plugins/*/package.json; do
[ -f "$pkg_json" ] || continue

name=$(jq -r '.name' "$pkg_json")
private=$(jq -r '.private // false' "$pkg_json")
current=$(jq -r '.version' "$pkg_json")

if [ "$private" = "true" ]; then
echo " skip $name (private)"
skipped=$((skipped + 1))
continue
fi

latest=$(npm view "$name" version 2>/dev/null || echo "")
if [ -z "$latest" ]; then
echo " skip $name (not on npm)"
skipped=$((skipped + 1))
continue
fi

if [ "$current" = "$latest" ]; then
echo " ok $name@$current"
skipped=$((skipped + 1))
else
jq --arg v "$latest" '.version = $v' "$pkg_json" > "$pkg_json.tmp" && mv "$pkg_json.tmp" "$pkg_json"
echo " bump $name $current -> $latest"
updated=$((updated + 1))
fi
done

echo ""
echo "Done: $updated updated, $skipped unchanged/skipped"
1 change: 1 addition & 0 deletions shells/devbox-fast.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@
],
"format": ["treefmt"],
"lint": ["treefmt --fail-on-change"],
"sync-versions": ["bash $SCRIPTS_DIR/sync-versions.sh"],
"update-apps": [
"yarn install --no-immutable",
"yarn e2e install --no-immutable",
Expand Down
15 changes: 9 additions & 6 deletions wiki/release.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,30 +4,33 @@ This repo uses semantic-release with multi-semantic-release to version and publi

### Prerequisites

- Secrets: `GH_TOKEN` (repo `contents` write) and `NPM_TOKEN` (publish). CI also passes `YARN_NPM_AUTH_TOKEN` (same as `NPM_TOKEN`).
- Secrets: npm trusted publishing (OIDC) is configured per-package on npmjs.com. The workflow uses `github.token` for GitHub operations.
- Git history: full clone (`fetch-depth: 0`) so semantic-release can find prior tags.
- Commit format: conventional commits; commitlint is already configured.

### What runs

- Config files: `release.config.js` (single-package defaults) and `multi-release.config.js` (multi-package orchestration, sequential init/prepare, ignore private packages, tag format/branches).
- Plugins: commit analyzer + release notes, changelog (`CHANGELOG.md`), npm publish, GitHub release (no success comment), and git commit of changelog + package.json.
- Plugins: commit analyzer + release notes, npm publish (with provenance), and GitHub release (no success comment).
- Script: root `yarn release` runs `multi-semantic-release` with the above config per public package.

### CI/CD path (recommended)

1. Ensure `master`/`beta` are green. Merges must use conventional commits.
2. Trigger `Publish` workflow in Actions. Inputs are tokens only; workflow fetches full history, installs Devbox, then runs `devbox run release`.
3. Outputs: package tags (`${name}-vX.Y.Z`), npm publishes, GitHub releases, and updated changelog commits pushed back via the workflow token.
2. Trigger `Release` workflow in Actions. Choose type: `dry-run`, `beta`, or `production`.
3. Outputs: package tags (`${name}-vX.Y.Z`), npm publishes, and GitHub releases.

Note: version bumps and changelogs are **not** committed back to the repo. The source of truth for versions is the git tags and npm registry. To sync the repo's `package.json` versions with npm, run `devbox run --config=shells/devbox-fast.json sync-versions` and include the changes in a PR.

### Local dry run

1. `GH_TOKEN=<token> NPM_TOKEN=<token> YARN_NPM_AUTH_TOKEN=<token>` (GH token needs `contents` write; npm token can be automation/classic publish).
2. `devbox run release -- --dry-run` to see what would publish. Omit `--dry-run` to actually publish (only do this if you intend to release from your machine).
1. `GH_TOKEN=<token> devbox run --config=shells/devbox-fast.json release-dry-run` (GH token needs `contents` read).
2. Omit `--dry-run` to actually publish (only do this if you intend to release from your machine; npm auth is handled via OIDC in CI).

### Tips and gotchas

- Only public packages release; private workspaces (e.g., `packages/shared`) are ignored.
- Tag pattern is important: keep `${name}-v${version}` if you create manual tags for debugging.
- If adding a new branch for releases, update both `release.config.js` and `multi-release.config.js`.
- Keep yarn.lock in sync before releasing to avoid install differences between CI and local.
- `.npmrc` contains `workspaces-update=false` to prevent `npm version` from failing on Yarn's `workspace:` protocol.