@mnci/cli 4.45.0 → 4.46.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/README.md +10 -0
- package/dist/cli.js +293 -84
- package/dist/cli.js.map +1 -1
- package/package.json +1 -1
package/dist/cli.js
CHANGED
|
@@ -8417,7 +8417,7 @@ function checkReleaseTagsResolve(workspaceRoot, nxJson) {
|
|
|
8417
8417
|
check: "release tags resolve under each project's current name",
|
|
8418
8418
|
ok: stranded.length === 0,
|
|
8419
8419
|
detail: `${stranded.map((entry) => `${entry.project} has only ${entry.oldTag}`).join("; ")} - nx release finds no tag under the new name and would release from the disk version, a downgrade`,
|
|
8420
|
-
remedy: `
|
|
8420
|
+
remedy: `run \`mnci adopt --tags\` to create the baseline tag for each (${stranded.map((entry) => entry.newTag).join(", ")}) on the commit of its old tag, then push the tags`
|
|
8421
8421
|
};
|
|
8422
8422
|
}
|
|
8423
8423
|
function collectFindings(workspaceRoot) {
|
|
@@ -8485,13 +8485,190 @@ function runDoctor(workspaceRoot, options = {}) {
|
|
|
8485
8485
|
process.exitCode = 1;
|
|
8486
8486
|
}
|
|
8487
8487
|
|
|
8488
|
+
// src/repository-adoption/adopt-kinds.use-case.ts
|
|
8489
|
+
var import_node_fs31 = require("fs");
|
|
8490
|
+
var import_node_path36 = require("path");
|
|
8491
|
+
|
|
8492
|
+
// src/repository-adoption/clean-working-tree.validator.ts
|
|
8493
|
+
function requireCleanWorkingTree(repositoryRoot, capture = runCapture) {
|
|
8494
|
+
if (capture("git", ["rev-parse", "--is-inside-work-tree"], repositoryRoot).status !== 0) {
|
|
8495
|
+
throw new Error("This directory is not a git repository. Every adoption step is one diff to review, so it needs git.");
|
|
8496
|
+
}
|
|
8497
|
+
if (capture("git", ["status", "--porcelain"], repositoryRoot).stdout.trim() !== "") {
|
|
8498
|
+
throw new Error("The working tree has uncommitted changes. Commit or stash them, so this step is one diff you can review or discard.");
|
|
8499
|
+
}
|
|
8500
|
+
}
|
|
8501
|
+
|
|
8502
|
+
// src/repository-adoption/infer-project-kind.algorithm.ts
|
|
8503
|
+
var SERVER_FRAMEWORKS = ["express", "koa", "fastify", "@nestjs/core"];
|
|
8504
|
+
function declares(manifest, name) {
|
|
8505
|
+
return ["dependencies", "devDependencies", "peerDependencies"].some((key) => {
|
|
8506
|
+
const block = manifest[key];
|
|
8507
|
+
return typeof block === "object" && block !== null && Object.keys(block).includes(name);
|
|
8508
|
+
});
|
|
8509
|
+
}
|
|
8510
|
+
function inferNpm(evidence) {
|
|
8511
|
+
const { manifest, files } = evidence;
|
|
8512
|
+
const engines = manifest.engines;
|
|
8513
|
+
if (engines?.vscode !== void 0) {
|
|
8514
|
+
return { kind: "vscode-extension", certainty: "certain", reason: "engines.vscode is set" };
|
|
8515
|
+
}
|
|
8516
|
+
if (files.includes("host.json") || declares(manifest, "@azure/functions")) {
|
|
8517
|
+
return { kind: "node-function-app", certainty: "certain", reason: "an Azure Functions host.json or @azure/functions" };
|
|
8518
|
+
}
|
|
8519
|
+
const privatePackage = manifest.private === true;
|
|
8520
|
+
if (declares(manifest, "react") || declares(manifest, "react-dom")) {
|
|
8521
|
+
if (files.includes("index.html")) {
|
|
8522
|
+
return { kind: "react-app", certainty: "certain", reason: "React with an index.html entry" };
|
|
8523
|
+
}
|
|
8524
|
+
return { kind: privatePackage ? "react-internal-lib" : "react-lib", certainty: "certain", reason: `React without an index.html, ${privatePackage ? "private" : "publishable"}` };
|
|
8525
|
+
}
|
|
8526
|
+
const framework = SERVER_FRAMEWORKS.find((name) => declares(manifest, name));
|
|
8527
|
+
if (framework !== void 0) {
|
|
8528
|
+
return { kind: "node-app", certainty: "certain", reason: `a ${framework} server` };
|
|
8529
|
+
}
|
|
8530
|
+
const scripts = manifest.scripts;
|
|
8531
|
+
if (manifest.bin !== void 0 || scripts?.start !== void 0) {
|
|
8532
|
+
return { kind: "node-app", certainty: "guess", reason: "it has a bin or a start script, but no known server framework" };
|
|
8533
|
+
}
|
|
8534
|
+
if (privatePackage) {
|
|
8535
|
+
return { kind: "internal-lib", certainty: "certain", reason: "private, with no entry point of its own" };
|
|
8536
|
+
}
|
|
8537
|
+
const hasEntry = ["main", "module", "exports"].some((key) => manifest[key] !== void 0);
|
|
8538
|
+
return { kind: "npm-lib", certainty: hasEntry ? "certain" : "guess", reason: hasEntry ? "publishable, with a library entry" : "publishable, but no main, module or exports" };
|
|
8539
|
+
}
|
|
8540
|
+
function inferPython(evidence) {
|
|
8541
|
+
const { files, text } = evidence;
|
|
8542
|
+
if (files.includes("function_app.py") || files.includes("host.json")) {
|
|
8543
|
+
return { kind: "python-function-app", certainty: "certain", reason: "an Azure Functions function_app.py or host.json" };
|
|
8544
|
+
}
|
|
8545
|
+
if (text.includes("[project.scripts]") || files.includes("__main__.py")) {
|
|
8546
|
+
return { kind: "python-app", certainty: "guess", reason: "it declares a script or a __main__.py, which a library can too" };
|
|
8547
|
+
}
|
|
8548
|
+
if (text.includes("Private :: Do Not Upload")) {
|
|
8549
|
+
return { kind: "python-internal-lib", certainty: "certain", reason: "classified Private :: Do Not Upload" };
|
|
8550
|
+
}
|
|
8551
|
+
return { kind: "python-lib", certainty: "guess", reason: "a library, but internal or published is a choice only you can make" };
|
|
8552
|
+
}
|
|
8553
|
+
function inferFlutter(evidence) {
|
|
8554
|
+
if (evidence.hasProgram) {
|
|
8555
|
+
return { kind: "flutter-app", certainty: "certain", reason: "lib/main.dart is the entry point" };
|
|
8556
|
+
}
|
|
8557
|
+
const internal = /^publish_to:\s*['"]?none['"]?\s*$/m.test(evidence.text);
|
|
8558
|
+
return { kind: internal ? "flutter-internal-lib" : "flutter-lib", certainty: "certain", reason: internal ? "publish_to: none" : "publishable, with no entry point" };
|
|
8559
|
+
}
|
|
8560
|
+
function inferCsharp(evidence) {
|
|
8561
|
+
const { text } = evidence;
|
|
8562
|
+
if (/<OutputType>\s*Exe\s*<\/OutputType>/i.test(text)) {
|
|
8563
|
+
const functions = /Microsoft\.Azure\.Functions|Azure\.Functions\.Sdk/.test(text);
|
|
8564
|
+
return { kind: functions ? "csharp-function-app" : "csharp-app", certainty: "certain", reason: functions ? "an executable using the Azure Functions worker" : "an executable" };
|
|
8565
|
+
}
|
|
8566
|
+
if (/<IsPackable>\s*false\s*<\/IsPackable>/i.test(text)) {
|
|
8567
|
+
return { kind: "csharp-internal-lib", certainty: "certain", reason: "IsPackable is false" };
|
|
8568
|
+
}
|
|
8569
|
+
return { kind: "csharp-lib", certainty: "guess", reason: "a library, but internal or published is a choice only you can make" };
|
|
8570
|
+
}
|
|
8571
|
+
function inferGo(evidence) {
|
|
8572
|
+
if (evidence.hasProgram) {
|
|
8573
|
+
const functions = evidence.files.includes("host.json");
|
|
8574
|
+
return { kind: functions ? "go-function-app" : "go-app", certainty: "certain", reason: functions ? "package main with an Azure Functions host.json" : "a package main" };
|
|
8575
|
+
}
|
|
8576
|
+
return { kind: "go-lib", certainty: "guess", reason: "a library, but internal or published is a choice only you can make" };
|
|
8577
|
+
}
|
|
8578
|
+
function inferProjectKind(evidence) {
|
|
8579
|
+
switch (evidence.ecosystem) {
|
|
8580
|
+
case "npm": {
|
|
8581
|
+
return inferNpm(evidence);
|
|
8582
|
+
}
|
|
8583
|
+
case "pip": {
|
|
8584
|
+
return inferPython(evidence);
|
|
8585
|
+
}
|
|
8586
|
+
case "pub": {
|
|
8587
|
+
return inferFlutter(evidence);
|
|
8588
|
+
}
|
|
8589
|
+
case "nuget": {
|
|
8590
|
+
return inferCsharp(evidence);
|
|
8591
|
+
}
|
|
8592
|
+
case "go": {
|
|
8593
|
+
return inferGo(evidence);
|
|
8594
|
+
}
|
|
8595
|
+
}
|
|
8596
|
+
}
|
|
8597
|
+
|
|
8598
|
+
// src/repository-adoption/adopt-kinds.use-case.ts
|
|
8599
|
+
var TYPE_TAG = "type:";
|
|
8600
|
+
function readEvidence(repositoryRoot, location) {
|
|
8601
|
+
const directory = (0, import_node_path36.join)(repositoryRoot, location.dir);
|
|
8602
|
+
const files = (0, import_node_fs31.readdirSync)(directory);
|
|
8603
|
+
const manifest = location.ecosystem === "npm" ? readJson(location.manifestPath) : {};
|
|
8604
|
+
const text = location.ecosystem === "npm" ? "" : (0, import_node_fs31.readFileSync)(location.manifestPath, "utf8");
|
|
8605
|
+
let hasProgram = false;
|
|
8606
|
+
if (location.ecosystem === "go") {
|
|
8607
|
+
hasProgram = files.filter((file) => file.endsWith(".go")).some((file) => /^package main\b/m.test((0, import_node_fs31.readFileSync)((0, import_node_path36.join)(directory, file), "utf8")));
|
|
8608
|
+
} else if (location.ecosystem === "pub") {
|
|
8609
|
+
hasProgram = (0, import_node_fs31.existsSync)((0, import_node_path36.join)(directory, "lib", "main.dart"));
|
|
8610
|
+
}
|
|
8611
|
+
return { ecosystem: location.ecosystem, manifest, text, files, hasProgram };
|
|
8612
|
+
}
|
|
8613
|
+
function existingKind(directory) {
|
|
8614
|
+
const sources = [];
|
|
8615
|
+
if (fileExists((0, import_node_path36.join)(directory, "project.json"))) {
|
|
8616
|
+
sources.push(readJson((0, import_node_path36.join)(directory, "project.json")).tags ?? []);
|
|
8617
|
+
}
|
|
8618
|
+
if (fileExists((0, import_node_path36.join)(directory, "package.json"))) {
|
|
8619
|
+
sources.push(readJson((0, import_node_path36.join)(directory, "package.json")).nx?.tags ?? []);
|
|
8620
|
+
}
|
|
8621
|
+
return sources.flat().find((tag) => tag.startsWith(TYPE_TAG))?.slice(TYPE_TAG.length);
|
|
8622
|
+
}
|
|
8623
|
+
function writeKindTag(directory, name, kind) {
|
|
8624
|
+
const tag = `${TYPE_TAG}${kind}`;
|
|
8625
|
+
const projectJson = (0, import_node_path36.join)(directory, "project.json");
|
|
8626
|
+
const packageJson = (0, import_node_path36.join)(directory, "package.json");
|
|
8627
|
+
if (fileExists(projectJson)) {
|
|
8628
|
+
const project = readJson(projectJson);
|
|
8629
|
+
writeFileEnsured(projectJson, toJson({ ...project, tags: [...project.tags ?? [], tag] }));
|
|
8630
|
+
} else if (fileExists(packageJson)) {
|
|
8631
|
+
const manifest = readJson(packageJson);
|
|
8632
|
+
writeFileEnsured(packageJson, toJson({ ...manifest, nx: { ...manifest.nx, tags: [...manifest.nx?.tags ?? [], tag] } }));
|
|
8633
|
+
} else {
|
|
8634
|
+
writeFileEnsured(projectJson, toJson({ name, tags: [tag] }));
|
|
8635
|
+
}
|
|
8636
|
+
}
|
|
8637
|
+
function adoptKinds(repositoryRoot, overrides = {}, dependencies = {}) {
|
|
8638
|
+
requireCleanWorkingTree(repositoryRoot, dependencies.capture ?? runCapture);
|
|
8639
|
+
const locations = locateProjects(repositoryRoot);
|
|
8640
|
+
const known = new Set(locations.map((location) => location.dir));
|
|
8641
|
+
for (const [dir, kind] of Object.entries(overrides)) {
|
|
8642
|
+
if (!known.has(dir)) {
|
|
8643
|
+
throw new Error(`--kind ${dir}=${kind}: no project at ${dir}. Projects found: ${[...known].join(", ")}`);
|
|
8644
|
+
}
|
|
8645
|
+
if (!PROJECT_KINDS.includes(kind)) {
|
|
8646
|
+
throw new Error(`--kind ${dir}=${kind}: ${kind} is not a kind. Kinds: ${PROJECT_KINDS.join(", ")}`);
|
|
8647
|
+
}
|
|
8648
|
+
}
|
|
8649
|
+
return locations.map((location) => {
|
|
8650
|
+
const directory = (0, import_node_path36.join)(repositoryRoot, location.dir);
|
|
8651
|
+
const present = existingKind(directory);
|
|
8652
|
+
if (present !== void 0) {
|
|
8653
|
+
return { dir: location.dir, outcome: "already", kind: present, reason: PROJECT_KINDS.includes(present) ? "it already has a type tag" : "it already has a type tag of its own, which is not an mnci kind name; left as it is" };
|
|
8654
|
+
}
|
|
8655
|
+
const chosen = overrides[location.dir];
|
|
8656
|
+
const proposal = chosen === void 0 ? inferProjectKind(readEvidence(repositoryRoot, location)) : { kind: chosen, certainty: "certain", reason: "named with --kind" };
|
|
8657
|
+
if (proposal.certainty === "guess") {
|
|
8658
|
+
return { dir: location.dir, outcome: "undecided", kind: proposal.kind, reason: proposal.reason };
|
|
8659
|
+
}
|
|
8660
|
+
writeKindTag(directory, location.name, proposal.kind);
|
|
8661
|
+
return { dir: location.dir, outcome: "tagged", kind: proposal.kind, reason: proposal.reason };
|
|
8662
|
+
}).toSorted((a, b) => a.dir.localeCompare(b.dir));
|
|
8663
|
+
}
|
|
8664
|
+
|
|
8488
8665
|
// src/repository-adoption/adopt-overlay.use-case.ts
|
|
8489
|
-
var
|
|
8490
|
-
var
|
|
8666
|
+
var import_node_fs33 = require("fs");
|
|
8667
|
+
var import_node_path38 = require("path");
|
|
8491
8668
|
|
|
8492
8669
|
// src/workspace-upgrade/upgrade-workspace.use-case.ts
|
|
8493
|
-
var
|
|
8494
|
-
var
|
|
8670
|
+
var import_node_fs32 = require("fs");
|
|
8671
|
+
var import_node_path37 = require("path");
|
|
8495
8672
|
function resolveRegistry(options, persisted) {
|
|
8496
8673
|
if (options.registry === "azure-artifacts" || options.organization && options.artifactsFeed) {
|
|
8497
8674
|
const persistedAzure = persisted?.kind === "azure-artifacts" ? persisted : void 0;
|
|
@@ -8520,7 +8697,7 @@ function resolveWorkspaceName(workspaceRoot, persisted) {
|
|
|
8520
8697
|
return persisted.workspaceName;
|
|
8521
8698
|
}
|
|
8522
8699
|
try {
|
|
8523
|
-
const existing = (0,
|
|
8700
|
+
const existing = (0, import_node_fs32.readdirSync)(workspaceRoot).find(
|
|
8524
8701
|
(file) => file.endsWith(".code-workspace") && file !== "undefined.code-workspace"
|
|
8525
8702
|
);
|
|
8526
8703
|
if (existing) {
|
|
@@ -8528,11 +8705,11 @@ function resolveWorkspaceName(workspaceRoot, persisted) {
|
|
|
8528
8705
|
}
|
|
8529
8706
|
} catch {
|
|
8530
8707
|
}
|
|
8531
|
-
return (0,
|
|
8708
|
+
return (0, import_node_path37.basename)(workspaceRoot);
|
|
8532
8709
|
}
|
|
8533
8710
|
function detectNpmAuth(workspaceRoot) {
|
|
8534
8711
|
try {
|
|
8535
|
-
return (0,
|
|
8712
|
+
return (0, import_node_fs32.readFileSync)((0, import_node_path37.join)(workspaceRoot, "azure-pipelines.yml"), "utf8").includes("npmAuthenticate@0") ? "build-identity" : void 0;
|
|
8536
8713
|
} catch {
|
|
8537
8714
|
return void 0;
|
|
8538
8715
|
}
|
|
@@ -8579,7 +8756,7 @@ function resolveOverlayOptions(workspaceRoot, options, persisted) {
|
|
|
8579
8756
|
};
|
|
8580
8757
|
}
|
|
8581
8758
|
function runUpgrade(workspaceRoot, options) {
|
|
8582
|
-
if (!fileExists((0,
|
|
8759
|
+
if (!fileExists((0, import_node_path37.join)(workspaceRoot, "nx.json"))) {
|
|
8583
8760
|
throw new Error(
|
|
8584
8761
|
`No nx.json found in ${workspaceRoot} \u2014 this does not look like an Nx workspace. Run 'mnci upgrade' from the workspace root.`
|
|
8585
8762
|
);
|
|
@@ -8653,30 +8830,20 @@ function runUpgrade(workspaceRoot, options) {
|
|
|
8653
8830
|
"Formatting the workspace (eslint --fix) \u2014 the slowest step, minutes on a large workspace"
|
|
8654
8831
|
);
|
|
8655
8832
|
runFormatter(workspaceRoot);
|
|
8656
|
-
const nxJson = readJson((0,
|
|
8833
|
+
const nxJson = readJson((0, import_node_path37.join)(workspaceRoot, "nx.json"));
|
|
8657
8834
|
const stranded = locateStrandedReleaseTags(workspaceRoot, nxJson.release?.releaseTag?.pattern);
|
|
8658
8835
|
for (const entry of stranded) {
|
|
8659
|
-
logger.warn(`${entry.project} has release tags only under ${entry.oldTag}: nx release would restart it from its disk version. Run \`
|
|
8836
|
+
logger.warn(`${entry.project} has release tags only under ${entry.oldTag}: nx release would restart it from its disk version. Run \`mnci adopt --tags\` before the next release to create ${entry.newTag} locally (\`mnci doctor\` lists them all).`);
|
|
8660
8837
|
}
|
|
8661
8838
|
logger.success("Done. Review the changes with `git diff` before committing.");
|
|
8662
8839
|
logger.info("Run `npm install` and commit package-lock.json too: the overlay may have added or moved a dependency, and CI installs with `npm ci`, which refuses a stale lockfile.");
|
|
8663
8840
|
}
|
|
8664
8841
|
|
|
8665
|
-
// src/repository-adoption/clean-working-tree.validator.ts
|
|
8666
|
-
function requireCleanWorkingTree(repositoryRoot, capture = runCapture) {
|
|
8667
|
-
if (capture("git", ["rev-parse", "--is-inside-work-tree"], repositoryRoot).status !== 0) {
|
|
8668
|
-
throw new Error("This directory is not a git repository. Every adoption step is one diff to review, so it needs git.");
|
|
8669
|
-
}
|
|
8670
|
-
if (capture("git", ["status", "--porcelain"], repositoryRoot).stdout.trim() !== "") {
|
|
8671
|
-
throw new Error("The working tree has uncommitted changes. Commit or stash them, so this step is one diff you can review or discard.");
|
|
8672
|
-
}
|
|
8673
|
-
}
|
|
8674
|
-
|
|
8675
8842
|
// src/repository-adoption/adopt-overlay.use-case.ts
|
|
8676
8843
|
function detectCiProvider(repositoryRoot) {
|
|
8677
|
-
const azure = (0,
|
|
8678
|
-
const workflows = (0,
|
|
8679
|
-
const github = (0,
|
|
8844
|
+
const azure = (0, import_node_fs33.existsSync)((0, import_node_path38.join)(repositoryRoot, "azure-pipelines.yml"));
|
|
8845
|
+
const workflows = (0, import_node_path38.join)(repositoryRoot, ".github", "workflows");
|
|
8846
|
+
const github = (0, import_node_fs33.existsSync)(workflows) && (0, import_node_fs33.readdirSync)(workflows).some((file) => /\.ya?ml$/.test(file));
|
|
8680
8847
|
if (azure && github) {
|
|
8681
8848
|
return "both";
|
|
8682
8849
|
}
|
|
@@ -8686,7 +8853,7 @@ function detectCiProvider(repositoryRoot) {
|
|
|
8686
8853
|
return github ? "github" : void 0;
|
|
8687
8854
|
}
|
|
8688
8855
|
function detectTestRunner(repositoryRoot) {
|
|
8689
|
-
const manifestPath = (0,
|
|
8856
|
+
const manifestPath = (0, import_node_path38.join)(repositoryRoot, "package.json");
|
|
8690
8857
|
if (!fileExists(manifestPath)) {
|
|
8691
8858
|
return void 0;
|
|
8692
8859
|
}
|
|
@@ -8699,7 +8866,7 @@ function detectTestRunner(repositoryRoot) {
|
|
|
8699
8866
|
}
|
|
8700
8867
|
function adoptOverlay(repositoryRoot, options, dependencies = {}) {
|
|
8701
8868
|
requireCleanWorkingTree(repositoryRoot, dependencies.capture ?? runCapture);
|
|
8702
|
-
if (!fileExists((0,
|
|
8869
|
+
if (!fileExists((0, import_node_path38.join)(repositoryRoot, "nx.json"))) {
|
|
8703
8870
|
throw new Error("There is no nx.json, so Nx is not set up here. Set it up first (`npx nx@latest init`); adopt does not install Nx yet.");
|
|
8704
8871
|
}
|
|
8705
8872
|
const persisted = readMnciConfig(repositoryRoot);
|
|
@@ -8712,7 +8879,7 @@ function adoptOverlay(repositoryRoot, options, dependencies = {}) {
|
|
|
8712
8879
|
}
|
|
8713
8880
|
|
|
8714
8881
|
// src/repository-adoption/adopt-toolchain.use-case.ts
|
|
8715
|
-
var
|
|
8882
|
+
var import_node_path40 = require("path");
|
|
8716
8883
|
|
|
8717
8884
|
// src/repository-adoption/align-nx-family.algorithm.ts
|
|
8718
8885
|
var VERSION = /^[\^~]?(\d+)\.(\d+)\.(\d+)$/;
|
|
@@ -8750,24 +8917,24 @@ function alignNxFamily(dependencies, version) {
|
|
|
8750
8917
|
}
|
|
8751
8918
|
|
|
8752
8919
|
// src/repository-adoption/retire-tooling.use-case.ts
|
|
8753
|
-
var
|
|
8754
|
-
var
|
|
8920
|
+
var import_node_fs34 = require("fs");
|
|
8921
|
+
var import_node_path39 = require("path");
|
|
8755
8922
|
var RETIRED_COMMAND = /\b(?:prettier|oxfmt|oxlint)\b/;
|
|
8756
8923
|
function retireTooling(repositoryRoot) {
|
|
8757
8924
|
const removed = [];
|
|
8758
8925
|
for (const file of RETIRED_FORMATTER_FILES) {
|
|
8759
|
-
if (!fileExists((0,
|
|
8926
|
+
if (!fileExists((0, import_node_path39.join)(repositoryRoot, file))) {
|
|
8760
8927
|
continue;
|
|
8761
8928
|
}
|
|
8762
|
-
(0,
|
|
8929
|
+
(0, import_node_fs34.rmSync)((0, import_node_path39.join)(repositoryRoot, file), { force: true });
|
|
8763
8930
|
removed.push(file);
|
|
8764
8931
|
}
|
|
8765
|
-
const hadRegistry = fileExists((0,
|
|
8932
|
+
const hadRegistry = fileExists((0, import_node_path39.join)(repositoryRoot, ".verdaccio"));
|
|
8766
8933
|
removeLocalRegistryScaffolding(repositoryRoot);
|
|
8767
8934
|
if (hadRegistry) {
|
|
8768
8935
|
removed.push(".verdaccio, its dependency and the local-registry target");
|
|
8769
8936
|
}
|
|
8770
|
-
const manifestPath = (0,
|
|
8937
|
+
const manifestPath = (0, import_node_path39.join)(repositoryRoot, "package.json");
|
|
8771
8938
|
if (!fileExists(manifestPath)) {
|
|
8772
8939
|
return removed;
|
|
8773
8940
|
}
|
|
@@ -8814,7 +8981,7 @@ function adoptToolchain(repositoryRoot, options = {}, dependencies = {}) {
|
|
|
8814
8981
|
console.log(message);
|
|
8815
8982
|
});
|
|
8816
8983
|
requireCleanWorkingTree(repositoryRoot, capture);
|
|
8817
|
-
const manifestPath = (0,
|
|
8984
|
+
const manifestPath = (0, import_node_path40.join)(repositoryRoot, "package.json");
|
|
8818
8985
|
if (!fileExists(manifestPath)) {
|
|
8819
8986
|
throw new Error("No package.json at the repository root.");
|
|
8820
8987
|
}
|
|
@@ -8864,8 +9031,8 @@ function createBaselineTags(repositoryRoot, stranded) {
|
|
|
8864
9031
|
}
|
|
8865
9032
|
|
|
8866
9033
|
// src/repository-adoption/inspect-repository.use-case.ts
|
|
8867
|
-
var
|
|
8868
|
-
var
|
|
9034
|
+
var import_node_fs35 = require("fs");
|
|
9035
|
+
var import_node_path41 = require("path");
|
|
8869
9036
|
var LOCKFILES = [
|
|
8870
9037
|
["package-lock.json", "npm"],
|
|
8871
9038
|
["pnpm-lock.yaml", "pnpm"],
|
|
@@ -8886,25 +9053,25 @@ function inspectRepository(repositoryRoot) {
|
|
|
8886
9053
|
const isGitRepo = inside.status === 0 && inside.stdout.trim() === "true";
|
|
8887
9054
|
const dirty = isGitRepo && runCapture("git", ["status", "--porcelain"], repositoryRoot).stdout.trim() !== "";
|
|
8888
9055
|
const tags = isGitRepo ? runCapture("git", ["tag", "--list"], repositoryRoot).stdout.split(/\r?\n/).filter(Boolean) : [];
|
|
8889
|
-
const manifestPath = (0,
|
|
9056
|
+
const manifestPath = (0, import_node_path41.join)(repositoryRoot, "package.json");
|
|
8890
9057
|
const manifest = fileExists(manifestPath) ? readJson(manifestPath) : {};
|
|
8891
|
-
const nxJsonPath = (0,
|
|
9058
|
+
const nxJsonPath = (0, import_node_path41.join)(repositoryRoot, "nx.json");
|
|
8892
9059
|
const nxJson = fileExists(nxJsonPath) ? readJson(nxJsonPath) : {};
|
|
8893
9060
|
const ci = [];
|
|
8894
9061
|
const pipelines = [];
|
|
8895
|
-
if ((0,
|
|
9062
|
+
if ((0, import_node_fs35.existsSync)((0, import_node_path41.join)(repositoryRoot, "azure-pipelines.yml"))) {
|
|
8896
9063
|
ci.push("azure");
|
|
8897
|
-
pipelines.push((0,
|
|
9064
|
+
pipelines.push((0, import_node_path41.join)(repositoryRoot, "azure-pipelines.yml"));
|
|
8898
9065
|
}
|
|
8899
|
-
const workflows = (0,
|
|
8900
|
-
if ((0,
|
|
8901
|
-
const files = (0,
|
|
9066
|
+
const workflows = (0, import_node_path41.join)(repositoryRoot, ".github", "workflows");
|
|
9067
|
+
if ((0, import_node_fs35.existsSync)(workflows)) {
|
|
9068
|
+
const files = (0, import_node_fs35.readdirSync)(workflows).filter((file) => /\.ya?ml$/.test(file));
|
|
8902
9069
|
if (files.length > 0) {
|
|
8903
9070
|
ci.push("github");
|
|
8904
|
-
pipelines.push(...files.map((file) => (0,
|
|
9071
|
+
pipelines.push(...files.map((file) => (0, import_node_path41.join)(workflows, file)));
|
|
8905
9072
|
}
|
|
8906
9073
|
}
|
|
8907
|
-
const rootFiles = (0,
|
|
9074
|
+
const rootFiles = (0, import_node_fs35.readdirSync)(repositoryRoot);
|
|
8908
9075
|
return {
|
|
8909
9076
|
isGitRepo,
|
|
8910
9077
|
dirty,
|
|
@@ -8915,7 +9082,7 @@ function inspectRepository(repositoryRoot) {
|
|
|
8915
9082
|
tagCount: tags.length,
|
|
8916
9083
|
strandedTags: isGitRepo ? locateStrandedReleaseTags(repositoryRoot, nxJson.release?.releaseTag?.pattern) : [],
|
|
8917
9084
|
ci,
|
|
8918
|
-
pipelineUsesMnci: pipelines.some((file) => /\bmnci ci\b/.test((0,
|
|
9085
|
+
pipelineUsesMnci: pipelines.some((file) => /\bmnci ci\b/.test((0, import_node_fs35.readFileSync)(file, "utf8"))),
|
|
8919
9086
|
retiredTooling: [.../* @__PURE__ */ new Set([...rootFiles.filter((file) => RETIRED_FILE_PATTERN.test(file) || file === ".verdaccio"), ...retiredNamesIn(manifest)])],
|
|
8920
9087
|
personalFiles: PERSONAL_FILES.filter((file) => rootFiles.includes(file))
|
|
8921
9088
|
};
|
|
@@ -8972,6 +9139,10 @@ function reportAdoption(repositoryRoot) {
|
|
|
8972
9139
|
}
|
|
8973
9140
|
function runAdopt(repositoryRoot, options = {}) {
|
|
8974
9141
|
const report = reportAdoption(repositoryRoot);
|
|
9142
|
+
if (options.kinds === true) {
|
|
9143
|
+
runKinds2(repositoryRoot, options);
|
|
9144
|
+
return;
|
|
9145
|
+
}
|
|
8975
9146
|
if (options.overlay === true) {
|
|
8976
9147
|
runOverlay(repositoryRoot, options);
|
|
8977
9148
|
return;
|
|
@@ -9071,6 +9242,42 @@ function runOverlay(repositoryRoot, options) {
|
|
|
9071
9242
|
process.exitCode = 1;
|
|
9072
9243
|
}
|
|
9073
9244
|
}
|
|
9245
|
+
function parseKindChoices(choices) {
|
|
9246
|
+
const parsed = {};
|
|
9247
|
+
for (const choice of choices) {
|
|
9248
|
+
const [dir, kind] = choice.split("=", 2);
|
|
9249
|
+
if (dir === "" || kind === void 0 || kind === "") {
|
|
9250
|
+
throw new Error(`--kind ${choice}: write it as <directory>=<kind>, for example --kind apps/api=node-app`);
|
|
9251
|
+
}
|
|
9252
|
+
parsed[dir] = kind;
|
|
9253
|
+
}
|
|
9254
|
+
return parsed;
|
|
9255
|
+
}
|
|
9256
|
+
function runKinds2(repositoryRoot, options) {
|
|
9257
|
+
try {
|
|
9258
|
+
const outcomes = adoptKinds(repositoryRoot, parseKindChoices(options.kind ?? []));
|
|
9259
|
+
for (const outcome of outcomes) {
|
|
9260
|
+
const line = `${outcome.dir.padEnd(30)} ${outcome.kind} (${outcome.reason})`;
|
|
9261
|
+
if (outcome.outcome === "tagged") {
|
|
9262
|
+
logger.success(`tagged ${line}`);
|
|
9263
|
+
} else if (outcome.outcome === "already") {
|
|
9264
|
+
logger.info(`kept ${line}`);
|
|
9265
|
+
} else {
|
|
9266
|
+
logger.warn(`guessed ${line}`);
|
|
9267
|
+
}
|
|
9268
|
+
}
|
|
9269
|
+
const undecided = outcomes.filter((outcome) => outcome.outcome === "undecided");
|
|
9270
|
+
if (undecided.length > 0) {
|
|
9271
|
+
logger.error(`${undecided.length} project(s) need you to choose. Run again with ${undecided.map((outcome) => `--kind ${outcome.dir}=${outcome.kind}`).join(" ")} to accept the guesses, or name another kind.`);
|
|
9272
|
+
process.exitCode = 1;
|
|
9273
|
+
} else {
|
|
9274
|
+
logger.success("Every project has a kind. Review with `git diff` and commit.");
|
|
9275
|
+
}
|
|
9276
|
+
} catch (error) {
|
|
9277
|
+
logger.error(error instanceof Error ? error.message : String(error));
|
|
9278
|
+
process.exitCode = 1;
|
|
9279
|
+
}
|
|
9280
|
+
}
|
|
9074
9281
|
|
|
9075
9282
|
// src/command-catalog/command-groups.config.ts
|
|
9076
9283
|
var COMMAND_GROUPS = {
|
|
@@ -9143,13 +9350,15 @@ function runCommands(program, options) {
|
|
|
9143
9350
|
}
|
|
9144
9351
|
|
|
9145
9352
|
// src/workspace-info/list-projects.use-case.ts
|
|
9146
|
-
var
|
|
9353
|
+
var import_node_path42 = require("path");
|
|
9147
9354
|
var TYPE_TAG_PREFIX = "type:";
|
|
9148
9355
|
function listProjects(workspaceRoot) {
|
|
9149
9356
|
return locateProjects(workspaceRoot).map((location) => {
|
|
9150
|
-
const projectJsonPath = (0,
|
|
9357
|
+
const projectJsonPath = (0, import_node_path42.join)(workspaceRoot, location.dir, "project.json");
|
|
9151
9358
|
const project = fileExists(projectJsonPath) ? readJson(projectJsonPath) : {};
|
|
9152
|
-
const
|
|
9359
|
+
const manifestPath = (0, import_node_path42.join)(workspaceRoot, location.dir, "package.json");
|
|
9360
|
+
const manifestTags = fileExists(manifestPath) ? readJson(manifestPath).nx?.tags ?? [] : [];
|
|
9361
|
+
const typeTag = [...project.tags ?? [], ...manifestTags].find((tag) => tag.startsWith(TYPE_TAG_PREFIX));
|
|
9153
9362
|
return {
|
|
9154
9363
|
name: location.name,
|
|
9155
9364
|
dir: location.dir,
|
|
@@ -9160,7 +9369,7 @@ function listProjects(workspaceRoot) {
|
|
|
9160
9369
|
}).toSorted((a, b) => a.dir.localeCompare(b.dir));
|
|
9161
9370
|
}
|
|
9162
9371
|
function runProjects(workspaceRoot, options) {
|
|
9163
|
-
if (!fileExists((0,
|
|
9372
|
+
if (!fileExists((0, import_node_path42.join)(workspaceRoot, "nx.json"))) {
|
|
9164
9373
|
throw new Error("No nx.json found here. Run `projects` from the workspace root.");
|
|
9165
9374
|
}
|
|
9166
9375
|
const projects = listProjects(workspaceRoot);
|
|
@@ -9174,11 +9383,11 @@ function runProjects(workspaceRoot, options) {
|
|
|
9174
9383
|
}
|
|
9175
9384
|
|
|
9176
9385
|
// src/workspace-info/read-workspace-info.use-case.ts
|
|
9177
|
-
var
|
|
9386
|
+
var import_node_path44 = require("path");
|
|
9178
9387
|
|
|
9179
9388
|
// src/cli-version/check-for-update.use-case.ts
|
|
9180
|
-
var
|
|
9181
|
-
var
|
|
9389
|
+
var import_node_fs36 = require("fs");
|
|
9390
|
+
var import_node_path43 = require("path");
|
|
9182
9391
|
var import_cross_spawn3 = __toESM(require("cross-spawn"));
|
|
9183
9392
|
var PACKAGE_NAME2 = "@mnci/cli";
|
|
9184
9393
|
var REGISTRY_TIMEOUT_MS = 2e3;
|
|
@@ -9237,8 +9446,8 @@ function releaseTriple(version) {
|
|
|
9237
9446
|
}
|
|
9238
9447
|
function readCliVersion(packageDirectory) {
|
|
9239
9448
|
try {
|
|
9240
|
-
const manifestPath = (0,
|
|
9241
|
-
const manifest = JSON.parse((0,
|
|
9449
|
+
const manifestPath = (0, import_node_path43.join)(packageDirectory, "..", "package.json");
|
|
9450
|
+
const manifest = JSON.parse((0, import_node_fs36.readFileSync)(manifestPath, "utf8"));
|
|
9242
9451
|
return manifest.version ?? "0.0.0";
|
|
9243
9452
|
} catch {
|
|
9244
9453
|
return "0.0.0";
|
|
@@ -9248,7 +9457,7 @@ function readCliVersion(packageDirectory) {
|
|
|
9248
9457
|
// src/workspace-info/read-workspace-info.use-case.ts
|
|
9249
9458
|
function readWorkspaceInfo(workspaceRoot, cliVersion) {
|
|
9250
9459
|
const latest = fetchLatestVersion() ?? null;
|
|
9251
|
-
const isWorkspace = fileExists((0,
|
|
9460
|
+
const isWorkspace = fileExists((0, import_node_path44.join)(workspaceRoot, "nx.json"));
|
|
9252
9461
|
return {
|
|
9253
9462
|
cli: {
|
|
9254
9463
|
version: cliVersion,
|
|
@@ -9269,8 +9478,8 @@ function runInfo(workspaceRoot, cliVersion, options) {
|
|
|
9269
9478
|
}
|
|
9270
9479
|
|
|
9271
9480
|
// src/workspace-creation/adopt-directory.use-case.ts
|
|
9272
|
-
var
|
|
9273
|
-
var
|
|
9481
|
+
var import_node_fs37 = require("fs");
|
|
9482
|
+
var import_node_path45 = require("path");
|
|
9274
9483
|
var NEVER_COPIED = /* @__PURE__ */ new Set([".git", "node_modules"]);
|
|
9275
9484
|
var AGENT_AND_CI_ENTRIES = [
|
|
9276
9485
|
"AGENTS.md",
|
|
@@ -9301,13 +9510,13 @@ var PREFLIGHT_BLOCKERS = [
|
|
|
9301
9510
|
"packages"
|
|
9302
9511
|
];
|
|
9303
9512
|
function assertAdoptableDirectory(target) {
|
|
9304
|
-
if (!(0,
|
|
9513
|
+
if (!(0, import_node_fs37.existsSync)(target)) {
|
|
9305
9514
|
throw new Error(`--into '${target}' does not exist. Create or clone it first.`);
|
|
9306
9515
|
}
|
|
9307
|
-
if (!(0,
|
|
9516
|
+
if (!(0, import_node_fs37.statSync)(target).isDirectory()) {
|
|
9308
9517
|
throw new Error(`--into '${target}' is not a directory.`);
|
|
9309
9518
|
}
|
|
9310
|
-
const blockers = PREFLIGHT_BLOCKERS.filter((entry) => (0,
|
|
9519
|
+
const blockers = PREFLIGHT_BLOCKERS.filter((entry) => (0, import_node_fs37.existsSync)((0, import_node_path45.join)(target, entry)));
|
|
9311
9520
|
if (blockers.length > 0) {
|
|
9312
9521
|
throw new Error(
|
|
9313
9522
|
`--into '${target}' already holds ${blockers.join(", ")}, so it is a project already. Use \`mnci upgrade\` to re-apply the overlay to an existing workspace, or point --into at an empty checkout.`
|
|
@@ -9315,15 +9524,15 @@ function assertAdoptableDirectory(target) {
|
|
|
9315
9524
|
}
|
|
9316
9525
|
}
|
|
9317
9526
|
function mergeGitignore(generatedFile, targetFile) {
|
|
9318
|
-
const existing = (0,
|
|
9527
|
+
const existing = (0, import_node_fs37.readFileSync)(targetFile, "utf8");
|
|
9319
9528
|
const present = new Set(existing.split("\n").map((line) => line.trim()));
|
|
9320
|
-
const additions = (0,
|
|
9529
|
+
const additions = (0, import_node_fs37.readFileSync)(generatedFile, "utf8").split("\n").map((line) => line.trimEnd()).filter((line) => {
|
|
9321
9530
|
const trimmed = line.trim();
|
|
9322
9531
|
return trimmed !== "" && !trimmed.startsWith("#") && !present.has(trimmed);
|
|
9323
9532
|
});
|
|
9324
9533
|
if (additions.length === 0) return false;
|
|
9325
9534
|
const separator = existing.endsWith("\n") ? "" : "\n";
|
|
9326
|
-
(0,
|
|
9535
|
+
(0, import_node_fs37.writeFileSync)(
|
|
9327
9536
|
targetFile,
|
|
9328
9537
|
`${existing}${separator}
|
|
9329
9538
|
# Added by mnci (Nx workspace)
|
|
@@ -9333,9 +9542,9 @@ ${additions.join("\n")}
|
|
|
9333
9542
|
return true;
|
|
9334
9543
|
}
|
|
9335
9544
|
function adoptGeneratedWorkspace(generatedRoot, target) {
|
|
9336
|
-
const entries = (0,
|
|
9545
|
+
const entries = (0, import_node_fs37.readdirSync)(generatedRoot).filter((entry) => !NEVER_COPIED.has(entry));
|
|
9337
9546
|
const collisions = entries.filter(
|
|
9338
|
-
(entry) => (0,
|
|
9547
|
+
(entry) => (0, import_node_fs37.existsSync)((0, import_node_path45.join)(target, entry)) && !EXISTING_WINS.has(entry) && entry !== ".gitignore"
|
|
9339
9548
|
);
|
|
9340
9549
|
if (collisions.length > 0) {
|
|
9341
9550
|
throw new Error(
|
|
@@ -9344,28 +9553,28 @@ function adoptGeneratedWorkspace(generatedRoot, target) {
|
|
|
9344
9553
|
}
|
|
9345
9554
|
const result = { copied: [], kept: [], mergedGitignore: false };
|
|
9346
9555
|
for (const entry of entries) {
|
|
9347
|
-
const from = (0,
|
|
9348
|
-
const to = (0,
|
|
9349
|
-
if (entry === ".gitignore" && (0,
|
|
9556
|
+
const from = (0, import_node_path45.join)(generatedRoot, entry);
|
|
9557
|
+
const to = (0, import_node_path45.join)(target, entry);
|
|
9558
|
+
if (entry === ".gitignore" && (0, import_node_fs37.existsSync)(to)) {
|
|
9350
9559
|
result.mergedGitignore = mergeGitignore(from, to);
|
|
9351
9560
|
result.kept.push(entry);
|
|
9352
9561
|
continue;
|
|
9353
9562
|
}
|
|
9354
|
-
if ((0,
|
|
9563
|
+
if ((0, import_node_fs37.existsSync)(to)) {
|
|
9355
9564
|
result.kept.push(entry);
|
|
9356
9565
|
continue;
|
|
9357
9566
|
}
|
|
9358
|
-
(0,
|
|
9567
|
+
(0, import_node_fs37.cpSync)(from, to, { recursive: true });
|
|
9359
9568
|
result.copied.push(entry);
|
|
9360
9569
|
}
|
|
9361
|
-
(0,
|
|
9570
|
+
(0, import_node_fs37.rmSync)(generatedRoot, { recursive: true, force: true });
|
|
9362
9571
|
return result;
|
|
9363
9572
|
}
|
|
9364
9573
|
|
|
9365
9574
|
// src/workspace-creation/create-workspace.use-case.ts
|
|
9366
|
-
var
|
|
9575
|
+
var import_node_fs38 = require("fs");
|
|
9367
9576
|
var import_node_os2 = require("os");
|
|
9368
|
-
var
|
|
9577
|
+
var import_node_path46 = require("path");
|
|
9369
9578
|
function nxCloudProviderValue(ci) {
|
|
9370
9579
|
return ci === "azure" ? "azure" : "github";
|
|
9371
9580
|
}
|
|
@@ -9408,9 +9617,9 @@ async function resolveRegistry2(options) {
|
|
|
9408
9617
|
return await promptRegistry();
|
|
9409
9618
|
}
|
|
9410
9619
|
async function runNew(name, options) {
|
|
9411
|
-
const adoptTarget = options.into === void 0 ? void 0 : (0,
|
|
9620
|
+
const adoptTarget = options.into === void 0 ? void 0 : (0, import_node_path46.resolve)(process.cwd(), options.into);
|
|
9412
9621
|
if (adoptTarget !== void 0) assertAdoptableDirectory(adoptTarget);
|
|
9413
|
-
const workspaceName = name ?? (adoptTarget === void 0 ? await promptText("Workspace name") : (0,
|
|
9622
|
+
const workspaceName = name ?? (adoptTarget === void 0 ? await promptText("Workspace name") : (0, import_node_path46.basename)(adoptTarget));
|
|
9414
9623
|
assertValidProjectName(workspaceName, "Workspace name");
|
|
9415
9624
|
const scope = options.scope ?? (options.yes ? `@${workspaceName}` : await promptText("npm scope for publishable packages", `@${workspaceName}`));
|
|
9416
9625
|
const registry = await resolveRegistry2(options);
|
|
@@ -9423,8 +9632,8 @@ async function runNew(name, options) {
|
|
|
9423
9632
|
const npmAuth = resolveNpmAuth(options.npmAuth, registry, ci);
|
|
9424
9633
|
const stack = await resolveStack(options);
|
|
9425
9634
|
const nxCloud = options.nxCloud ?? (options.yes ? false : await promptNxCloud());
|
|
9426
|
-
const stagingParent = adoptTarget === void 0 ? process.cwd() : (0,
|
|
9427
|
-
let workspaceRoot = (0,
|
|
9635
|
+
const stagingParent = adoptTarget === void 0 ? process.cwd() : (0, import_node_fs38.mkdtempSync)((0, import_node_path46.join)((0, import_node_os2.tmpdir)(), "mnci-new-"));
|
|
9636
|
+
let workspaceRoot = (0, import_node_path46.join)(stagingParent, workspaceName);
|
|
9428
9637
|
try {
|
|
9429
9638
|
logger.step(`Creating Nx workspace '${workspaceName}' (preset: ts)`);
|
|
9430
9639
|
runNpx(
|
|
@@ -9447,7 +9656,7 @@ async function runNew(name, options) {
|
|
|
9447
9656
|
workspaceRoot = adoptTarget;
|
|
9448
9657
|
}
|
|
9449
9658
|
} finally {
|
|
9450
|
-
if (adoptTarget !== void 0) (0,
|
|
9659
|
+
if (adoptTarget !== void 0) (0, import_node_fs38.rmSync)(stagingParent, { recursive: true, force: true });
|
|
9451
9660
|
}
|
|
9452
9661
|
logger.step(
|
|
9453
9662
|
"Applying MoNecromanCI overlay (VS Code workspace, release config, .npmrc, commitlint, pipeline, stack)"
|
|
@@ -9457,8 +9666,8 @@ async function runNew(name, options) {
|
|
|
9457
9666
|
{ workspaceName, scope, registry, agent, variableGroup, ci, stack, ...npmAuth && { npmAuth } },
|
|
9458
9667
|
logger.detail
|
|
9459
9668
|
);
|
|
9460
|
-
(0,
|
|
9461
|
-
(0,
|
|
9669
|
+
(0, import_node_fs38.rmSync)((0, import_node_path46.join)(workspaceRoot, "node_modules"), { recursive: true, force: true });
|
|
9670
|
+
(0, import_node_fs38.rmSync)((0, import_node_path46.join)(workspaceRoot, "package-lock.json"), { force: true });
|
|
9462
9671
|
logger.step("Installing the toolchain (commitlint + husky + linting/formatting)");
|
|
9463
9672
|
const installStatus = runShell(
|
|
9464
9673
|
"npm",
|
|
@@ -9496,10 +9705,10 @@ function projectKindHintLines(kinds = PROJECT_KINDS) {
|
|
|
9496
9705
|
}
|
|
9497
9706
|
|
|
9498
9707
|
// src/workspace-creation/interactive-wizard.use-case.ts
|
|
9499
|
-
var
|
|
9708
|
+
var import_node_path47 = require("path");
|
|
9500
9709
|
var import_prompts4 = require("@inquirer/prompts");
|
|
9501
9710
|
async function runInteractive() {
|
|
9502
|
-
const inWorkspace = fileExists((0,
|
|
9711
|
+
const inWorkspace = fileExists((0, import_node_path47.join)(process.cwd(), "nx.json"));
|
|
9503
9712
|
const choiceNew = { name: "Create a new monorepo", value: "new" };
|
|
9504
9713
|
const choiceAdd = { name: "Add a project to this workspace", value: "add" };
|
|
9505
9714
|
const choiceUpgrade = {
|
|
@@ -9551,7 +9760,7 @@ function buildProgram(cliVersion) {
|
|
|
9551
9760
|
).option("--json", "print the findings as one JSON document, each with its remedy").action((options) => {
|
|
9552
9761
|
runDoctor(process.cwd(), options);
|
|
9553
9762
|
});
|
|
9554
|
-
program.command("adopt").description("Read an existing repository and report what bringing it under mnci would involve: blockers, warnings and the step that clears each. Read-only unless a step flag is given; exits non-zero when something blocks").option("--json", "print the report as one JSON document").option("--tags", "create, locally, the baseline tag each project whose release tags are stranded under an old name needs; nothing is pushed").option("--toolchain", "retire old formatter and registry tooling, align the Nx family to one version and run npm audit fix until the audit gate passes; needs a clean git tree and leaves the changes uncommitted").option("--nx <version>", "the Nx version --toolchain aligns to (default: the newest published in the major already in use)").option("--overlay", "apply the mnci overlay (release config, pipeline, npmrc, commitlint, scripts) with the flags mnci upgrade takes; the pipeline keeps the steps mnci does not recognise in its slots; needs a clean git tree and an nx.json").option("--scope <scope>", "npm scope for publishable packages (--overlay)").option("--registry <kind>", "azure-artifacts | npm (--overlay)").option("--organization <name>", "Azure DevOps organization (--overlay)").option("--project <name>", "Azure DevOps project (--overlay)").option("--artifacts-feed <name>", "Azure Artifacts feed (--overlay)").option("--agent <pool>", "CI build agent (--overlay)").option("--variable-group <name>", "Azure DevOps variable group holding the npm PAT (--overlay)").option("--npm-auth <mode>", "pat (default) | build-identity (--overlay, --ci azure only)").option("--ci <provider>", "azure | github | both (--overlay; default: what the repository already has)").option("--test-runner <runner>", "jest | vitest (--overlay; default: what the repository already declares)").action((options) => {
|
|
9763
|
+
program.command("adopt").description("Read an existing repository and report what bringing it under mnci would involve: blockers, warnings and the step that clears each. Read-only unless a step flag is given; exits non-zero when something blocks").option("--json", "print the report as one JSON document").option("--tags", "create, locally, the baseline tag each project whose release tags are stranded under an old name needs; nothing is pushed").option("--toolchain", "retire old formatter and registry tooling, align the Nx family to one version and run npm audit fix until the audit gate passes; needs a clean git tree and leaves the changes uncommitted").option("--nx <version>", "the Nx version --toolchain aligns to (default: the newest published in the major already in use)").option("--kinds", "record each project's mnci kind as a type:<kind> tag (npm, Python, Go, Flutter and C# projects); a project where two kinds fit is listed with a guess and not tagged; needs a clean git tree").option("--kind <dir=kind>", "the kind you choose for one project, for --kinds (repeatable)", (value, previous = []) => [...previous, value]).option("--overlay", "apply the mnci overlay (release config, pipeline, npmrc, commitlint, scripts) with the flags mnci upgrade takes; the pipeline keeps the steps mnci does not recognise in its slots; needs a clean git tree and an nx.json").option("--scope <scope>", "npm scope for publishable packages (--overlay)").option("--registry <kind>", "azure-artifacts | npm (--overlay)").option("--organization <name>", "Azure DevOps organization (--overlay)").option("--project <name>", "Azure DevOps project (--overlay)").option("--artifacts-feed <name>", "Azure Artifacts feed (--overlay)").option("--agent <pool>", "CI build agent (--overlay)").option("--variable-group <name>", "Azure DevOps variable group holding the npm PAT (--overlay)").option("--npm-auth <mode>", "pat (default) | build-identity (--overlay, --ci azure only)").option("--ci <provider>", "azure | github | both (--overlay; default: what the repository already has)").option("--test-runner <runner>", "jest | vitest (--overlay; default: what the repository already declares)").action((options) => {
|
|
9555
9764
|
runAdopt(process.cwd(), options);
|
|
9556
9765
|
});
|
|
9557
9766
|
program.command("ci").addArgument(new import_commander.Argument("<phase>", "which phase of the pipeline to run").choices(CI_PHASES)).description(
|