@mui/internal-code-infra 0.0.4-canary.5 → 0.0.4-canary.50
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/README.md +19 -8
- package/build/babel-config.d.mts +11 -3
- package/build/brokenLinksChecker/crawlWorker.d.mts +1 -0
- package/build/brokenLinksChecker/index.d.mts +45 -2
- package/build/changelog/types.d.ts +1 -1
- package/build/cli/cmdArgosPush.d.mts +2 -2
- package/build/cli/cmdBuild.d.mts +2 -2
- package/build/cli/cmdCopyFiles.d.mts +2 -2
- package/build/cli/cmdExtractErrorCodes.d.mts +2 -2
- package/build/cli/cmdGenerateChangelog.d.mts +2 -2
- package/build/cli/cmdGithubAuth.d.mts +2 -2
- package/build/cli/cmdListWorkspaces.d.mts +4 -2
- package/build/cli/cmdNetlifyIgnore.d.mts +2 -2
- package/build/cli/cmdPublish.d.mts +4 -2
- package/build/cli/cmdPublishCanary.d.mts +3 -3
- package/build/cli/cmdPublishNewPackage.d.mts +4 -2
- package/build/cli/cmdSetVersionOverrides.d.mts +2 -2
- package/build/cli/cmdVale.d.mts +46 -0
- package/build/cli/cmdValidateBuiltTypes.d.mts +2 -2
- package/build/eslint/baseConfig.d.mts +3 -1
- package/build/eslint/mui/rules/disallow-react-api-in-server-components.d.mts +2 -2
- package/build/eslint/mui/rules/docgen-ignore-before-comment.d.mts +2 -2
- package/build/eslint/mui/rules/no-guarded-throw.d.mts +31 -0
- package/build/eslint/mui/rules/no-presentation-role.d.mts +5 -0
- package/build/eslint/mui/rules/no-restricted-resolved-imports.d.mts +2 -2
- package/build/eslint/mui/rules/nodeEnvUtils.d.mts +18 -0
- package/build/markdownlint/duplicate-h1.d.mts +1 -1
- package/build/markdownlint/git-diff.d.mts +1 -1
- package/build/markdownlint/index.d.mts +1 -1
- package/build/markdownlint/straight-quotes.d.mts +1 -1
- package/build/markdownlint/table-alignment.d.mts +1 -1
- package/build/markdownlint/terminal-language.d.mts +1 -1
- package/build/remark/config.d.mts +43 -0
- package/build/remark/createLintTester.d.mts +10 -0
- package/build/remark/firstBlockHeading.d.mts +4 -0
- package/build/remark/gitDiff.d.mts +2 -0
- package/build/remark/noSpaceInLinks.d.mts +2 -0
- package/build/remark/straightQuotes.d.mts +2 -0
- package/build/remark/tableAlignment.d.mts +2 -0
- package/build/remark/terminalLanguage.d.mts +2 -0
- package/build/utils/babel.d.mts +1 -1
- package/build/utils/build.d.mts +4 -4
- package/build/utils/github.d.mts +1 -1
- package/build/utils/pnpm.d.mts +68 -2
- package/build/utils/testUtils.d.mts +7 -0
- package/build/utils/typescript.d.mts +2 -2
- package/package.json +62 -35
- package/src/babel-config.mjs +9 -3
- package/src/brokenLinksChecker/__fixtures__/static-site/index.html +1 -0
- package/src/brokenLinksChecker/__fixtures__/static-site/invalid-html.html +15 -0
- package/src/brokenLinksChecker/crawlWorker.mjs +217 -0
- package/src/brokenLinksChecker/index.mjs +217 -164
- package/src/brokenLinksChecker/index.test.ts +50 -13
- package/src/changelog/categorizeCommits.test.ts +5 -5
- package/src/changelog/fetchChangelogs.mjs +6 -2
- package/src/changelog/parseCommitLabels.test.ts +5 -5
- package/src/changelog/renderChangelog.mjs +1 -1
- package/src/changelog/types.ts +1 -1
- package/src/cli/cmdListWorkspaces.mjs +9 -2
- package/src/cli/cmdNetlifyIgnore.mjs +4 -88
- package/src/cli/cmdPublish.mjs +51 -14
- package/src/cli/cmdPublishCanary.mjs +128 -132
- package/src/cli/cmdPublishNewPackage.mjs +27 -6
- package/src/cli/cmdVale.mjs +513 -0
- package/src/cli/cmdVale.test.mjs +644 -0
- package/src/cli/index.mjs +2 -0
- package/src/cli/packageJson.d.ts +1 -1
- package/src/eslint/baseConfig.mjs +45 -20
- package/src/eslint/docsConfig.mjs +2 -1
- package/src/eslint/jsonConfig.mjs +2 -1
- package/src/eslint/mui/config.mjs +21 -1
- package/src/eslint/mui/index.mjs +4 -0
- package/src/eslint/mui/rules/no-guarded-throw.mjs +115 -0
- package/src/eslint/mui/rules/no-guarded-throw.test.mjs +206 -0
- package/src/eslint/mui/rules/no-presentation-role.mjs +60 -0
- package/src/eslint/mui/rules/no-presentation-role.test.mjs +33 -0
- package/src/eslint/mui/rules/nodeEnvUtils.mjs +52 -0
- package/src/eslint/mui/rules/require-dev-wrapper.mjs +25 -40
- package/src/eslint/testConfig.mjs +2 -1
- package/src/estree-typescript.d.ts +1 -1
- package/src/remark/config.mjs +157 -0
- package/src/remark/createLintTester.mjs +19 -0
- package/src/remark/firstBlockHeading.mjs +87 -0
- package/src/remark/firstBlockHeading.test.mjs +107 -0
- package/src/remark/gitDiff.mjs +43 -0
- package/src/remark/gitDiff.test.mjs +45 -0
- package/src/remark/noSpaceInLinks.mjs +42 -0
- package/src/remark/noSpaceInLinks.test.mjs +22 -0
- package/src/remark/straightQuotes.mjs +31 -0
- package/src/remark/straightQuotes.test.mjs +25 -0
- package/src/remark/tableAlignment.mjs +23 -0
- package/src/remark/tableAlignment.test.mjs +28 -0
- package/src/remark/terminalLanguage.mjs +19 -0
- package/src/remark/terminalLanguage.test.mjs +17 -0
- package/src/untyped-plugins.d.ts +11 -11
- package/src/utils/build.mjs +18 -1
- package/src/utils/build.test.mjs +585 -575
- package/src/utils/pnpm.mjs +192 -3
- package/src/utils/pnpm.test.mjs +580 -0
- package/src/utils/testUtils.mjs +18 -0
- package/src/utils/typescript.test.mjs +249 -272
- package/vale/.vale.ini +1 -0
- package/vale/styles/MUI/CorrectReferenceAllCases.yml +43 -0
- package/vale/styles/MUI/CorrectRererenceCased.yml +14 -0
- package/vale/styles/MUI/GoogleLatin.yml +11 -0
- package/vale/styles/MUI/MuiBrandName.yml +22 -0
- package/vale/styles/MUI/NoBritish.yml +112 -0
- package/vale/styles/MUI/NoCompanyName.yml +17 -0
|
@@ -16,10 +16,12 @@ import * as semver from 'semver';
|
|
|
16
16
|
|
|
17
17
|
import {
|
|
18
18
|
getPackageVersionInfo,
|
|
19
|
+
getTransitiveDependencies,
|
|
19
20
|
getWorkspacePackages,
|
|
20
21
|
publishPackages,
|
|
21
22
|
readPackageJson,
|
|
22
23
|
semverMax,
|
|
24
|
+
validatePublishDependencies,
|
|
23
25
|
writePackageJson,
|
|
24
26
|
} from '../utils/pnpm.mjs';
|
|
25
27
|
import { getCurrentGitSha, getRepositoryInfo } from '../utils/git.mjs';
|
|
@@ -28,7 +30,7 @@ import { getCurrentGitSha, getRepositoryInfo } from '../utils/git.mjs';
|
|
|
28
30
|
* @typedef {Object} Args
|
|
29
31
|
* @property {boolean} [dryRun] - Whether to run in dry-run mode
|
|
30
32
|
* @property {boolean} [githubRelease] - Whether to create GitHub releases for canary packages
|
|
31
|
-
* @property {string[]} [
|
|
33
|
+
* @property {string[]} [filter] - Same as filtering packages with --filter in pnpm. Only publish packages matching the filter. See https://pnpm.io/filtering.
|
|
32
34
|
*/
|
|
33
35
|
|
|
34
36
|
const CANARY_TAG = 'canary';
|
|
@@ -119,80 +121,6 @@ function cleanupCommitMessage(message) {
|
|
|
119
121
|
return `${prefix}${msg}`.trim();
|
|
120
122
|
}
|
|
121
123
|
|
|
122
|
-
async function getPackageToDependencyMap() {
|
|
123
|
-
/**
|
|
124
|
-
* @type {(PublicPackage & { dependencies: Record<string, unknown>; private: boolean; })[]}
|
|
125
|
-
*/
|
|
126
|
-
const packagesWithDeps = JSON.parse(
|
|
127
|
-
(await $`pnpm ls -r --json --exclude-peers --only-projects --prod`).stdout,
|
|
128
|
-
);
|
|
129
|
-
/** @type {Record<string, string[]>} */
|
|
130
|
-
const directPkgDependencies = packagesWithDeps
|
|
131
|
-
.filter((pkg) => !pkg.private)
|
|
132
|
-
.reduce((acc, pkg) => {
|
|
133
|
-
if (!pkg.name) {
|
|
134
|
-
return acc;
|
|
135
|
-
}
|
|
136
|
-
const deps = pkg.dependencies ? Object.keys(pkg.dependencies) : [];
|
|
137
|
-
if (!deps.length) {
|
|
138
|
-
return acc;
|
|
139
|
-
}
|
|
140
|
-
acc[pkg.name] = deps;
|
|
141
|
-
return acc;
|
|
142
|
-
}, /** @type {Record<string, string[]>} */ ({}));
|
|
143
|
-
return directPkgDependencies;
|
|
144
|
-
}
|
|
145
|
-
|
|
146
|
-
/**
|
|
147
|
-
* @param {Record<string, string[]>} pkgGraph
|
|
148
|
-
*/
|
|
149
|
-
function resolveTransitiveDependencies(pkgGraph = {}) {
|
|
150
|
-
// Compute transitive (nested) dependencies limited to workspace packages and avoid cycles.
|
|
151
|
-
const workspacePkgNames = new Set(Object.keys(pkgGraph));
|
|
152
|
-
const nestedMap = /** @type {Record<string, string[]>} */ ({});
|
|
153
|
-
|
|
154
|
-
/**
|
|
155
|
-
*
|
|
156
|
-
* @param {string} pkgName
|
|
157
|
-
* @returns {string[]}
|
|
158
|
-
*/
|
|
159
|
-
const getTransitiveDeps = (pkgName) => {
|
|
160
|
-
/**
|
|
161
|
-
* @type {Set<string>}
|
|
162
|
-
*/
|
|
163
|
-
const seen = new Set();
|
|
164
|
-
const stack = (pkgGraph[pkgName] || []).slice();
|
|
165
|
-
|
|
166
|
-
while (stack.length) {
|
|
167
|
-
const dep = stack.pop();
|
|
168
|
-
if (!dep || seen.has(dep)) {
|
|
169
|
-
continue;
|
|
170
|
-
}
|
|
171
|
-
// Only consider workspace packages for transitive expansion
|
|
172
|
-
if (!workspacePkgNames.has(dep)) {
|
|
173
|
-
// still record external deps as direct deps but don't traverse into them
|
|
174
|
-
seen.add(dep);
|
|
175
|
-
continue;
|
|
176
|
-
}
|
|
177
|
-
seen.add(dep);
|
|
178
|
-
const children = pkgGraph[dep] || [];
|
|
179
|
-
for (const c of children) {
|
|
180
|
-
if (!seen.has(c)) {
|
|
181
|
-
stack.push(c);
|
|
182
|
-
}
|
|
183
|
-
}
|
|
184
|
-
}
|
|
185
|
-
|
|
186
|
-
return Array.from(seen);
|
|
187
|
-
};
|
|
188
|
-
|
|
189
|
-
for (const name of Object.keys(pkgGraph)) {
|
|
190
|
-
nestedMap[name] = getTransitiveDeps(name);
|
|
191
|
-
}
|
|
192
|
-
|
|
193
|
-
return nestedMap;
|
|
194
|
-
}
|
|
195
|
-
|
|
196
124
|
/**
|
|
197
125
|
* Prepare changelog data for packages using GitHub API
|
|
198
126
|
* @param {PublicPackage[]} packagesToPublish - Packages that will be published
|
|
@@ -225,14 +153,23 @@ async function prepareChangelogsFromGitCli(packagesToPublish, allPackages, canar
|
|
|
225
153
|
}
|
|
226
154
|
}),
|
|
227
155
|
);
|
|
228
|
-
// Second pass: check for dependency updates in other packages not part of git history
|
|
229
|
-
const
|
|
230
|
-
const
|
|
156
|
+
// Second pass: check for dependency updates in other packages not part of git history.
|
|
157
|
+
const workspacePathByName = new Map(allPackages.map((pkg) => [pkg.name, pkg.path]));
|
|
158
|
+
const publishedNames = new Set(packagesToPublish.map((p) => p.name));
|
|
159
|
+
|
|
160
|
+
const transitiveDepSets = await Promise.all(
|
|
161
|
+
allPackages.map((pkg) =>
|
|
162
|
+
getTransitiveDependencies([pkg.name], {
|
|
163
|
+
includeDev: false,
|
|
164
|
+
workspacePathByName,
|
|
165
|
+
}),
|
|
166
|
+
),
|
|
167
|
+
);
|
|
231
168
|
|
|
232
169
|
for (let i = 0; i < allPackages.length; i += 1) {
|
|
233
170
|
const pkg = allPackages[i];
|
|
234
|
-
const depsToPublish =
|
|
235
|
-
|
|
171
|
+
const depsToPublish = [...transitiveDepSets[i]].filter(
|
|
172
|
+
(dep) => dep !== pkg.name && publishedNames.has(dep),
|
|
236
173
|
);
|
|
237
174
|
if (depsToPublish.length === 0) {
|
|
238
175
|
continue;
|
|
@@ -291,6 +228,41 @@ async function prepareChangelogsForPackages(packagesToPublish, allPackages, cana
|
|
|
291
228
|
return changelogs;
|
|
292
229
|
}
|
|
293
230
|
|
|
231
|
+
/**
|
|
232
|
+
* Create or replace a GitHub release. Attempts to create the release first,
|
|
233
|
+
* and if it already exists (422), deletes the existing one and retries.
|
|
234
|
+
*
|
|
235
|
+
* @param {InstanceType<typeof Octokit>} octokit
|
|
236
|
+
* @param {NonNullable<Parameters<Octokit['repos']['createRelease']>[0]>} params
|
|
237
|
+
*/
|
|
238
|
+
async function upsertGitHubRelease(octokit, params) {
|
|
239
|
+
try {
|
|
240
|
+
return await octokit.repos.createRelease(params);
|
|
241
|
+
} catch (/** @type {any} */ error) {
|
|
242
|
+
const isAlreadyExists =
|
|
243
|
+
error.status === 422 &&
|
|
244
|
+
error.response?.data?.errors?.some(
|
|
245
|
+
(/** @type {any} */ err) => err.code === 'already_exists' && err.field === 'tag_name',
|
|
246
|
+
);
|
|
247
|
+
if (!isAlreadyExists) {
|
|
248
|
+
throw error;
|
|
249
|
+
}
|
|
250
|
+
}
|
|
251
|
+
|
|
252
|
+
// Release already exists — delete and recreate
|
|
253
|
+
const existing = await octokit.repos.getReleaseByTag({
|
|
254
|
+
owner: params.owner,
|
|
255
|
+
repo: params.repo,
|
|
256
|
+
tag: params.tag_name,
|
|
257
|
+
});
|
|
258
|
+
await octokit.repos.deleteRelease({
|
|
259
|
+
owner: params.owner,
|
|
260
|
+
repo: params.repo,
|
|
261
|
+
release_id: existing.data.id,
|
|
262
|
+
});
|
|
263
|
+
return octokit.repos.createRelease(params);
|
|
264
|
+
}
|
|
265
|
+
|
|
294
266
|
/**
|
|
295
267
|
* Create GitHub releases and tags for published packages
|
|
296
268
|
* @param {PublicPackage[]} publishedPackages - Packages that were published
|
|
@@ -343,15 +315,20 @@ async function createGitHubReleasesForPackages(
|
|
|
343
315
|
GIT_COMMITTER_NAME: 'Code infra',
|
|
344
316
|
GIT_COMMITTER_EMAIL: 'code-infra@mui.com',
|
|
345
317
|
},
|
|
346
|
-
})`git tag -
|
|
318
|
+
})`git tag -fa ${tagName} -m ${`Canary release ${pkg.name}@${version}`}`;
|
|
347
319
|
|
|
320
|
+
// Force-push to handle retries where the tag already exists from a previous
|
|
321
|
+
// failed publish. The npm registry is the source of truth for published
|
|
322
|
+
// versions, so it's safe to rewrite a tag even if it points to a different
|
|
323
|
+
// commit — it just means the prior publish for this version failed partway
|
|
324
|
+
// through and the GitHub release needs to be recreated.
|
|
348
325
|
// eslint-disable-next-line no-await-in-loop
|
|
349
|
-
await $`git push origin ${tagName}`;
|
|
326
|
+
await $`git push --force origin ${tagName}`;
|
|
350
327
|
console.log(`✅ Created and pushed git tag: ${tagName}`);
|
|
351
328
|
|
|
352
329
|
// Create GitHub release
|
|
353
330
|
// eslint-disable-next-line no-await-in-loop
|
|
354
|
-
const res = await octokit
|
|
331
|
+
const res = await upsertGitHubRelease(octokit, {
|
|
355
332
|
owner: repoInfo.owner,
|
|
356
333
|
repo: repoInfo.repo,
|
|
357
334
|
tag_name: tagName,
|
|
@@ -381,7 +358,14 @@ async function getLastCanaryTag() {
|
|
|
381
358
|
// Tag might not exist locally, which is fine
|
|
382
359
|
}
|
|
383
360
|
|
|
384
|
-
|
|
361
|
+
try {
|
|
362
|
+
await $`git fetch origin tag ${CANARY_TAG}`;
|
|
363
|
+
} catch (err) {
|
|
364
|
+
// Tag might not exist on the remote yet (first canary run), which is fine
|
|
365
|
+
if (!(/** @type {Error} */ (err).message?.includes("couldn't find remote ref"))) {
|
|
366
|
+
throw err;
|
|
367
|
+
}
|
|
368
|
+
}
|
|
385
369
|
const { stdout: remoteCanaryTag } = await $`git ls-remote --tags origin ${CANARY_TAG}`;
|
|
386
370
|
return remoteCanaryTag.trim() ? CANARY_TAG : null;
|
|
387
371
|
}
|
|
@@ -493,20 +477,23 @@ async function publishCanaryVersions(
|
|
|
493
477
|
}
|
|
494
478
|
|
|
495
479
|
// Third pass: publish only the changed packages using recursive publish
|
|
496
|
-
|
|
480
|
+
/** @type {Set<string>} */
|
|
481
|
+
const publishedNames = new Set();
|
|
497
482
|
try {
|
|
498
483
|
console.log(`📤 Publishing ${packagesToPublish.length} canary versions...`);
|
|
499
|
-
await publishPackages(packagesToPublish, {
|
|
484
|
+
const publishedPackages = await publishPackages(packagesToPublish, {
|
|
500
485
|
dryRun: options.dryRun,
|
|
501
486
|
noGitChecks: true,
|
|
502
487
|
tag: CANARY_TAG,
|
|
503
488
|
});
|
|
504
489
|
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
})
|
|
509
|
-
|
|
490
|
+
// Only use package names from the report summary, not versions.
|
|
491
|
+
// pnpm-publish-summary.json reports the version from the workspace
|
|
492
|
+
// package.json, which is wrong for packages with publishConfig.directory.
|
|
493
|
+
for (const { name } of publishedPackages) {
|
|
494
|
+
publishedNames.add(name);
|
|
495
|
+
console.log(`✅ Published ${name}@${canaryVersions.get(name)}`);
|
|
496
|
+
}
|
|
510
497
|
} finally {
|
|
511
498
|
// Always restore original package.json files in parallel
|
|
512
499
|
console.log('\n🔄 Restoring original package.json files...');
|
|
@@ -520,16 +507,26 @@ async function publishCanaryVersions(
|
|
|
520
507
|
await Promise.all(restorePromises);
|
|
521
508
|
}
|
|
522
509
|
|
|
523
|
-
if (
|
|
524
|
-
// Create
|
|
525
|
-
await createCanaryTag(options.dryRun);
|
|
526
|
-
|
|
527
|
-
// Create GitHub releases if requested
|
|
510
|
+
if (publishedNames.size > 0) {
|
|
511
|
+
// Create GitHub releases only for actually published packages
|
|
528
512
|
if (options.githubRelease) {
|
|
529
|
-
|
|
513
|
+
const actuallyPublished = packagesToPublish.filter((pkg) => publishedNames.has(pkg.name));
|
|
514
|
+
await createGitHubReleasesForPackages(actuallyPublished, canaryVersions, changelogs, options);
|
|
530
515
|
}
|
|
531
516
|
|
|
532
|
-
|
|
517
|
+
// Only advance the canary tag if all expected packages were published.
|
|
518
|
+
// Otherwise the tag would skip over unpublished packages and they'd
|
|
519
|
+
// never be retried on the next run.
|
|
520
|
+
const missing = packagesToPublish.filter((pkg) => !publishedNames.has(pkg.name));
|
|
521
|
+
if (missing.length === 0) {
|
|
522
|
+
await createCanaryTag(options.dryRun);
|
|
523
|
+
console.log('\n🎉 All canary versions published successfully!');
|
|
524
|
+
} else {
|
|
525
|
+
const missingNames = missing.map((pkg) => pkg.name).join(', ');
|
|
526
|
+
console.warn(
|
|
527
|
+
`\n⚠️ Canary tag not advanced, some packages failed to publish: ${missingNames}`,
|
|
528
|
+
);
|
|
529
|
+
}
|
|
533
530
|
}
|
|
534
531
|
}
|
|
535
532
|
|
|
@@ -548,14 +545,15 @@ export default /** @type {import('yargs').CommandModule<{}, Args>} */ ({
|
|
|
548
545
|
default: false,
|
|
549
546
|
description: 'Create GitHub releases for published packages',
|
|
550
547
|
})
|
|
551
|
-
.option('
|
|
548
|
+
.option('filter', {
|
|
552
549
|
type: 'string',
|
|
553
550
|
array: true,
|
|
554
|
-
description:
|
|
551
|
+
description:
|
|
552
|
+
'Same as filtering packages with --filter in pnpm. Only publish packages matching the filter. See https://pnpm.io/filtering.',
|
|
555
553
|
});
|
|
556
554
|
},
|
|
557
555
|
handler: async (argv) => {
|
|
558
|
-
const { dryRun = false, githubRelease = false,
|
|
556
|
+
const { dryRun = false, githubRelease = false, filter = [] } = argv;
|
|
559
557
|
|
|
560
558
|
const options = { dryRun, githubRelease };
|
|
561
559
|
|
|
@@ -567,48 +565,46 @@ export default /** @type {import('yargs').CommandModule<{}, Args>} */ ({
|
|
|
567
565
|
console.log('📝 GitHub releases will be created for published packages\n');
|
|
568
566
|
}
|
|
569
567
|
|
|
570
|
-
//
|
|
568
|
+
// All public packages — needed by publishCanaryVersions to bump versions and update
|
|
569
|
+
// package.json across the entire workspace, even for packages not being published.
|
|
571
570
|
console.log('🔍 Discovering all workspace packages...');
|
|
572
|
-
const
|
|
571
|
+
const filteredPackages = await getWorkspacePackages({ publicOnly: true, filter });
|
|
573
572
|
|
|
574
|
-
if (
|
|
575
|
-
console.log(
|
|
573
|
+
if (filteredPackages.length === 0) {
|
|
574
|
+
console.log(
|
|
575
|
+
`⚠️ No publishable packages found in workspace${filter.length > 0 ? ` matching filter "${filter.join(', ')}"` : ''}`,
|
|
576
|
+
);
|
|
576
577
|
return;
|
|
577
578
|
}
|
|
578
579
|
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
const
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
deps.forEach((dep) => {
|
|
586
|
-
if (!explicitPackages.includes(dep)) {
|
|
587
|
-
missingDeps.add(dep);
|
|
588
|
-
}
|
|
589
|
-
});
|
|
590
|
-
}
|
|
591
|
-
if (missingDeps.size > 0) {
|
|
580
|
+
if (filter.length > 0) {
|
|
581
|
+
console.log('🔍 Validating workspace dependencies for filtered packages...');
|
|
582
|
+
|
|
583
|
+
const { issues } = await validatePublishDependencies(filteredPackages);
|
|
584
|
+
|
|
585
|
+
if (issues.length > 0) {
|
|
592
586
|
throw new Error(
|
|
593
|
-
`
|
|
594
|
-
${
|
|
595
|
-
|
|
587
|
+
`Invalid dependencies structure of packages to be published -
|
|
588
|
+
${issues.join('\n ')}
|
|
589
|
+
`,
|
|
590
|
+
{
|
|
591
|
+
cause: issues,
|
|
592
|
+
},
|
|
596
593
|
);
|
|
597
594
|
}
|
|
595
|
+
|
|
596
|
+
console.log('✅ All workspace dependency requirements satisfied');
|
|
598
597
|
}
|
|
599
598
|
|
|
600
|
-
// Check for canary tag to determine selective publishing
|
|
599
|
+
// Check for canary tag to determine selective publishing.
|
|
600
|
+
// --filter is applied on top of sinceRef: publish only packages that have
|
|
601
|
+
// changed since the last canary tag AND match the filter.
|
|
601
602
|
const canaryTag = await getLastCanaryTag();
|
|
602
603
|
|
|
603
604
|
console.log('🔍 Checking for packages changed since canary tag...');
|
|
604
|
-
|
|
605
|
-
? await getWorkspacePackages({ sinceRef: canaryTag, publicOnly: true })
|
|
606
|
-
:
|
|
607
|
-
|
|
608
|
-
// If user provided package list, filter to only those in packageNames
|
|
609
|
-
if (explicitPackages.length > 0) {
|
|
610
|
-
packages = packages.filter((pkg) => explicitPackages.includes(pkg.name));
|
|
611
|
-
}
|
|
605
|
+
const packages = canaryTag
|
|
606
|
+
? await getWorkspacePackages({ sinceRef: canaryTag, publicOnly: true, filter })
|
|
607
|
+
: filteredPackages;
|
|
612
608
|
|
|
613
609
|
console.log(`📋 Found ${packages.length} packages(s) for canary publishing:`);
|
|
614
610
|
packages.forEach((pkg) => {
|
|
@@ -617,7 +613,7 @@ Pass all workspace dependencies explicitly through the --package argument.`,
|
|
|
617
613
|
|
|
618
614
|
// Fetch version info for all packages in parallel
|
|
619
615
|
console.log('\n🔍 Fetching package version information...');
|
|
620
|
-
const versionInfoPromises =
|
|
616
|
+
const versionInfoPromises = filteredPackages.map(async (pkg) => {
|
|
621
617
|
const versionInfo = await getPackageVersionInfo(pkg.name, pkg.version);
|
|
622
618
|
return { packageName: pkg.name, versionInfo };
|
|
623
619
|
});
|
|
@@ -629,7 +625,7 @@ Pass all workspace dependencies explicitly through the --package argument.`,
|
|
|
629
625
|
packageVersionInfo.set(packageName, versionInfo);
|
|
630
626
|
}
|
|
631
627
|
|
|
632
|
-
await publishCanaryVersions(packages,
|
|
628
|
+
await publishCanaryVersions(packages, filteredPackages, packageVersionInfo, options);
|
|
633
629
|
|
|
634
630
|
console.log('\n🏁 Publishing complete!');
|
|
635
631
|
},
|
|
@@ -16,17 +16,34 @@ import { getWorkspacePackages } from '../utils/pnpm.mjs';
|
|
|
16
16
|
/**
|
|
17
17
|
* @typedef {Object} Args
|
|
18
18
|
* @property {boolean} [dryRun] If true, will only log the commands without executing them
|
|
19
|
+
* @property {string} [otp] 6 digit auth code to forward to npm for two-factor authentication
|
|
19
20
|
*/
|
|
20
21
|
|
|
21
22
|
export default /** @type {import('yargs').CommandModule<{}, Args>} */ ({
|
|
22
23
|
command: 'publish-new-package [pkg...]',
|
|
23
24
|
describe: 'Publish new empty package(s) to the npm registry.',
|
|
24
25
|
builder: (yargs) =>
|
|
25
|
-
yargs
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
26
|
+
yargs
|
|
27
|
+
.option('dryRun', {
|
|
28
|
+
type: 'boolean',
|
|
29
|
+
default: false,
|
|
30
|
+
description: 'If true, will only log the commands without executing them.',
|
|
31
|
+
})
|
|
32
|
+
.option('otp', {
|
|
33
|
+
type: 'string',
|
|
34
|
+
description: '6 digit auth code to forward to npm for two-factor authentication.',
|
|
35
|
+
coerce: (value) => {
|
|
36
|
+
if (value === undefined) {
|
|
37
|
+
return value;
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
if (!/^\d{6}$/.test(value)) {
|
|
41
|
+
throw new Error('The --otp option must be a 6 digit number.');
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
return value;
|
|
45
|
+
},
|
|
46
|
+
}),
|
|
30
47
|
async handler(args) {
|
|
31
48
|
console.log(`🔍 Detecting new packages to publish in workspace...`);
|
|
32
49
|
const newPackages = await getWorkspacePackages({ nonPublishedOnly: true });
|
|
@@ -62,7 +79,7 @@ export default /** @type {import('yargs').CommandModule<{}, Args>} */ ({
|
|
|
62
79
|
version: '0.0.1',
|
|
63
80
|
repository: {
|
|
64
81
|
type: 'git',
|
|
65
|
-
url: `git+https://github.com/${repo.owner}/${repo.
|
|
82
|
+
url: `git+https://github.com/${repo.owner}/${repo.repo}.git`,
|
|
66
83
|
directory: toPosixPath(path.relative(workspaceDir, pkg.path)),
|
|
67
84
|
},
|
|
68
85
|
};
|
|
@@ -78,8 +95,12 @@ export default /** @type {import('yargs').CommandModule<{}, Args>} */ ({
|
|
|
78
95
|
if (args.dryRun) {
|
|
79
96
|
publishArgs.push('--dry-run');
|
|
80
97
|
}
|
|
98
|
+
if (args.otp) {
|
|
99
|
+
publishArgs.push('--otp', args.otp);
|
|
100
|
+
}
|
|
81
101
|
await $({
|
|
82
102
|
cwd: newPkgDir,
|
|
103
|
+
stdio: 'inherit',
|
|
83
104
|
})`npm publish --access public --tag=canary ${publishArgs}`;
|
|
84
105
|
console.log(
|
|
85
106
|
`✅ ${args.dryRun ? '[Dry run] ' : ''}Published ${chalk.bold(`${pkg.name}@${packageJson.version}`)} to npm registry.`,
|