@williamthorsen/release-kit 6.0.0 → 7.0.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 +8 -0
- package/README.md +3 -3
- package/dist/esm/.cache +1 -1
- package/dist/esm/assertCleanWorkingTree.js +9 -14
- package/dist/esm/bin/release-kit.js +200 -199
- package/dist/esm/buildChangelogEntries.d.ts +2 -2
- package/dist/esm/buildChangelogEntries.js +142 -149
- package/dist/esm/buildDependencyGraph.d.ts +1 -1
- package/dist/esm/buildDependencyGraph.js +60 -59
- package/dist/esm/buildEmptyReleaseEntry.d.ts +1 -1
- package/dist/esm/buildEmptyReleaseEntry.js +12 -15
- package/dist/esm/buildReleaseSummary.d.ts +1 -1
- package/dist/esm/buildReleaseSummary.js +23 -26
- package/dist/esm/buildSyntheticChangelogEntry.d.ts +1 -1
- package/dist/esm/buildSyntheticChangelogEntry.js +9 -12
- package/dist/esm/bumpAllVersions.d.ts +1 -1
- package/dist/esm/bumpAllVersions.js +51 -52
- package/dist/esm/bumpVersion.d.ts +1 -1
- package/dist/esm/bumpVersion.js +25 -28
- package/dist/esm/changelogJsonFile.d.ts +1 -1
- package/dist/esm/changelogJsonFile.js +59 -62
- package/dist/esm/changelogJsonUtils.d.ts +1 -1
- package/dist/esm/changelogJsonUtils.js +35 -32
- package/dist/esm/changelogOverrides.d.ts +1 -1
- package/dist/esm/changelogOverrides.js +374 -377
- package/dist/esm/checkWorkTypesDrift.js +104 -102
- package/dist/esm/collectPolicyViolations.d.ts +2 -2
- package/dist/esm/collectPolicyViolations.js +11 -14
- package/dist/esm/commitCommand.js +48 -46
- package/dist/esm/compareVersions.js +20 -23
- package/dist/esm/createGithubRelease.js +56 -59
- package/dist/esm/createGithubReleaseCommand.js +21 -23
- package/dist/esm/createTags.js +57 -56
- package/dist/esm/decideRelease.d.ts +2 -2
- package/dist/esm/decideRelease.js +27 -41
- package/dist/esm/defaults.d.ts +3 -3
- package/dist/esm/defaults.js +36 -48
- package/dist/esm/deleteFileIfExists.js +10 -12
- package/dist/esm/deriveWorkspaceConfig.d.ts +1 -1
- package/dist/esm/deriveWorkspaceConfig.js +34 -36
- package/dist/esm/detectPackageManager.js +35 -37
- package/dist/esm/detectUndeclaredTagPrefixes.js +41 -40
- package/dist/esm/determineBumpFromCommits.d.ts +2 -2
- package/dist/esm/determineBumpFromCommits.js +25 -29
- package/dist/esm/determineBumpType.d.ts +1 -1
- package/dist/esm/determineBumpType.js +31 -32
- package/dist/esm/discoverWorkspaces.js +38 -40
- package/dist/esm/format.js +6 -11
- package/dist/esm/generateChangelogs.d.ts +1 -1
- package/dist/esm/generateChangelogs.js +13 -17
- package/dist/esm/getCommitsSinceTarget.d.ts +1 -1
- package/dist/esm/getCommitsSinceTarget.js +54 -55
- package/dist/esm/hasPrettierConfig.js +33 -35
- package/dist/esm/help/prepareHelp.js +4 -8
- package/dist/esm/index.d.ts +4 -4
- package/dist/esm/index.js +2 -8
- package/dist/esm/init/checks.js +28 -32
- package/dist/esm/init/detectRepoType.js +12 -15
- package/dist/esm/init/initCommand.js +60 -54
- package/dist/esm/init/parseJsonRecord.js +9 -11
- package/dist/esm/init/scaffold.d.ts +1 -1
- package/dist/esm/init/scaffold.js +32 -38
- package/dist/esm/init/templates.d.ts +1 -1
- package/dist/esm/init/templates.js +16 -22
- package/dist/esm/injectReleaseNotesIntoReadme.js +42 -49
- package/dist/esm/injectSection.js +17 -27
- package/dist/esm/loadConfig.d.ts +1 -1
- package/dist/esm/loadConfig.js +206 -225
- package/dist/esm/parseCommitMessage.d.ts +1 -1
- package/dist/esm/parseCommitMessage.js +72 -76
- package/dist/esm/parseRequestedTags.js +6 -9
- package/dist/esm/prepareCommand.d.ts +1 -1
- package/dist/esm/prepareCommand.js +225 -235
- package/dist/esm/previewTagPrefixes.d.ts +1 -1
- package/dist/esm/previewTagPrefixes.js +101 -96
- package/dist/esm/propagateBumps.d.ts +2 -2
- package/dist/esm/propagateBumps.js +48 -50
- package/dist/esm/publish.d.ts +2 -2
- package/dist/esm/publish.js +22 -28
- package/dist/esm/publishCommand.js +75 -80
- package/dist/esm/pushCommand.js +33 -34
- package/dist/esm/pushRelease.d.ts +1 -1
- package/dist/esm/pushRelease.js +21 -24
- package/dist/esm/readCurrentVersion.js +13 -17
- package/dist/esm/releasePrepare.d.ts +1 -1
- package/dist/esm/releasePrepare.js +213 -231
- package/dist/esm/releasePrepareMono.d.ts +2 -2
- package/dist/esm/releasePrepareMono.js +434 -494
- package/dist/esm/releasePrepareProject.d.ts +2 -2
- package/dist/esm/releasePrepareProject.js +143 -153
- package/dist/esm/renderChangelogMarkdown.d.ts +1 -1
- package/dist/esm/renderChangelogMarkdown.js +20 -24
- package/dist/esm/renderReleaseNotes.d.ts +1 -1
- package/dist/esm/renderReleaseNotes.js +50 -55
- package/dist/esm/reportPrepare.d.ts +1 -1
- package/dist/esm/reportPrepare.js +230 -231
- package/dist/esm/resolveCliffConfigPath.js +18 -23
- package/dist/esm/resolveCommandTags.d.ts +1 -1
- package/dist/esm/resolveCommandTags.js +47 -45
- package/dist/esm/resolveReleaseNotesConfig.d.ts +1 -1
- package/dist/esm/resolveReleaseNotesConfig.js +39 -43
- package/dist/esm/resolveReleaseTags.d.ts +1 -1
- package/dist/esm/resolveReleaseTags.js +39 -40
- package/dist/esm/runGitCliff.js +27 -30
- package/dist/esm/showTagPrefixesCommand.js +48 -70
- package/dist/esm/stripEmojiPrefix.js +2 -5
- package/dist/esm/stripScope.js +18 -21
- package/dist/esm/sync-labels/generateCommand.d.ts +1 -1
- package/dist/esm/sync-labels/generateCommand.js +51 -53
- package/dist/esm/sync-labels/initCommand.js +46 -48
- package/dist/esm/sync-labels/loadSyncLabelsConfig.d.ts +1 -1
- package/dist/esm/sync-labels/loadSyncLabelsConfig.js +46 -52
- package/dist/esm/sync-labels/presets.d.ts +1 -1
- package/dist/esm/sync-labels/presets.js +40 -43
- package/dist/esm/sync-labels/resolveLabels.d.ts +1 -1
- package/dist/esm/sync-labels/resolveLabels.js +28 -35
- package/dist/esm/sync-labels/syncCommand.js +30 -31
- package/dist/esm/sync-labels/templates.d.ts +1 -1
- package/dist/esm/sync-labels/templates.js +23 -26
- package/dist/esm/sync-labels/types.js +1 -0
- package/dist/esm/syncWorkTypes.js +83 -84
- package/dist/esm/tagCommand.js +12 -14
- package/dist/esm/typeGuards.js +4 -8
- package/dist/esm/types.js +66 -60
- package/dist/esm/validateConfig.d.ts +1 -1
- package/dist/esm/validateConfig.js +109 -115
- package/dist/esm/validateOnlyExcludesStrandedDependents.d.ts +2 -2
- package/dist/esm/validateOnlyExcludesStrandedDependents.js +97 -91
- package/dist/esm/validateOverridesCommand.d.ts +2 -2
- package/dist/esm/validateOverridesCommand.js +110 -111
- package/dist/esm/workTypesData.js +57 -60
- package/dist/esm/workTypesUtils.js +16 -21
- package/dist/esm/writeReleaseNotesPreviews.js +55 -57
- package/package.json +2 -2
|
@@ -1,10 +1,7 @@
|
|
|
1
|
-
function parseRequestedTags(flagValue) {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
1
|
+
export function parseRequestedTags(flagValue) {
|
|
2
|
+
if (flagValue === undefined) {
|
|
3
|
+
return undefined;
|
|
4
|
+
}
|
|
5
|
+
const segments = flagValue.split(',').filter(Boolean);
|
|
6
|
+
return segments.length === 0 ? undefined : segments;
|
|
7
7
|
}
|
|
8
|
-
export {
|
|
9
|
-
parseRequestedTags
|
|
10
|
-
};
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { WriteResult } from '@williamthorsen/nmr-core';
|
|
2
|
-
import type { ReleaseType } from './types.
|
|
2
|
+
import type { ReleaseType } from './types.js';
|
|
3
3
|
export declare const RELEASE_TAGS_FILE = "tmp/.release-tags";
|
|
4
4
|
export declare const RELEASE_SUMMARY_FILE = "tmp/.release-summary";
|
|
5
5
|
export declare const prepareFlagSchema: {
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { parseArgsOrExit, reportError, writeFileWithCheck } from
|
|
1
|
+
import { parseArgsOrExit, reportError, writeFileWithCheck } from '@williamthorsen/nmr-core';
|
|
2
2
|
import { assertCleanWorkingTree } from "./assertCleanWorkingTree.js";
|
|
3
3
|
import { buildDependencyGraph } from "./buildDependencyGraph.js";
|
|
4
4
|
import { buildReleaseSummary } from "./buildReleaseSummary.js";
|
|
@@ -11,265 +11,255 @@ import { releasePrepareMono } from "./releasePrepareMono.js";
|
|
|
11
11
|
import { reportPrepare } from "./reportPrepare.js";
|
|
12
12
|
import { validateConfig } from "./validateConfig.js";
|
|
13
13
|
import { validateOnlyExcludesStrandedDependents } from "./validateOnlyExcludesStrandedDependents.js";
|
|
14
|
-
const RELEASE_TAGS_FILE =
|
|
15
|
-
const RELEASE_SUMMARY_FILE =
|
|
16
|
-
const VALID_BUMP_TYPES = [
|
|
14
|
+
export const RELEASE_TAGS_FILE = 'tmp/.release-tags';
|
|
15
|
+
export const RELEASE_SUMMARY_FILE = 'tmp/.release-summary';
|
|
16
|
+
const VALID_BUMP_TYPES = ['major', 'minor', 'patch'];
|
|
17
17
|
const CANONICAL_SEMVER_PATTERN = /^\d+\.\d+\.\d+$/;
|
|
18
18
|
function isReleaseType(value) {
|
|
19
|
-
|
|
19
|
+
return VALID_BUMP_TYPES.includes(value);
|
|
20
20
|
}
|
|
21
|
-
const prepareFlagSchema = {
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
21
|
+
export const prepareFlagSchema = {
|
|
22
|
+
dryRun: { long: '--dry-run', type: 'boolean' },
|
|
23
|
+
force: { long: '--force', type: 'boolean' },
|
|
24
|
+
noGitChecks: {
|
|
25
|
+
long: '--no-git-checks',
|
|
26
|
+
type: 'boolean',
|
|
27
|
+
short: '-n',
|
|
28
|
+
},
|
|
29
|
+
bump: { long: '--bump', type: 'string' },
|
|
30
|
+
setVersion: { long: '--set-version', type: 'string' },
|
|
31
|
+
only: { long: '--only', type: 'string' },
|
|
32
|
+
withReleaseNotes: { long: '--with-release-notes', type: 'boolean' },
|
|
33
33
|
};
|
|
34
|
-
function parseArgs(argv) {
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
34
|
+
export function parseArgs(argv) {
|
|
35
|
+
const { flags } = parseArgsOrExit(argv, prepareFlagSchema);
|
|
36
|
+
let bumpOverride;
|
|
37
|
+
if (flags.bump !== undefined) {
|
|
38
|
+
if (!isReleaseType(flags.bump)) {
|
|
39
|
+
reportError(`Invalid bump type "${flags.bump}". Must be one of: ${VALID_BUMP_TYPES.join(', ')}`);
|
|
40
|
+
process.exit(1);
|
|
41
|
+
}
|
|
42
|
+
bumpOverride = flags.bump;
|
|
41
43
|
}
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
);
|
|
50
|
-
process.exit(1);
|
|
44
|
+
let setVersion;
|
|
45
|
+
if (flags.setVersion !== undefined) {
|
|
46
|
+
if (!CANONICAL_SEMVER_PATTERN.test(flags.setVersion)) {
|
|
47
|
+
reportError(`Invalid --set-version value "${flags.setVersion}". Must be canonical semver (N.N.N, no pre-release suffix).`);
|
|
48
|
+
process.exit(1);
|
|
49
|
+
}
|
|
50
|
+
setVersion = flags.setVersion;
|
|
51
51
|
}
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
withReleaseNotes: flags.withReleaseNotes
|
|
74
|
-
};
|
|
52
|
+
let only;
|
|
53
|
+
if (flags.only !== undefined) {
|
|
54
|
+
only = flags.only.split(',');
|
|
55
|
+
}
|
|
56
|
+
if (setVersion !== undefined && bumpOverride !== undefined) {
|
|
57
|
+
reportError('--set-version cannot be combined with --bump');
|
|
58
|
+
process.exit(1);
|
|
59
|
+
}
|
|
60
|
+
if (setVersion !== undefined && flags.force) {
|
|
61
|
+
reportError('--set-version cannot be combined with --force');
|
|
62
|
+
process.exit(1);
|
|
63
|
+
}
|
|
64
|
+
return {
|
|
65
|
+
dryRun: flags.dryRun,
|
|
66
|
+
force: flags.force,
|
|
67
|
+
noGitChecks: flags.noGitChecks,
|
|
68
|
+
bumpOverride,
|
|
69
|
+
only,
|
|
70
|
+
setVersion,
|
|
71
|
+
withReleaseNotes: flags.withReleaseNotes,
|
|
72
|
+
};
|
|
75
73
|
}
|
|
76
|
-
function writeReleaseTags(tags, dryRun) {
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
74
|
+
export function writeReleaseTags(tags, dryRun) {
|
|
75
|
+
if (tags.length === 0) {
|
|
76
|
+
return undefined;
|
|
77
|
+
}
|
|
78
|
+
return writeFileWithCheck(RELEASE_TAGS_FILE, tags.join('\n'), {
|
|
79
|
+
dryRun,
|
|
80
|
+
overwrite: true,
|
|
81
|
+
});
|
|
84
82
|
}
|
|
85
|
-
async function prepareCommand(argv) {
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
83
|
+
export async function prepareCommand(argv) {
|
|
84
|
+
const { dryRun, force, noGitChecks, bumpOverride, only, setVersion, withReleaseNotes } = parseArgs(argv);
|
|
85
|
+
const options = {
|
|
86
|
+
dryRun,
|
|
87
|
+
force,
|
|
88
|
+
...(bumpOverride === undefined ? {} : { bumpOverride }),
|
|
89
|
+
...(setVersion === undefined ? {} : { setVersion }),
|
|
90
|
+
...(withReleaseNotes ? { withReleaseNotes: true } : {}),
|
|
91
|
+
};
|
|
92
|
+
if (dryRun) {
|
|
93
|
+
console.info('\n🔍 DRY RUN — no files will be modified\n');
|
|
94
|
+
}
|
|
95
|
+
if (!dryRun && !noGitChecks) {
|
|
96
|
+
try {
|
|
97
|
+
assertCleanWorkingTree();
|
|
98
|
+
}
|
|
99
|
+
catch (error) {
|
|
100
|
+
reportError(error instanceof Error ? error.message : String(error));
|
|
101
|
+
process.exit(1);
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
const userConfig = await loadAndValidateConfig();
|
|
105
|
+
let discoveredPaths;
|
|
98
106
|
try {
|
|
99
|
-
|
|
100
|
-
}
|
|
101
|
-
|
|
102
|
-
|
|
107
|
+
discoveredPaths = await discoverWorkspaces();
|
|
108
|
+
}
|
|
109
|
+
catch (error) {
|
|
110
|
+
reportError(`Failed to discover workspaces: ${error instanceof Error ? error.message : String(error)}`);
|
|
111
|
+
process.exit(1);
|
|
112
|
+
}
|
|
113
|
+
if (discoveredPaths === undefined) {
|
|
114
|
+
runSinglePackageMode(userConfig, options, only, dryRun);
|
|
115
|
+
}
|
|
116
|
+
else {
|
|
117
|
+
runMonorepoMode(discoveredPaths, userConfig, options, only, setVersion, dryRun);
|
|
103
118
|
}
|
|
104
|
-
}
|
|
105
|
-
const userConfig = await loadAndValidateConfig();
|
|
106
|
-
let discoveredPaths;
|
|
107
|
-
try {
|
|
108
|
-
discoveredPaths = await discoverWorkspaces();
|
|
109
|
-
} catch (error) {
|
|
110
|
-
reportError(`Failed to discover workspaces: ${error instanceof Error ? error.message : String(error)}`);
|
|
111
|
-
process.exit(1);
|
|
112
|
-
}
|
|
113
|
-
if (discoveredPaths === void 0) {
|
|
114
|
-
runSinglePackageMode(userConfig, options, only, dryRun);
|
|
115
|
-
} else {
|
|
116
|
-
runMonorepoMode(discoveredPaths, userConfig, options, only, setVersion, dryRun);
|
|
117
|
-
}
|
|
118
119
|
}
|
|
119
120
|
function runSinglePackageMode(userConfig, options, only, dryRun) {
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
runAndReport(() => releasePrepare(config, options), dryRun);
|
|
121
|
+
if (only !== undefined) {
|
|
122
|
+
reportError('--only is only supported for monorepo configurations');
|
|
123
|
+
process.exit(1);
|
|
124
|
+
}
|
|
125
|
+
if (options.force && options.bumpOverride === undefined) {
|
|
126
|
+
reportError('--force without --bump is only supported for monorepo configurations. ' +
|
|
127
|
+
'Use --bump=major|minor|patch to set the level for a single-package release.');
|
|
128
|
+
process.exit(1);
|
|
129
|
+
}
|
|
130
|
+
const config = mergeSinglePackageConfig(userConfig);
|
|
131
|
+
runAndReport(() => releasePrepare(config, options), dryRun);
|
|
132
132
|
}
|
|
133
133
|
function runMonorepoMode(discoveredPaths, userConfig, options, only, setVersion, dryRun) {
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
}
|
|
142
|
-
if (setVersion !== void 0 && config.project !== void 0) {
|
|
143
|
-
reportError(
|
|
144
|
-
"--set-version cannot be combined with a project release. --set-version operates on a single workspace; a project release rolls up every contributing workspace. To use --set-version, run on a config without a `project` block."
|
|
145
|
-
);
|
|
146
|
-
process.exit(1);
|
|
147
|
-
}
|
|
148
|
-
if (only !== void 0 && config.project !== void 0) {
|
|
149
|
-
reportError(
|
|
150
|
-
"--only cannot be combined with a project release. To release a single workspace, use a config without a `project` block, or run a full `prepare` (no --only) to include the project release."
|
|
151
|
-
);
|
|
152
|
-
process.exit(1);
|
|
153
|
-
}
|
|
154
|
-
if (only !== void 0) {
|
|
155
|
-
const knownNames = config.workspaces.map((w) => w.dir);
|
|
156
|
-
for (const name of only) {
|
|
157
|
-
if (!knownNames.includes(name)) {
|
|
158
|
-
reportError(`Unknown workspace "${name}". Known workspaces: ${knownNames.join(", ")}`);
|
|
134
|
+
let config;
|
|
135
|
+
try {
|
|
136
|
+
const rootPackage = readRootPackageVersion();
|
|
137
|
+
config = mergeMonorepoConfig(discoveredPaths, userConfig, rootPackage);
|
|
138
|
+
}
|
|
139
|
+
catch (error) {
|
|
140
|
+
reportError(`Failed to resolve workspaces: ${error instanceof Error ? error.message : String(error)}`);
|
|
159
141
|
process.exit(1);
|
|
160
|
-
}
|
|
161
142
|
}
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
process.stderr.write("The following packages must be added to --only or have their dependencies removed:\n");
|
|
174
|
-
for (const violation of violations) {
|
|
175
|
-
const since = violation.tag ?? "the beginning";
|
|
176
|
-
process.stderr.write(
|
|
177
|
-
` - ${violation.dir} (downstream of ${violation.downstreamOf}; has commits since ${since})
|
|
178
|
-
`
|
|
179
|
-
);
|
|
180
|
-
}
|
|
181
|
-
process.stderr.write("Alternatively, run `release-kit prepare` without --only to release everything.\n");
|
|
182
|
-
process.exit(1);
|
|
143
|
+
if (setVersion !== undefined && config.project !== undefined) {
|
|
144
|
+
reportError('--set-version cannot be combined with a project release. ' +
|
|
145
|
+
'--set-version operates on a single workspace; a project release rolls up every ' +
|
|
146
|
+
'contributing workspace. To use --set-version, run on a config without a `project` block.');
|
|
147
|
+
process.exit(1);
|
|
148
|
+
}
|
|
149
|
+
if (only !== undefined && config.project !== undefined) {
|
|
150
|
+
reportError('--only cannot be combined with a project release. ' +
|
|
151
|
+
'To release a single workspace, use a config without a `project` block, ' +
|
|
152
|
+
'or run a full `prepare` (no --only) to include the project release.');
|
|
153
|
+
process.exit(1);
|
|
183
154
|
}
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
155
|
+
if (only !== undefined) {
|
|
156
|
+
const knownNames = config.workspaces.map((w) => w.dir);
|
|
157
|
+
for (const name of only) {
|
|
158
|
+
if (!knownNames.includes(name)) {
|
|
159
|
+
reportError(`Unknown workspace "${name}". Known workspaces: ${knownNames.join(', ')}`);
|
|
160
|
+
process.exit(1);
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
const graph = buildDependencyGraph(config.workspaces);
|
|
164
|
+
const violations = validateOnlyExcludesStrandedDependents(config.workspaces, only, graph, (workspace) => {
|
|
165
|
+
const tagPrefixes = [
|
|
166
|
+
workspace.tagPrefix,
|
|
167
|
+
...(workspace.legacyIdentities?.map((identity) => identity.tagPrefix) ?? []),
|
|
168
|
+
];
|
|
169
|
+
const result = getCommitsSinceTarget(tagPrefixes, workspace.paths);
|
|
170
|
+
return { has: result.commits.length > 0, tag: result.tag };
|
|
171
|
+
});
|
|
172
|
+
if (violations !== undefined) {
|
|
173
|
+
reportError('--only excludes packages with changes that would be stranded by the release.');
|
|
174
|
+
process.stderr.write('The following packages must be added to --only or have their dependencies removed:\n');
|
|
175
|
+
for (const violation of violations) {
|
|
176
|
+
const since = violation.tag ?? 'the beginning';
|
|
177
|
+
process.stderr.write(` - ${violation.dir} (downstream of ${violation.downstreamOf}; has commits since ${since})\n`);
|
|
178
|
+
}
|
|
179
|
+
process.stderr.write('Alternatively, run `release-kit prepare` without --only to release everything.\n');
|
|
180
|
+
process.exit(1);
|
|
181
|
+
}
|
|
182
|
+
config.workspaces = config.workspaces.filter((w) => only.includes(w.dir));
|
|
190
183
|
}
|
|
191
|
-
if (
|
|
192
|
-
|
|
193
|
-
|
|
184
|
+
if (setVersion !== undefined) {
|
|
185
|
+
if (only === undefined) {
|
|
186
|
+
reportError('--set-version requires --only in monorepo mode');
|
|
187
|
+
process.exit(1);
|
|
188
|
+
}
|
|
189
|
+
if (config.workspaces.length !== 1) {
|
|
190
|
+
reportError(`--set-version requires --only to match exactly one workspace; matched ${config.workspaces.length}`);
|
|
191
|
+
process.exit(1);
|
|
192
|
+
}
|
|
194
193
|
}
|
|
195
|
-
|
|
196
|
-
runAndReport(() => releasePrepareMono(config, options), dryRun);
|
|
194
|
+
runAndReport(() => releasePrepareMono(config, options), dryRun);
|
|
197
195
|
}
|
|
198
196
|
async function loadAndValidateConfig() {
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
203
|
-
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
`);
|
|
197
|
+
let rawConfig;
|
|
198
|
+
try {
|
|
199
|
+
rawConfig = await loadConfig();
|
|
200
|
+
}
|
|
201
|
+
catch (error) {
|
|
202
|
+
reportError(`Failed to load config: ${error instanceof Error ? error.message : String(error)}`);
|
|
203
|
+
process.exit(1);
|
|
204
|
+
}
|
|
205
|
+
if (rawConfig === undefined) {
|
|
206
|
+
return undefined;
|
|
207
|
+
}
|
|
208
|
+
const { config, errors, warnings } = validateConfig(rawConfig);
|
|
209
|
+
if (errors.length > 0) {
|
|
210
|
+
process.stderr.write('Invalid config:\n');
|
|
211
|
+
for (const err of errors) {
|
|
212
|
+
process.stderr.write(` ❌ ${err}\n`);
|
|
213
|
+
}
|
|
214
|
+
process.exit(1);
|
|
215
|
+
}
|
|
216
|
+
for (const warning of warnings) {
|
|
217
|
+
console.warn(` ⚠️ ${warning}`);
|
|
215
218
|
}
|
|
216
|
-
|
|
217
|
-
}
|
|
218
|
-
for (const warning of warnings) {
|
|
219
|
-
console.warn(` \u26A0\uFE0F ${warning}`);
|
|
220
|
-
}
|
|
221
|
-
return config;
|
|
219
|
+
return config;
|
|
222
220
|
}
|
|
223
221
|
function runAndReport(execute, dryRun) {
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
} catch (error) {
|
|
228
|
-
reportError(error instanceof Error ? error.message : String(error));
|
|
229
|
-
process.exit(1);
|
|
230
|
-
}
|
|
231
|
-
process.stdout.write(reportPrepare(result) + "\n");
|
|
232
|
-
const writeResult = writeReleaseTags(result.tags, dryRun);
|
|
233
|
-
if (writeResult?.outcome === "failed") {
|
|
234
|
-
reportError(`Failed to write release tags: ${writeResult.error ?? "unknown error"}`);
|
|
235
|
-
process.exit(1);
|
|
236
|
-
}
|
|
237
|
-
if (writeResult) {
|
|
238
|
-
if (dryRun) {
|
|
239
|
-
console.info(dim(` [dry-run] Would write ${RELEASE_TAGS_FILE}: ${result.tags.join(" ")}`));
|
|
240
|
-
} else {
|
|
241
|
-
console.info(dim(` Wrote ${RELEASE_TAGS_FILE}: ${result.tags.join(" ")}`));
|
|
242
|
-
console.info(dim(`
|
|
243
|
-
Release tags file: ${RELEASE_TAGS_FILE}`));
|
|
222
|
+
let result;
|
|
223
|
+
try {
|
|
224
|
+
result = execute();
|
|
244
225
|
}
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
const summaryResult = writeFileWithCheck(RELEASE_SUMMARY_FILE, summary, {
|
|
249
|
-
dryRun,
|
|
250
|
-
overwrite: true
|
|
251
|
-
});
|
|
252
|
-
if (summaryResult.outcome === "failed") {
|
|
253
|
-
reportError(`Failed to write release summary: ${summaryResult.error ?? "unknown error"}`);
|
|
254
|
-
process.exit(1);
|
|
226
|
+
catch (error) {
|
|
227
|
+
reportError(error instanceof Error ? error.message : String(error));
|
|
228
|
+
process.exit(1);
|
|
255
229
|
}
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
230
|
+
process.stdout.write(reportPrepare(result) + '\n');
|
|
231
|
+
const writeResult = writeReleaseTags(result.tags, dryRun);
|
|
232
|
+
if (writeResult?.outcome === 'failed') {
|
|
233
|
+
reportError(`Failed to write release tags: ${writeResult.error ?? 'unknown error'}`);
|
|
234
|
+
process.exit(1);
|
|
235
|
+
}
|
|
236
|
+
if (writeResult) {
|
|
237
|
+
if (dryRun) {
|
|
238
|
+
console.info(dim(` [dry-run] Would write ${RELEASE_TAGS_FILE}: ${result.tags.join(' ')}`));
|
|
239
|
+
}
|
|
240
|
+
else {
|
|
241
|
+
console.info(dim(` Wrote ${RELEASE_TAGS_FILE}: ${result.tags.join(' ')}`));
|
|
242
|
+
console.info(dim(`\n Release tags file: ${RELEASE_TAGS_FILE}`));
|
|
243
|
+
}
|
|
244
|
+
}
|
|
245
|
+
const summary = buildReleaseSummary(result);
|
|
246
|
+
if (summary.length > 0) {
|
|
247
|
+
const summaryResult = writeFileWithCheck(RELEASE_SUMMARY_FILE, summary, {
|
|
248
|
+
dryRun,
|
|
249
|
+
overwrite: true,
|
|
250
|
+
});
|
|
251
|
+
if (summaryResult.outcome === 'failed') {
|
|
252
|
+
reportError(`Failed to write release summary: ${summaryResult.error ?? 'unknown error'}`);
|
|
253
|
+
process.exit(1);
|
|
254
|
+
}
|
|
255
|
+
if (dryRun) {
|
|
256
|
+
console.info(dim(` [dry-run] Would write ${RELEASE_SUMMARY_FILE}`));
|
|
257
|
+
}
|
|
258
|
+
else {
|
|
259
|
+
console.info(dim(` Wrote ${RELEASE_SUMMARY_FILE}`));
|
|
260
|
+
}
|
|
261
|
+
}
|
|
262
|
+
if (writeResult && !dryRun) {
|
|
263
|
+
process.stderr.write(`\nRun 'release-kit commit' to create the release commit.\n`);
|
|
260
264
|
}
|
|
261
|
-
}
|
|
262
|
-
if (writeResult && !dryRun) {
|
|
263
|
-
process.stderr.write(`
|
|
264
|
-
Run 'release-kit commit' to create the release commit.
|
|
265
|
-
`);
|
|
266
|
-
}
|
|
267
265
|
}
|
|
268
|
-
export {
|
|
269
|
-
RELEASE_SUMMARY_FILE,
|
|
270
|
-
RELEASE_TAGS_FILE,
|
|
271
|
-
parseArgs,
|
|
272
|
-
prepareCommand,
|
|
273
|
-
prepareFlagSchema,
|
|
274
|
-
writeReleaseTags
|
|
275
|
-
};
|