@williamthorsen/release-kit 5.0.0 → 5.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +149 -49
- package/README.md +275 -78
- package/cliff.toml.template +26 -17
- package/dist/esm/.cache +1 -1
- package/dist/esm/assertCleanWorkingTree.js +1 -1
- package/dist/esm/bin/release-kit.js +97 -4
- package/dist/esm/buildChangelogEntries.d.ts +4 -0
- package/dist/esm/buildChangelogEntries.js +173 -0
- package/dist/esm/buildDependencyGraph.d.ts +1 -0
- package/dist/esm/buildDependencyGraph.js +8 -1
- package/dist/esm/buildReleaseSummary.js +9 -1
- package/dist/esm/buildSyntheticChangelogEntry.d.ts +5 -0
- package/dist/esm/buildSyntheticChangelogEntry.js +13 -0
- package/dist/esm/changelogJsonFile.d.ts +4 -0
- package/dist/esm/changelogJsonFile.js +68 -0
- package/dist/esm/checkWorkTypesDrift.d.ts +11 -0
- package/dist/esm/checkWorkTypesDrift.js +110 -0
- package/dist/esm/collectPolicyViolations.d.ts +6 -0
- package/dist/esm/collectPolicyViolations.js +15 -0
- package/dist/esm/createGithubRelease.d.ts +12 -2
- package/dist/esm/createGithubRelease.js +12 -8
- package/dist/esm/createGithubReleaseCommand.js +10 -6
- package/dist/esm/decideRelease.d.ts +28 -0
- package/dist/esm/decideRelease.js +44 -0
- package/dist/esm/defaults.d.ts +8 -0
- package/dist/esm/defaults.js +43 -20
- package/dist/esm/deriveWorkspaceConfig.js +3 -0
- package/dist/esm/determineBumpFromCommits.d.ts +6 -1
- package/dist/esm/determineBumpFromCommits.js +9 -3
- package/dist/esm/generateChangelogs.js +14 -29
- package/dist/esm/index.d.ts +2 -43
- package/dist/esm/index.js +0 -82
- package/dist/esm/init/templates.js +2 -2
- package/dist/esm/loadConfig.d.ts +10 -1
- package/dist/esm/loadConfig.js +110 -24
- package/dist/esm/parseCommitMessage.d.ts +8 -2
- package/dist/esm/parseCommitMessage.js +32 -3
- package/dist/esm/prepareCommand.js +51 -9
- package/dist/esm/publish.d.ts +0 -1
- package/dist/esm/publish.js +3 -3
- package/dist/esm/publishCommand.js +31 -3
- package/dist/esm/releasePrepare.js +109 -41
- package/dist/esm/releasePrepareMono.js +156 -87
- package/dist/esm/releasePrepareProject.d.ts +9 -0
- package/dist/esm/releasePrepareProject.js +121 -0
- package/dist/esm/renderReleaseNotes.js +2 -1
- package/dist/esm/reportPrepare.js +88 -24
- package/dist/esm/resolveCommandTags.js +16 -6
- package/dist/esm/resolveReleaseTags.d.ts +8 -1
- package/dist/esm/resolveReleaseTags.js +11 -7
- package/dist/esm/runGitCliff.d.ts +2 -0
- package/dist/esm/runGitCliff.js +27 -0
- package/dist/esm/stripEmojiPrefix.d.ts +1 -0
- package/dist/esm/stripEmojiPrefix.js +7 -0
- package/dist/esm/syncWorkTypes.d.ts +10 -0
- package/dist/esm/syncWorkTypes.js +90 -0
- package/dist/esm/types.d.ts +72 -14
- package/dist/esm/validateConfig.js +26 -0
- package/dist/esm/validateOnlyExcludesStrandedDependents.d.ts +14 -0
- package/dist/esm/validateOnlyExcludesStrandedDependents.js +109 -0
- package/dist/esm/work-types.json +127 -0
- package/dist/esm/work-types.schema.json +73 -0
- package/dist/esm/workTypesData.d.ts +14 -0
- package/dist/esm/workTypesData.js +59 -0
- package/dist/esm/workTypesUtils.d.ts +5 -0
- package/dist/esm/workTypesUtils.js +16 -0
- package/package.json +9 -3
- package/presets/labels/common.yaml +9 -6
- package/schemas/label-map.json +24 -0
- package/dist/esm/generateChangelogJson.d.ts +0 -7
- package/dist/esm/generateChangelogJson.js +0 -232
- package/dist/esm/version.d.ts +0 -1
- package/dist/esm/version.js +0 -4
package/README.md
CHANGED
|
@@ -5,61 +5,39 @@ Version-bumping and changelog-generation toolkit for release workflows.
|
|
|
5
5
|
Provides a self-contained CLI that auto-discovers workspaces from `pnpm-workspace.yaml`, parses conventional commits, determines version bumps, updates `package.json` files, and generates changelogs with `git-cliff`.
|
|
6
6
|
|
|
7
7
|
<!-- section:release-notes -->
|
|
8
|
-
## Release notes — v5.
|
|
8
|
+
## Release notes — v5.2.0 (2026-05-04)
|
|
9
9
|
|
|
10
|
-
###
|
|
10
|
+
### 🎉 Features
|
|
11
11
|
|
|
12
|
-
-
|
|
12
|
+
- Add emojis to changelog and release-note headings (#352)
|
|
13
13
|
|
|
14
|
-
|
|
14
|
+
Adds emoji prefixes to the section headings rendered in `CHANGELOG.md` and release notes generated by `@williamthorsen/release-kit`. Each of the 13 default work types gets a single decorative emoji so its section is easier to spot when skimming a release: 🐛 Bug fixes, 🎉 Features, 📚 Documentation, ♻️ Refactoring, ⚡ Performance, 🔒 Security, 🧪 Tests, ⚙️ Tooling, 👷 CI, 📦 Dependencies, 🏗️ Internal, 🗑️ Deprecated, and 🤖 Agentic support. Matching of `changelogJson.devOnlySections` is emoji-tolerant: existing consumer overrides written as bare names continue to work without modification.
|
|
15
15
|
|
|
16
|
-
|
|
16
|
+
- Surface bang violations in release prepare reports (#359)
|
|
17
17
|
|
|
18
|
-
-
|
|
18
|
+
Release-prepare flows now surface `!`-policy violations as warnings in the prepare report. Each workspace's and project's commit window is parsed against the default policy table — `internal!` is rejected as contradictory, bare `drop:` is rejected for missing the required `!`, and so on — and any violations appear under the workspace's section in the report alongside short hash, truncated subject, type, and surface (prefix or body). A new `breakingPolicies` config field lets consumers override individual entries or pass `{}` to disable enforcement entirely. Release-time enforcement remains tolerant: violations are warnings, never failures, so a single legacy commit cannot block a release.
|
|
19
19
|
|
|
20
|
-
|
|
20
|
+
### 🐛 Bug fixes
|
|
21
21
|
|
|
22
|
-
-
|
|
22
|
+
- Restrict publish to publishable workspaces (#345)
|
|
23
23
|
|
|
24
|
-
|
|
24
|
+
Fixes an issue where `release-kit publish` failed for workspaces marked `package.json#private: true`. The command now operates only on publishable workspaces — those where `private` is absent or `false` — and the rest of the release pipeline (`tag`, `create-github-release`, `prepare`, changelog) continues to handle private workspaces unchanged. This preserves the "versioned but not published" workflow: a private workspace can still be versioned, tagged, and published as a GitHub Release; only the registry-publish step is skipped. Without `--tags`, unpublishable tags are silently filtered (an empty result prints `Nothing to publish.` and exits 0). With `--tags` naming an unpublishable workspace, `release-kit publish` exits 1 with one error per offending tag, citing `package.json#private` and the workspace path.
|
|
25
25
|
|
|
26
|
-
-
|
|
26
|
+
- Skip tooling-only releases instead of failing (#347)
|
|
27
27
|
|
|
28
|
-
|
|
28
|
+
Fixes an issue where `release-kit create-github-release --tags <tag>` exited 1 whenever the tag's changelog had no all-audience content. The reusable `create-github-release.reusable.yaml` workflow forwards `github.ref_name` into `--tags`, so tooling-only releases consistently produced failed workflow runs even though no failure occurred. The command now exits 1 only when a requested tag has no changelog entry; intentional skip reasons (`no-audience-content`, `empty-body`) are informational. A typoed tag still surfaces an error even when batched alongside successful tags, and the info summary reports the per-tag skip reason for diagnostic visibility.
|
|
29
29
|
|
|
30
|
-
-
|
|
30
|
+
- Establish canonical work-types SSOT and restore changelog section ordering (#358)
|
|
31
31
|
|
|
32
|
-
|
|
32
|
+
Restores canonical section ordering in changelogs and release notes — sections were appearing in unpredictable order after the previous release added emoji prefixes to section headers. Sections now follow a stable priority: public-facing types (Features, Fixes, Security, …) first, then internal types, then process types. Release-note bullets for breaking changes carry a `🚨 **Breaking:**` prefix so they stand out at a glance. Documentation entries move out of public release notes — they continue to appear in dev changelogs.
|
|
33
33
|
|
|
34
|
-
|
|
34
|
+
Closes #355.
|
|
35
35
|
|
|
36
|
-
|
|
36
|
+
### ⚡ Performance
|
|
37
37
|
|
|
38
|
-
-
|
|
38
|
+
- Skip npx registry revalidation when running git-cliff (#361)
|
|
39
39
|
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
- Add migrate-tag-prefixes.sh migration tool (#282)
|
|
43
|
-
|
|
44
|
-
Adds a one-shot migration tool, `migrate-tag-prefixes.sh`, shipped inside the release-kit package. The tool creates additive annotated-tag aliases under release-kit's new unscoped-package-name prefix that point at the same commits as the previous directory-basename tags, bridging the gap so post-migration `getCommitsSinceTarget` calls can resolve prior releases.
|
|
45
|
-
|
|
46
|
-
- Add legacyTagPrefixes config field (#289)
|
|
47
|
-
|
|
48
|
-
Replaces the v4 → v5 tag-prefix migration mechanism (tag aliasing via `migrate-tag-prefixes.sh`) with a declarative `legacyTagPrefixes` config field. release-kit now searches for both legacy and modern prefixes when generating changelogs.
|
|
49
|
-
|
|
50
|
-
Adds a companion `release-kit show-tag-prefixes` CLI command that renders a per-workspace table of derived and declared legacy prefixes, flags cross-workspace collisions, and surfaces undeclared candidate prefixes with a copy-pasteable config snippet. `release-kit prepare` gains a one-line hint pointing operators to `show-tag-prefixes` when a workspace has no baseline tag but the repo contains candidate-shaped tags.
|
|
51
|
-
|
|
52
|
-
- Replace `legacyTagPrefixes` with `legacyIdentities` (#297)
|
|
53
|
-
|
|
54
|
-
Replaces the per-workspace `legacyTagPrefixes: string[]` field with `legacyIdentities: LegacyIdentity[]`, a structured array of complete `(name, tagPrefix)` historical snapshots. Each legacy identity is now a self-consistent record of what a workspace used to be called and how its tags used to be prefixed, so a workspace that has been renamed (npm name change, tag-prefix change, or both) carries one entry per prior identity.
|
|
55
|
-
|
|
56
|
-
- Add `retiredPackages` repo-level config field (#299)
|
|
57
|
-
|
|
58
|
-
Adds support for declaring packages that once lived in this repo but have been extracted or removed, so their historical tag prefixes (e.g., `preflight-v*` from the extracted `readyup` project) no longer surface as "Undeclared tag prefixes" in `release-kit show-tag-prefixes`. Declared retired packages are acknowledged as real history but never consulted for baseline lookup or changelog attribution — they complement `workspaces[].legacyIdentities`, which is used when a workspace still exists under a new identity.
|
|
59
|
-
|
|
60
|
-
- Add release-notes preview generator to `release-kit prepare` (#302)
|
|
61
|
-
|
|
62
|
-
Adds the ability to generate release notes when running `release-kit prepare`. The `--with-release-notes` option enables the generation of per-workspace preview files so authors can verify release-note injection before publishing. Injected release notes are also now prefixed with a `## Release notes — v{version} ({date})` heading to add missing context to the README.
|
|
40
|
+
Speeds up `release-kit prepare` by skipping the npm registry cache-revalidation HTTP request that ran on every `git-cliff` invocation. Per-invocation overhead drops from ~4.6 s to ~2.0 s; in a four-workspace monorepo this saves about 10 seconds per run. Also suppresses a transient stderr spinner that briefly appeared during package resolution and looked like a half-complete log message. Network fallback is preserved — runs on machines with an empty npx cache still resolve `git-cliff` over the network.
|
|
63
41
|
<!-- /section:release-notes -->
|
|
64
42
|
|
|
65
43
|
## Installation
|
|
@@ -163,15 +141,17 @@ The config file supports both `export default config` and `export const config =
|
|
|
163
141
|
|
|
164
142
|
### `ReleaseKitConfig` reference
|
|
165
143
|
|
|
166
|
-
| Field
|
|
167
|
-
|
|
|
168
|
-
| `cliffConfigPath`
|
|
169
|
-
| `workspaces`
|
|
170
|
-
| `formatCommand`
|
|
171
|
-
| `versionPatterns`
|
|
172
|
-
| `scopeAliases`
|
|
173
|
-
| `workTypes`
|
|
174
|
-
| `
|
|
144
|
+
| Field | Type | Description |
|
|
145
|
+
| ------------------ | --------------------------------------------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
146
|
+
| `cliffConfigPath` | `string` | Explicit path to cliff config. If omitted, resolved automatically: `.config/git-cliff.toml` → `cliff.toml` → bundled template |
|
|
147
|
+
| `workspaces` | `WorkspaceOverride[]` | Override or exclude discovered workspaces (matched by `dir`) |
|
|
148
|
+
| `formatCommand` | `string` | Shell command to run after changelog generation; modified file paths are appended as arguments |
|
|
149
|
+
| `versionPatterns` | `VersionPatterns` | Rules for which commit types trigger major/minor bumps |
|
|
150
|
+
| `scopeAliases` | `Record<string, string>` | Maps shorthand scope names to canonical names in commits |
|
|
151
|
+
| `workTypes` | `Record<string, WorkTypeConfig>` | Work type definitions, merged with defaults by key |
|
|
152
|
+
| `breakingPolicies` | `Record<string, 'forbidden' \| 'optional' \| 'required'>` | Per-type `!`-policy lookup. Defaults to `DEFAULT_BREAKING_POLICIES`. Replaces the default entirely when provided. Set to `{}` to disable enforcement |
|
|
153
|
+
| `retiredPackages` | `RetiredPackage[]` | Packages that once lived in this repo but have been extracted or removed; suppresses undeclared-tag-prefix warnings |
|
|
154
|
+
| `project` | `ProjectConfig` | Opt-in project-level release block. Declaring `project: {}` (even empty) enables a project-release stage in `prepare` |
|
|
175
155
|
|
|
176
156
|
All fields are optional.
|
|
177
157
|
|
|
@@ -222,10 +202,95 @@ Validation rules:
|
|
|
222
202
|
- `successor` is optional; if present, it must be a non-empty string.
|
|
223
203
|
- Full-tuple `(name, tagPrefix)` duplicates within `retiredPackages` are rejected.
|
|
224
204
|
- Two entries sharing the same `tagPrefix` but different `name`s are accepted — this documents a package renamed within the repo before being retired.
|
|
225
|
-
- A `tagPrefix` that collides with an active workspace's derived prefix or any declared `workspaces[].legacyIdentities[].tagPrefix` is rejected. A retired prefix cannot also be current or legacy.
|
|
226
205
|
|
|
227
206
|
`show-tag-prefixes` currently does not render a dedicated "Retired packages" section (deferred). Declaring a retired entry is verifiable by confirming that its `tagPrefix` stops appearing under "Undeclared tag prefixes" in the `show-tag-prefixes` output.
|
|
228
207
|
|
|
208
|
+
### Tag prefix collisions
|
|
209
|
+
|
|
210
|
+
Tag prefixes from distinct owners must not be identical or be a strict prefix of one another. An owner is one of:
|
|
211
|
+
|
|
212
|
+
- An active workspace, comprising its derived `tagPrefix` plus any declared `legacyIdentities[].tagPrefix`. Identities of the same workspace are one owner, so their prefixes are allowed to overlap (this represents the same package across renames).
|
|
213
|
+
- A `retiredPackages[]` entry (one owner per entry).
|
|
214
|
+
- The `project` block, when configured.
|
|
215
|
+
|
|
216
|
+
release-kit resolves baseline tags via `git describe --match=<prefix>*`, so a strict-prefix overlap between distinct owners would cause that glob to return cross-matches against the wrong owner's history. For example, a project prefix of `v` collides with a workspace prefix of `vue-helpers-v`, since `git describe --match=v*` would return both project tags and `vue-helpers` tags.
|
|
217
|
+
|
|
218
|
+
The rule is enforced at config load; the resulting error identifies both colliding declarations.
|
|
219
|
+
|
|
220
|
+
### Project releases
|
|
221
|
+
|
|
222
|
+
Some monorepos ship a single combined deliverable — a Chrome extension, a CLI binary, a packaged desktop app — for which the per-workspace tags and changelogs alone do not describe what the user actually receives. Declare the optional `project` block to add a project-level release stage that runs alongside the per-workspace pipeline.
|
|
223
|
+
|
|
224
|
+
```typescript
|
|
225
|
+
import type { ReleaseKitConfig } from '@williamthorsen/release-kit';
|
|
226
|
+
|
|
227
|
+
const config: ReleaseKitConfig = {
|
|
228
|
+
// Empty object is enough to opt in. Every non-excluded workspace contributes.
|
|
229
|
+
project: {},
|
|
230
|
+
};
|
|
231
|
+
|
|
232
|
+
export default config;
|
|
233
|
+
```
|
|
234
|
+
|
|
235
|
+
When configured, each `release-kit prepare` run additionally:
|
|
236
|
+
|
|
237
|
+
- Computes commits since the last project tag (`<tagPrefix><version>`), filtered to the union of every contributing workspace's paths.
|
|
238
|
+
- Bumps the root `package.json`'s `version` field using the same bump-derivation rules as workspaces (or the `--bump=...` override).
|
|
239
|
+
- Regenerates the root `./CHANGELOG.md` via `git-cliff`, scoped to the project's `tagPrefix` and contributing paths.
|
|
240
|
+
- Emits `./.meta/changelog.json` (when `changelogJson.enabled`).
|
|
241
|
+
- With `--with-release-notes`, additionally emits `./docs/RELEASE_NOTES.v<version>.md`.
|
|
242
|
+
- Appends the project tag to `tmp/.release-tags` so `release-kit commit` and `release-kit tag` pick it up alongside per-workspace tags.
|
|
243
|
+
|
|
244
|
+
If no contributing workspace has commits since the last project tag, the project release is silently skipped — same behavior as a per-workspace skip.
|
|
245
|
+
|
|
246
|
+
#### `ProjectConfig`
|
|
247
|
+
|
|
248
|
+
```typescript
|
|
249
|
+
interface ProjectConfig {
|
|
250
|
+
tagPrefix?: string; // Defaults to 'v'
|
|
251
|
+
}
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
| Field | Default | Description |
|
|
255
|
+
| ----------- | ------- | -------------------------------------------------------------------- |
|
|
256
|
+
| `tagPrefix` | `'v'` | Prefix for project tags. The full tag is `${tagPrefix}${newVersion}` |
|
|
257
|
+
|
|
258
|
+
Contributing workspaces are implicit: every non-excluded discovered workspace contributes. There is no field to override the contributing set in this initial release; if a future consumer needs to release a workspace as a component but exclude it from the project release, that override can be added then.
|
|
259
|
+
|
|
260
|
+
Validation rules:
|
|
261
|
+
|
|
262
|
+
- The root `package.json` must exist and declare a `version` field. release-kit reports an error at config-load time if either is missing.
|
|
263
|
+
- The `project` block is rejected in single-package mode (the implicit "all non-excluded workspaces contribute" rule is meaningless in a single-package repo).
|
|
264
|
+
- Unknown fields inside `project` are rejected.
|
|
265
|
+
|
|
266
|
+
CLI flag interactions:
|
|
267
|
+
|
|
268
|
+
- `--dry-run` previews project artifacts alongside workspace artifacts; no files are written.
|
|
269
|
+
- `--bump=major|minor|patch` propagates to the project release as a level chooser. It does not trigger a release on its own when there are no commits or no bump-worthy commits.
|
|
270
|
+
- `--force` runs the project release even when no commits or no bump-worthy commits exist since the last project tag. Defaults to patch when `--bump` is not given; combine with `--bump=X` to release at a different level.
|
|
271
|
+
- `--only` is rejected with an error when `project` is configured. `--only` is a surgical, single-workspace operation; combining it with a project release that rolls up every contributing workspace would create ambiguous semantics. To release a single workspace, use a config without a `project` block, or run a full `prepare` (no `--only`) to include the project release.
|
|
272
|
+
- `--set-version` is rejected with an error when `project` is configured. `--set-version` operates on a single workspace, but a project release rolls up every contributing workspace; the two semantics don't compose. To use `--set-version`, run on a config without a `project` block.
|
|
273
|
+
|
|
274
|
+
`--bump` and `--force` are orthogonal: `--bump` is purely a level chooser; `--force` is purely a release trigger. Examples:
|
|
275
|
+
|
|
276
|
+
```sh
|
|
277
|
+
# Release every target at its natural bump level (no flags).
|
|
278
|
+
release-kit prepare
|
|
279
|
+
|
|
280
|
+
# Force a release even when no bump-worthy commits exist; defaults to patch
|
|
281
|
+
# per target, with each target keeping its natural bump if one is derivable.
|
|
282
|
+
release-kit prepare --force
|
|
283
|
+
|
|
284
|
+
# Force a release at a uniform level across every releasing target.
|
|
285
|
+
release-kit prepare --force --bump=minor
|
|
286
|
+
|
|
287
|
+
# --bump=X alone is a level chooser, NOT a trigger. If a target has no
|
|
288
|
+
# bump-worthy commits, it skips with a "Pass --force..." reason. If it has
|
|
289
|
+
# bump-worthy commits, the override applies. (Behavioral change from earlier
|
|
290
|
+
# release-kit versions, where --bump=X alone would force a release.)
|
|
291
|
+
release-kit prepare --bump=minor
|
|
292
|
+
```
|
|
293
|
+
|
|
229
294
|
### `VersionPatterns`
|
|
230
295
|
|
|
231
296
|
Defines which commit types trigger major or minor bumps. Any recognized type not listed defaults to a patch bump.
|
|
@@ -239,30 +304,93 @@ interface VersionPatterns {
|
|
|
239
304
|
|
|
240
305
|
Default: `{ major: ['!'], minor: ['feat'] }`
|
|
241
306
|
|
|
242
|
-
###
|
|
307
|
+
### Work types and tiers
|
|
308
|
+
|
|
309
|
+
The canonical taxonomy lives in `packages/release-kit/src/work-types.json` and is split into three tiers that drive section rendering and audience classification.
|
|
310
|
+
|
|
311
|
+
| Tier | Key | Header | Aliases | `!` policy |
|
|
312
|
+
| -------- | ----------- | ------------------------- | ------------- | ------------ |
|
|
313
|
+
| Public | `feat` | 🎉 Features | `feature` | optional |
|
|
314
|
+
| Public | `drop` | 🪦 Removed | | **required** |
|
|
315
|
+
| Public | `deprecate` | 🗑️ Deprecated | | forbidden |
|
|
316
|
+
| Public | `fix` | 🐛 Bug fixes | `bugfix` | forbidden |
|
|
317
|
+
| Public | `sec` | 🔒 Security | `security` | optional |
|
|
318
|
+
| Public | `perf` | ⚡ Performance | `performance` | forbidden |
|
|
319
|
+
| Internal | `internal` | 🏗️ Internal features | `utility` | forbidden |
|
|
320
|
+
| Internal | `refactor` | ♻️ Refactoring | | forbidden |
|
|
321
|
+
| Internal | `tests` | 🧪 Tests | `test` | forbidden |
|
|
322
|
+
| Process | `tooling` | ⚙️ Tooling | | forbidden |
|
|
323
|
+
| Process | `ci` | 👷 CI | | forbidden |
|
|
324
|
+
| Process | `deps` | 📦 Dependencies | `dep` | forbidden |
|
|
325
|
+
| Process | `ai` | 🤖 Agentic support | | forbidden |
|
|
326
|
+
| Process | `docs` | 📚 Documentation | `doc` | forbidden |
|
|
327
|
+
| Process | `fmt` | (excluded from changelog) | | forbidden |
|
|
328
|
+
|
|
329
|
+
#### Tier semantics
|
|
330
|
+
|
|
331
|
+
- **Public** — visible to all audiences. Public-tier sections appear in both public release notes and dev changelogs.
|
|
332
|
+
- **Internal** — dev-only. Internal-tier sections appear in dev changelogs but not in public-facing release notes.
|
|
333
|
+
- **Process** — dev-only. Same audience treatment as Internal.
|
|
243
334
|
|
|
244
|
-
|
|
245
|
-
| ----------- | --------------- | ------------- |
|
|
246
|
-
| `fix` | Bug fixes | `bugfix` |
|
|
247
|
-
| `deprecate` | Deprecated | |
|
|
248
|
-
| `feat` | Features | `feature` |
|
|
249
|
-
| `internal` | Internal | |
|
|
250
|
-
| `perf` | Performance | `performance` |
|
|
251
|
-
| `refactor` | Refactoring | |
|
|
252
|
-
| `sec` | Security | `security` |
|
|
253
|
-
| `tests` | Tests | `test` |
|
|
254
|
-
| `tooling` | Tooling | |
|
|
255
|
-
| `ci` | CI | |
|
|
256
|
-
| `deps` | Dependencies | `dep` |
|
|
257
|
-
| `docs` | Documentation | `doc` |
|
|
258
|
-
| `ai` | Agentic support | |
|
|
259
|
-
| `fmt` | (skipped) | |
|
|
335
|
+
Section render order is **tier order (Public → Internal → Process), then row order within tier**. The bundled `cliff.toml.template` encodes this order via hidden `<!-- NN -->` HTML-comment prefixes on each parser's `group` value; tera's `group_by` filter sorts groups lexicographically (now monotonic by row number), and the body template's `striptags` filter erases the prefix from rendered headings.
|
|
260
336
|
|
|
261
|
-
|
|
337
|
+
#### `docs` reclassification
|
|
262
338
|
|
|
263
|
-
`
|
|
339
|
+
`docs`/Documentation has moved from the all-audience tier (where it lived before this taxonomy was formalised) to the dev-only Process tier. **Documentation commits no longer appear in public-facing release notes.** They still appear in `CHANGELOG.md` and `changelog.json` under the `audience: 'dev'` classification.
|
|
264
340
|
|
|
265
|
-
|
|
341
|
+
#### `utility` alias
|
|
342
|
+
|
|
343
|
+
`utility:` is a backward-compat alias for `internal:`. Both forms parse to the same canonical type, route to the same `🏗️ Internal features` section, and are subject to the same `!` policy.
|
|
344
|
+
|
|
345
|
+
#### `!` (breaking change) policy
|
|
346
|
+
|
|
347
|
+
Each work-type carries a `breakingPolicy` value:
|
|
348
|
+
|
|
349
|
+
- `optional` (`feat`, `sec`) — `!` is allowed; both `type:` and `type!:` parse cleanly.
|
|
350
|
+
- `forbidden` (most types) — `!` is a policy violation. The premise: types like `internal!`, `perf!`, `fix!` are contradictory; an internal change cannot break a consumer contract, a pure perf change preserves the contract, and a bug-fix is by definition not a contract change.
|
|
351
|
+
- `required` (`drop`) — bare `drop:` is a policy violation; only `drop!:` is accepted. The premise: removing a feature always breaks consumers; the `!` form makes that explicit.
|
|
352
|
+
|
|
353
|
+
##### Two-tier policy enforcement
|
|
354
|
+
|
|
355
|
+
The `!` policy operates at two distinct levels with different semantics:
|
|
356
|
+
|
|
357
|
+
- **Write-time** (commit-msg hook) — strict rejection. Policy violations are blocked at the gate where the author can act on them immediately. _Hook-based enforcement is tracked separately and is not yet shipped._
|
|
358
|
+
- **Release-time** (`parseCommitMessage`) — tolerant warn-and-continue. Commits already in the log cannot be rewritten, so a policy-violating commit is parsed using its canonical type with `breaking: false` (the `!` is dropped from the parse) and a `onPolicyViolation` callback fires. Callers (`decideRelease` etc.) can collect these warnings and surface them in the release report. A single legacy `internal!` in a year-old log does not block releases.
|
|
359
|
+
|
|
360
|
+
A `BREAKING CHANGE:` body footer on a `forbidden`-policy type triggers the same warning path as the prefix `!` does — the spirit of the policy is "internal/perf/etc. cannot be breaking", which must apply to both surfaces.
|
|
361
|
+
|
|
362
|
+
The release-prepare orchestrators (`releasePrepare`, `releasePrepareMono`, `releasePrepareProject`) apply `DEFAULT_BREAKING_POLICIES` automatically. Violations encountered while parsing each workspace's or project's commit window are collected onto the corresponding result's `policyViolations` field and rendered under the section in the prepare report:
|
|
363
|
+
|
|
364
|
+
```
|
|
365
|
+
arrays
|
|
366
|
+
Found 1 commits since arrays-v1.0.0
|
|
367
|
+
⚠️ 1 policy violation:
|
|
368
|
+
· def5678 'internal!: refactor cache' — type 'internal' at prefix surface
|
|
369
|
+
Bumping versions (patch)...
|
|
370
|
+
📦 1.0.0 → 1.0.1 (patch)
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
To customize, set `breakingPolicies` in `release-kit.config.ts` — provide a partial map to override individual types, or `{}` to disable enforcement entirely (the parser falls back to `'optional'` for any missing type). Violations remain warnings, never failures.
|
|
374
|
+
|
|
375
|
+
#### `🚨 **Breaking:**` bullet marker
|
|
376
|
+
|
|
377
|
+
Items whose commit subject carries the `!` prefix (e.g. `feat!`, `drop!`, `feat(api)!`) are rendered with a `🚨 **Breaking:** ` prefix on the bullet:
|
|
378
|
+
|
|
379
|
+
```markdown
|
|
380
|
+
- 🚨 **Breaking:** Drop legacy /v1 endpoint
|
|
381
|
+
```
|
|
382
|
+
|
|
383
|
+
Only the prefix `!` triggers this marker. A `BREAKING CHANGE:` body footer on its own does **not** retroactively mark a changelog item as breaking — the changelog signal is tied to the commit-prefix policy. This avoids surprise breaking-marker appearances for older commits written under earlier conventions.
|
|
384
|
+
|
|
385
|
+
#### `fmt`
|
|
386
|
+
|
|
387
|
+
`fmt:` commits are recognized by `parseCommitMessage` (they contribute to a patch bump) but `fmt` carries `excludedFromChangelog: true`. The bundled `cliff.toml.template` skips `fmt:` commits at the parser level, so they never appear in `CHANGELOG.md`, `changelog.json`, or release notes. The label and emoji are present in `work-types.json` for schema parity with the codeassembly upstream but never render.
|
|
388
|
+
|
|
389
|
+
#### Custom work types
|
|
390
|
+
|
|
391
|
+
Work types from your config are merged with these defaults by key — your entries override or extend, they don't replace the full set. Release-notes sections are rendered in the declaration order of the merged work-types record, with any unknown titles trailing the known ones.
|
|
392
|
+
|
|
393
|
+
The default `devOnlySections` (excluded from public release notes but still written to `CHANGELOG.md`) are derived from the Internal and Process tiers (excluding `fmt`). Override via `changelogJson.devOnlySections` in your config; matching is decorator-tolerant, so a bare-name override like `['Internal features']` keeps working against the emoji-prefixed and prefix-decorated default titles.
|
|
266
394
|
|
|
267
395
|
## CLI reference
|
|
268
396
|
|
|
@@ -277,15 +405,15 @@ Release-notes sections are rendered in the declaration order of the merged work-
|
|
|
277
405
|
|
|
278
406
|
Run release preparation with automatic workspace discovery.
|
|
279
407
|
|
|
280
|
-
| Flag | Description
|
|
281
|
-
| ---------------------------- |
|
|
282
|
-
| `--dry-run` | Preview changes without writing files
|
|
283
|
-
| `--bump=major\|minor\|patch` | Override the bump type for all workspaces
|
|
284
|
-
| `--set-version=X.Y.Z` | Set an explicit canonical semver version; bypasses commit-derived bumps. Requires `--only` in monorepo mode.
|
|
285
|
-
| `--force` |
|
|
286
|
-
| `--only=name1,name2` | Only process the named workspaces (monorepo only)
|
|
287
|
-
| `--with-release-notes` | Write per-workspace release-notes previews under `{workspacePath}/docs/`
|
|
288
|
-
| `--help`, `-h` | Show help
|
|
408
|
+
| Flag | Description |
|
|
409
|
+
| ---------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
410
|
+
| `--dry-run` | Preview changes without writing files |
|
|
411
|
+
| `--bump=major\|minor\|patch` | Override the bump type for all workspaces |
|
|
412
|
+
| `--set-version=X.Y.Z` | Set an explicit canonical semver version; bypasses commit-derived bumps. Requires `--only` in monorepo mode. |
|
|
413
|
+
| `--force` | Release even when no commits or no bump-worthy commits exist since the last tag (defaults to patch; combine with `--bump=X` for a different level) |
|
|
414
|
+
| `--only=name1,name2` | Only process the named workspaces (monorepo only; rejected when a `project` block is configured) |
|
|
415
|
+
| `--with-release-notes` | Write per-workspace release-notes previews under `{workspacePath}/docs/` |
|
|
416
|
+
| `--help`, `-h` | Show help |
|
|
289
417
|
|
|
290
418
|
Workspace names for `--only` match the package directory name (e.g., `arrays`, `release-kit`).
|
|
291
419
|
|
|
@@ -330,6 +458,33 @@ release-kit prepare --only arrays --set-version 1.0.0
|
|
|
330
458
|
|
|
331
459
|
An empty changelog section is expected for a bare promotion, because the changelog is generated from commits since the last tag. To include a narrative entry, land a descriptive release commit (e.g., a `feat!` describing the stable API) before running `prepare`.
|
|
332
460
|
|
|
461
|
+
### `release-kit publish`
|
|
462
|
+
|
|
463
|
+
Publish packages that have release tags on HEAD. The publish workflow's reusable workflow `publish.reusable.yaml` invokes this command in CI.
|
|
464
|
+
|
|
465
|
+
| Flag | Description |
|
|
466
|
+
| ---------------------- | ---------------------------------------------------------------------------- |
|
|
467
|
+
| `--dry-run` | Preview without publishing |
|
|
468
|
+
| `--no-git-checks` | Skip the clean-working-tree check |
|
|
469
|
+
| `--tags=tag1,tag2,...` | Only publish the named tags (comma-separated, full tag names) |
|
|
470
|
+
| `--provenance` | Generate provenance statement (requires OIDC, not supported by classic yarn) |
|
|
471
|
+
| `--help`, `-h` | Show help |
|
|
472
|
+
|
|
473
|
+
#### Publishability filter
|
|
474
|
+
|
|
475
|
+
`publish` operates only on workspaces where `package.json#private` is absent or `false`. A workspace marked `private: true` is "versioned but not published": it can still be tagged by `release-kit tag`, get a `CHANGELOG.md` entry, and get a GitHub Release via `release-kit create-github-release` — only the registry publish step is skipped. Other commands ignore this filter and operate on private workspaces unchanged.
|
|
476
|
+
|
|
477
|
+
The filter behaves differently depending on whether `--tags` is provided:
|
|
478
|
+
|
|
479
|
+
- **Without `--tags`** (implicit resolution): unpublishable tags on HEAD are silently filtered. The pre-publish listing shows only the publishable subset. If the filter empties the set, `release-kit publish` prints `Nothing to publish.` and exits 0.
|
|
480
|
+
- **With `--tags`** (explicit naming): if any named tag points at an unpublishable workspace, `release-kit publish` exits 1 with one error line per unpublishable tag, citing `package.json#private`. Explicit naming surfaces the contradiction rather than silently dropping the tag.
|
|
481
|
+
|
|
482
|
+
Example output when an explicit tag is unpublishable:
|
|
483
|
+
|
|
484
|
+
```
|
|
485
|
+
Error: basic-v1.0.0 (packages/basic) cannot be published: package.json#private is true.
|
|
486
|
+
```
|
|
487
|
+
|
|
333
488
|
### `release-kit create-github-release`
|
|
334
489
|
|
|
335
490
|
Create GitHub Releases from `changelog.json` for tags on HEAD. Independent of `npm publish`: invoking this command creates Releases regardless of whether the matching package was published.
|
|
@@ -373,6 +528,28 @@ Scaffolded files:
|
|
|
373
528
|
- `.config/release-kit.config.ts` — starter config with commented-out customization examples (with `--with-config`)
|
|
374
529
|
- `.config/git-cliff.toml` — copied from the bundled template (with `--with-config`)
|
|
375
530
|
|
|
531
|
+
### `release-kit work-types`
|
|
532
|
+
|
|
533
|
+
Manage the canonical work-types taxonomy used by changelog and release-notes generation.
|
|
534
|
+
|
|
535
|
+
| Subcommand | Description |
|
|
536
|
+
| ---------- | ----------------------------------------------------------------------------------- |
|
|
537
|
+
| `check` | Compare the local `work-types.json` against the upstream codeassembly canonical |
|
|
538
|
+
| `sync` | Overwrite the local `work-types.json` with the upstream contents (after validation) |
|
|
539
|
+
|
|
540
|
+
`check` exit codes:
|
|
541
|
+
|
|
542
|
+
| Code | Meaning |
|
|
543
|
+
| ---- | --------------------------------------------------------------------------------- |
|
|
544
|
+
| `0` | Match (or upstream missing — transitional warning printed) |
|
|
545
|
+
| `1` | Drift detected |
|
|
546
|
+
| `2` | Network error or non-OK HTTP response |
|
|
547
|
+
| `3` | Schema mismatch (upstream JSON does not parse or fails the top-level shape check) |
|
|
548
|
+
|
|
549
|
+
The check is non-blocking initially: until codeassembly publishes its `work-types.json`, the upstream URL returns 404 and `check` exits 0 with a warning. CI flip to a blocking check is tracked as a follow-up once the upstream ships.
|
|
550
|
+
|
|
551
|
+
These commands are also exposed as `nmr work-types:check` / `nmr work-types:sync` from any package directory.
|
|
552
|
+
|
|
376
553
|
### `release-kit sync-labels`
|
|
377
554
|
|
|
378
555
|
Manage GitHub label definitions via config-driven YAML files.
|
|
@@ -385,6 +562,26 @@ Manage GitHub label definitions via config-driven YAML files.
|
|
|
385
562
|
|
|
386
563
|
`init` scaffolds `.config/sync-labels.config.ts` with auto-detected workspace scope labels and a `.github/workflows/sync-labels.yaml` caller workflow, then generates `.github/labels.yaml`. `generate` reads the config and writes `.github/labels.yaml`. `sync` triggers the workflow remotely — it requires the `gh` CLI and an existing workflow file.
|
|
387
564
|
|
|
565
|
+
#### Published JSON Schema for `.meta/label-map.json`
|
|
566
|
+
|
|
567
|
+
release-kit publishes a JSON Schema for `.meta/label-map.json` — a separate, generic data file that maps commit-prefix scopes and types to GitHub label names. The schema lives at `packages/release-kit/schemas/label-map.json` in this repo and is reachable via the stable raw URL:
|
|
568
|
+
|
|
569
|
+
```
|
|
570
|
+
https://github.com/williamthorsen/node-monorepo-tools/raw/release-kit-v<version>/packages/release-kit/schemas/label-map.json
|
|
571
|
+
```
|
|
572
|
+
|
|
573
|
+
Consumers reference it from the top of their `.meta/label-map.json`:
|
|
574
|
+
|
|
575
|
+
```json
|
|
576
|
+
{
|
|
577
|
+
"$schema": "https://github.com/williamthorsen/node-monorepo-tools/raw/release-kit-v<version>/packages/release-kit/schemas/label-map.json",
|
|
578
|
+
"types": { "feat": "feature", "fix": "fix" },
|
|
579
|
+
"scopes": { "audit": "scope:audit" }
|
|
580
|
+
}
|
|
581
|
+
```
|
|
582
|
+
|
|
583
|
+
release-kit publishes the schema only; it does not generate `.meta/label-map.json`. Generation requires commit-prefix knowledge that lives outside release-kit (in agent-conventions tooling), and is owned by those consumers.
|
|
584
|
+
|
|
388
585
|
## GitHub Actions workflow
|
|
389
586
|
|
|
390
587
|
The `init` command scaffolds a release workflow at `.github/workflows/release.yaml` that delegates to a reusable release workflow. The scaffolded workflow accepts these inputs:
|
package/cliff.toml.template
CHANGED
|
@@ -10,6 +10,13 @@
|
|
|
10
10
|
# Only ticketed commits (leading #NN, PROJ-NN, or ##) are included.
|
|
11
11
|
# Unticketed maintenance commits (deps upgrades, tooling tweaks) are skipped.
|
|
12
12
|
# Use ## as a synthetic ticket prefix for ad-hoc commits that belong in the changelog.
|
|
13
|
+
#
|
|
14
|
+
# Section order: each `group` value carries a hidden `<!-- NN -->` HTML-comment
|
|
15
|
+
# prefix encoding the canonical row position. tera's `group_by` filter sorts
|
|
16
|
+
# groups lexicographically by string, and the body template's `striptags`
|
|
17
|
+
# filter erases the comment from the rendered heading. Numbering is per
|
|
18
|
+
# unique group (not per parser entry) — all parsers routing to the same group
|
|
19
|
+
# share the same prefix.
|
|
13
20
|
|
|
14
21
|
[changelog]
|
|
15
22
|
header = """
|
|
@@ -61,24 +68,26 @@ commit_preprocessors = []
|
|
|
61
68
|
commit_parsers = [
|
|
62
69
|
{ message = "^release:", skip = true },
|
|
63
70
|
{ message = "^Merge", skip = true },
|
|
64
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
65
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
66
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
67
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?deprecate(!)?:", group = "Deprecated" },
|
|
68
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
69
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
70
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
71
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
72
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?
|
|
71
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?feat(!)?:", group = "<!-- 01 -->🎉 Features" },
|
|
72
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?feature(!)?:", group = "<!-- 01 -->🎉 Features" },
|
|
73
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?drop(!)?:", group = "<!-- 02 -->🪦 Removed" },
|
|
74
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?deprecate(!)?:", group = "<!-- 03 -->🗑️ Deprecated" },
|
|
75
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?fix(!)?:", group = "<!-- 04 -->🐛 Bug fixes" },
|
|
76
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?bugfix(!)?:", group = "<!-- 04 -->🐛 Bug fixes" },
|
|
77
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?sec(!)?:", group = "<!-- 05 -->🔒 Security" },
|
|
78
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?security(!)?:", group = "<!-- 05 -->🔒 Security" },
|
|
79
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?perf(!)?:", group = "<!-- 06 -->⚡ Performance" },
|
|
80
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?performance(!)?:", group = "<!-- 06 -->⚡ Performance" },
|
|
81
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?internal(!)?:", group = "<!-- 07 -->🏗️ Internal features" },
|
|
82
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?utility(!)?:", group = "<!-- 07 -->🏗️ Internal features" },
|
|
83
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?refactor(!)?:", group = "<!-- 08 -->♻️ Refactoring" },
|
|
84
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?tests?(!)?:", group = "<!-- 09 -->🧪 Tests" },
|
|
85
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?tooling(!)?:", group = "<!-- 10 -->⚙️ Tooling" },
|
|
86
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?ci(!)?:", group = "<!-- 11 -->👷 CI" },
|
|
87
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?deps?(!)?:", group = "<!-- 12 -->📦 Dependencies" },
|
|
88
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?ai(!)?:", group = "<!-- 13 -->🤖 Agentic support" },
|
|
89
|
+
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?docs?(!)?:", group = "<!-- 14 -->📚 Documentation" },
|
|
73
90
|
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?fmt(!)?:", skip = true },
|
|
74
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?internal(!)?:", group = "Internal" },
|
|
75
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?perf(!)?:", group = "Performance" },
|
|
76
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?performance(!)?:", group = "Performance" },
|
|
77
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?refactor(!)?:", group = "Refactoring" },
|
|
78
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?sec(!)?:", group = "Security" },
|
|
79
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?security(!)?:", group = "Security" },
|
|
80
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?tests?(!)?:", group = "Tests" },
|
|
81
|
-
{ message = "^(\\#\\d+([.\\-]\\d+)?|\\#\\#|[A-Z]+-\\d+)\\s+([\\w-]+\\|)?tooling(!)?:", group = "Tooling" },
|
|
82
91
|
# Skip unticketed commits (maintenance, deps, initial scaffolding, etc.)
|
|
83
92
|
{ message = ".*", skip = true },
|
|
84
93
|
]
|
package/dist/esm/.cache
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
|
|
1
|
+
64d26b06f4a6e205faa07a507fd64938899e4d635dd02b333016caf1d937a14e
|
|
@@ -6,7 +6,7 @@ function assertCleanWorkingTree() {
|
|
|
6
6
|
}).trim();
|
|
7
7
|
if (status.length > 0) {
|
|
8
8
|
throw new Error(
|
|
9
|
-
"Working tree has uncommitted changes. Commit or stash them
|
|
9
|
+
"Working tree has uncommitted changes. Commit or stash them, or use --no-git-checks to bypass this check."
|
|
10
10
|
);
|
|
11
11
|
}
|
|
12
12
|
}
|