nx 23.2.0-beta.1 → 23.2.0-beta.3
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/dist/bin/nx.js +1 -0
- package/dist/src/analytics/analytics.d.ts +6 -0
- package/dist/src/analytics/analytics.js +16 -8
- package/dist/src/analytics/index.d.ts +1 -1
- package/dist/src/analytics/index.js +2 -1
- package/dist/src/command-line/graph/graph.d.ts +1 -0
- package/dist/src/command-line/graph/graph.js +15 -6
- package/dist/src/command-line/init/implementation/angular/integrated-workspace.js +2 -5
- package/dist/src/command-line/init/implementation/angular/legacy-angular-versions.js +3 -0
- package/dist/src/command-line/init/implementation/dot-nx/add-nx-scripts.js +4 -1
- package/dist/src/command-line/migrate/migrate.js +20 -1
- package/dist/src/command-line/nx-cloud/connect/connect-to-nx-cloud.js +1 -1
- package/dist/src/command-line/nx-cloud/connect/view-logs.js +2 -0
- package/dist/src/command-line/release/utils/remote-release-clients/github.js +1 -1
- package/dist/src/command-line/release/utils/remote-release-clients/gitlab.js +1 -1
- package/dist/src/command-line/show/show-target/inputs.js +50 -153
- package/dist/src/command-line/show/show-target/outputs.js +48 -173
- package/dist/src/command-line/show/show-target/utils.d.ts +28 -0
- package/dist/src/command-line/show/show-target/utils.js +83 -3
- package/dist/src/command-line/yargs-utils/shared-options.d.ts +1 -1
- package/dist/src/config/nx-json.d.ts +4 -2
- package/dist/src/core/graph/main.js +1 -1
- package/dist/src/daemon/server/handle-tasks-execution-hooks.d.ts +1 -1
- package/dist/src/daemon/server/server.js +7 -4
- package/dist/src/devkit-internals.d.ts +1 -0
- package/dist/src/devkit-internals.js +5 -2
- package/dist/src/hasher/check-task-files.d.ts +86 -0
- package/dist/src/hasher/check-task-files.js +378 -0
- package/dist/src/native/index.d.ts +27 -4
- package/dist/src/native/native-bindings.js +2 -0
- package/dist/src/native/nx.wasm32-wasi.debug.wasm +0 -0
- package/dist/src/native/nx.wasm32-wasi.wasm +0 -0
- package/dist/src/plugins/js/lock-file/utils/pnpm-normalizer.js +3 -0
- package/dist/src/plugins/js/project-graph/build-dependencies/target-project-locator.js +12 -4
- package/dist/src/project-graph/build-project-graph.js +7 -1
- package/dist/src/project-graph/plugins/loaded-nx-plugin.js +1 -0
- package/dist/src/project-graph/project-graph.js +3 -0
- package/dist/src/project-graph/utils/project-configuration/name-substitution-manager.d.ts +1 -0
- package/dist/src/project-graph/utils/project-configuration/name-substitution-manager.js +16 -2
- package/dist/src/project-graph/utils/project-configuration/project-nodes-manager.d.ts +5 -8
- package/dist/src/project-graph/utils/project-configuration/project-nodes-manager.js +11 -14
- package/dist/src/project-graph/utils/project-configuration/source-maps.d.ts +12 -5
- package/dist/src/project-graph/utils/project-configuration/source-maps.js +21 -7
- package/dist/src/project-graph/utils/project-configuration/target-defaults.d.ts +1 -1
- package/dist/src/project-graph/utils/project-configuration/target-defaults.js +26 -27
- package/dist/src/project-graph/utils/project-configuration/target-merging.js +50 -8
- package/dist/src/project-graph/utils/project-configuration/target-normalization.js +16 -3
- package/dist/src/project-graph/utils/project-configuration/utils.d.ts +15 -0
- package/dist/src/project-graph/utils/project-configuration/utils.js +42 -6
- package/dist/src/project-graph/utils/project-configuration-utils.d.ts +15 -12
- package/dist/src/project-graph/utils/project-configuration-utils.js +79 -99
- package/dist/src/tasks-runner/life-cycle.d.ts +2 -2
- package/dist/src/tasks-runner/life-cycle.js +2 -2
- package/dist/src/tasks-runner/pseudo-terminal.d.ts +1 -1
- package/dist/src/tasks-runner/pseudo-terminal.js +2 -2
- package/dist/src/tasks-runner/task-env.d.ts +9 -0
- package/dist/src/tasks-runner/task-env.js +26 -2
- package/dist/src/tasks-runner/task-orchestrator.d.ts +4 -1
- package/dist/src/tasks-runner/task-orchestrator.js +25 -12
- package/dist/src/utils/acknowledge-build-scripts.js +7 -5
- package/dist/src/utils/analytics-prompt.d.ts +0 -6
- package/dist/src/utils/analytics-prompt.js +0 -51
- package/dist/src/utils/catalog/bun-manager-utils.d.ts +8 -0
- package/dist/src/utils/catalog/bun-manager-utils.js +174 -0
- package/dist/src/utils/catalog/bun-manager.d.ts +28 -0
- package/dist/src/utils/catalog/bun-manager.js +130 -0
- package/dist/src/utils/catalog/index.d.ts +1 -1
- package/dist/src/utils/catalog/index.js +1 -1
- package/dist/src/utils/catalog/manager-factory.js +3 -0
- package/dist/src/utils/catalog/manager-utils.d.ts +8 -1
- package/dist/src/utils/catalog/manager-utils.js +9 -4
- package/dist/src/utils/catalog/manager.d.ts +13 -1
- package/dist/src/utils/catalog/manager.js +30 -0
- package/dist/src/utils/catalog/pnpm-manager.d.ts +2 -1
- package/dist/src/utils/catalog/pnpm-manager.js +3 -0
- package/dist/src/utils/catalog/types.d.ts +4 -0
- package/dist/src/utils/catalog/yarn-manager.d.ts +6 -2
- package/dist/src/utils/catalog/yarn-manager.js +23 -32
- package/dist/src/utils/git-utils.d.ts +15 -0
- package/dist/src/utils/git-utils.js +64 -6
- package/dist/src/utils/package-manager.d.ts +3 -1
- package/dist/src/utils/package-manager.js +22 -2
- package/dist/src/utils/workspace-id.d.ts +20 -0
- package/dist/src/utils/workspace-id.js +54 -0
- package/package.json +20 -15
package/dist/bin/nx.js
CHANGED
|
@@ -1,6 +1,12 @@
|
|
|
1
1
|
import type { EventDimensions } from '../native';
|
|
2
2
|
export declare const customDimensions: EventDimensions;
|
|
3
3
|
export type EventParameters = Partial<Record<EventDimensions[keyof EventDimensions], string | number | boolean>>;
|
|
4
|
+
/**
|
|
5
|
+
* Fraction of sessions that report perf spans. Stamping this rate on a
|
|
6
|
+
* measure's detail (as the sampleRate dimension) opts it into sampling; see
|
|
7
|
+
* is_sampled_in in native/telemetry/service.rs. Multiply GA counts by 1/rate.
|
|
8
|
+
*/
|
|
9
|
+
export declare const PERF_SPAN_SAMPLE_RATE = 0.1;
|
|
4
10
|
export declare function startAnalytics(): Promise<void>;
|
|
5
11
|
export declare function reportNxAddCommand(packageName: string, version: string): void;
|
|
6
12
|
export declare function reportNxGenerateCommand(generator: string): void;
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.customDimensions = void 0;
|
|
3
|
+
exports.PERF_SPAN_SAMPLE_RATE = exports.customDimensions = void 0;
|
|
4
4
|
exports.startAnalytics = startAnalytics;
|
|
5
5
|
exports.reportNxAddCommand = reportNxAddCommand;
|
|
6
6
|
exports.reportNxGenerateCommand = reportNxGenerateCommand;
|
|
@@ -19,7 +19,7 @@ const os = tslib_1.__importStar(require("os"));
|
|
|
19
19
|
const crypto_1 = require("crypto");
|
|
20
20
|
const machine_id_cache_1 = require("../utils/machine-id-cache");
|
|
21
21
|
const is_ci_1 = require("../utils/is-ci");
|
|
22
|
-
const
|
|
22
|
+
const workspace_id_1 = require("../utils/workspace-id");
|
|
23
23
|
const db_connection_1 = require("../utils/db-connection");
|
|
24
24
|
// Conditionally import telemetry functions only on non-WASM platforms
|
|
25
25
|
let initializeTelemetry;
|
|
@@ -42,6 +42,12 @@ exports.customDimensions = native_1.IS_WASM
|
|
|
42
42
|
? null
|
|
43
43
|
: (getEventDimensions?.() ?? null);
|
|
44
44
|
let _telemetryInitialized = false;
|
|
45
|
+
/**
|
|
46
|
+
* Fraction of sessions that report perf spans. Stamping this rate on a
|
|
47
|
+
* measure's detail (as the sampleRate dimension) opts it into sampling; see
|
|
48
|
+
* is_sampled_in in native/telemetry/service.rs. Multiply GA counts by 1/rate.
|
|
49
|
+
*/
|
|
50
|
+
exports.PERF_SPAN_SAMPLE_RATE = 0.1;
|
|
45
51
|
async function startAnalytics() {
|
|
46
52
|
// Analytics not supported on WASM
|
|
47
53
|
if (native_1.IS_WASM) {
|
|
@@ -52,17 +58,20 @@ async function startAnalytics() {
|
|
|
52
58
|
// detection, machine id, telemetry init) may throw past this boundary -
|
|
53
59
|
// on any failure, continue without telemetry.
|
|
54
60
|
try {
|
|
55
|
-
|
|
61
|
+
const nxJson = (0, nx_json_1.readNxJson)(workspace_root_1.workspaceRoot);
|
|
62
|
+
if (!isAnalyticsEnabled(nxJson)) {
|
|
56
63
|
return;
|
|
57
64
|
}
|
|
58
|
-
const
|
|
59
|
-
const workspaceId = (0, analytics_prompt_1.generateWorkspaceId)();
|
|
65
|
+
const workspaceId = (0, workspace_id_1.generateWorkspaceId)(workspace_root_1.workspaceRoot, nxJson);
|
|
60
66
|
if (!workspaceId) {
|
|
61
67
|
// Not a git repo — no telemetry
|
|
62
68
|
return;
|
|
63
69
|
}
|
|
64
70
|
const isNxCloud = !!(nxJson?.nxCloudId ?? nxJson?.nxCloudAccessToken);
|
|
65
|
-
|
|
71
|
+
// A CI fleet is not a user: shared images bake in /etc/machine-id, so a
|
|
72
|
+
// uid would collapse whole fleets into one GA "user" (and trip per-user
|
|
73
|
+
// collection caps). GA falls back to cid = workspace for CI traffic.
|
|
74
|
+
const userId = (0, is_ci_1.isCI)() ? undefined : await getTelemetryUserId(workspaceId);
|
|
66
75
|
const packageManagerInfo = getPackageManagerInfo();
|
|
67
76
|
const nodeVersion = (0, semver_1.parse)(process.version);
|
|
68
77
|
const nodeVersionString = nodeVersion
|
|
@@ -226,8 +235,7 @@ function getPackageManagerInfo() {
|
|
|
226
235
|
version: (0, package_manager_1.getPackageManagerVersion)(pm),
|
|
227
236
|
};
|
|
228
237
|
}
|
|
229
|
-
function isAnalyticsEnabled() {
|
|
230
|
-
const nxJson = (0, nx_json_1.readNxJson)(workspace_root_1.workspaceRoot);
|
|
238
|
+
function isAnalyticsEnabled(nxJson) {
|
|
231
239
|
return nxJson?.analytics === true;
|
|
232
240
|
}
|
|
233
241
|
// Mix workspace id in: shared Docker images (Gitpod, Cypress, etc.) bake
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export { customDimensions, EventParameters, startAnalytics, reportNxAddCommand, reportNxGenerateCommand, reportCommandRunEvent, reportEvent, flushAnalytics, } from './analytics';
|
|
1
|
+
export { customDimensions, EventParameters, PERF_SPAN_SAMPLE_RATE, startAnalytics, reportNxAddCommand, reportNxGenerateCommand, reportCommandRunEvent, reportEvent, flushAnalytics, } from './analytics';
|
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.flushAnalytics = exports.reportEvent = exports.reportCommandRunEvent = exports.reportNxGenerateCommand = exports.reportNxAddCommand = exports.startAnalytics = exports.customDimensions = void 0;
|
|
3
|
+
exports.flushAnalytics = exports.reportEvent = exports.reportCommandRunEvent = exports.reportNxGenerateCommand = exports.reportNxAddCommand = exports.startAnalytics = exports.PERF_SPAN_SAMPLE_RATE = exports.customDimensions = void 0;
|
|
4
4
|
var analytics_1 = require("./analytics");
|
|
5
5
|
Object.defineProperty(exports, "customDimensions", { enumerable: true, get: function () { return analytics_1.customDimensions; } });
|
|
6
|
+
Object.defineProperty(exports, "PERF_SPAN_SAMPLE_RATE", { enumerable: true, get: function () { return analytics_1.PERF_SPAN_SAMPLE_RATE; } });
|
|
6
7
|
Object.defineProperty(exports, "startAnalytics", { enumerable: true, get: function () { return analytics_1.startAnalytics; } });
|
|
7
8
|
Object.defineProperty(exports, "reportNxAddCommand", { enumerable: true, get: function () { return analytics_1.reportNxAddCommand; } });
|
|
8
9
|
Object.defineProperty(exports, "reportNxGenerateCommand", { enumerable: true, get: function () { return analytics_1.reportNxGenerateCommand; } });
|
|
@@ -50,6 +50,7 @@ export declare function generateGraph(args: {
|
|
|
50
50
|
exclude?: string[];
|
|
51
51
|
affected?: boolean;
|
|
52
52
|
}, affectedProjects: string[]): Promise<void>;
|
|
53
|
+
export declare function getExpandedTaskInputs(depGraphClientResponse: ProjectGraphClientResponse, expandedTaskInputsCache: Map<string, Record<string, string[]>>, taskId: string): Promise<Record<string, string[]>>;
|
|
53
54
|
/**
|
|
54
55
|
* The data type that `nx graph --file graph.json` or `nx build --graph graph.json` contains
|
|
55
56
|
*/
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.generateGraph = generateGraph;
|
|
4
|
+
exports.getExpandedTaskInputs = getExpandedTaskInputs;
|
|
4
5
|
const tslib_1 = require("tslib");
|
|
5
6
|
const crypto_1 = require("crypto");
|
|
6
7
|
const node_child_process_1 = require("node:child_process");
|
|
@@ -9,7 +10,6 @@ const daemon_socket_messenger_1 = require("../../daemon/client/daemon-socket-mes
|
|
|
9
10
|
const http = tslib_1.__importStar(require("node:http"));
|
|
10
11
|
const minimatch_1 = require("minimatch");
|
|
11
12
|
const node_url_1 = require("node:url");
|
|
12
|
-
const open_1 = tslib_1.__importDefault(require("open"));
|
|
13
13
|
const node_path_1 = require("node:path");
|
|
14
14
|
const net = tslib_1.__importStar(require("node:net"));
|
|
15
15
|
const node_perf_hooks_1 = require("node:perf_hooks");
|
|
@@ -34,6 +34,7 @@ const create_task_hasher_1 = require("../../hasher/create-task-hasher");
|
|
|
34
34
|
const task_env_1 = require("../../tasks-runner/task-env");
|
|
35
35
|
const error_types_1 = require("../../project-graph/error-types");
|
|
36
36
|
const nx_cloud_utils_1 = require("../../utils/nx-cloud-utils");
|
|
37
|
+
const split_target_1 = require("../../utils/split-target");
|
|
37
38
|
// maps file extention to MIME types
|
|
38
39
|
const mimeType = {
|
|
39
40
|
'.ico': 'image/x-icon',
|
|
@@ -349,7 +350,11 @@ async function generateGraph(args, affectedProjects) {
|
|
|
349
350
|
title: `Project graph started at ${url.toString()}`,
|
|
350
351
|
});
|
|
351
352
|
if (args.open) {
|
|
352
|
-
(
|
|
353
|
+
new Function('return import("open")')()
|
|
354
|
+
.then((m) => m.default(url.toString()))
|
|
355
|
+
.catch(() => {
|
|
356
|
+
// Ignore errors when opening browser (e.g. no browser available)
|
|
357
|
+
});
|
|
353
358
|
}
|
|
354
359
|
return new Promise((res) => {
|
|
355
360
|
app.once('close', res);
|
|
@@ -438,7 +443,7 @@ async function startServer(html, environmentJs, host, port = 4211, watchForChang
|
|
|
438
443
|
node_perf_hooks_1.performance.mark('task input generation:start');
|
|
439
444
|
const taskId = parsedUrl.searchParams.get('taskId');
|
|
440
445
|
res.writeHead(200, { 'Content-Type': 'application/json' });
|
|
441
|
-
const inputs = await getExpandedTaskInputs(taskId);
|
|
446
|
+
const inputs = await getExpandedTaskInputs(currentProjectGraphClientResponse, expandedTaskInputsCache, taskId);
|
|
442
447
|
node_perf_hooks_1.performance.mark('task input generation:end');
|
|
443
448
|
res.end(JSON.stringify({ [taskId]: inputs }));
|
|
444
449
|
node_perf_hooks_1.performance.measure('task input generation', 'task input generation:start', 'task input generation:end');
|
|
@@ -823,19 +828,23 @@ async function createTaskGraphForTargetsAndProjects(targetNames, projectNames, c
|
|
|
823
828
|
};
|
|
824
829
|
}
|
|
825
830
|
}
|
|
826
|
-
async function getExpandedTaskInputs(taskId) {
|
|
831
|
+
async function getExpandedTaskInputs(depGraphClientResponse, expandedTaskInputsCache, taskId) {
|
|
827
832
|
// Check cache first
|
|
828
833
|
if (expandedTaskInputsCache.has(taskId)) {
|
|
829
834
|
return expandedTaskInputsCache.get(taskId);
|
|
830
835
|
}
|
|
831
836
|
// Use the optimized version that only creates the specific task graph needed
|
|
832
|
-
|
|
837
|
+
// Use colon-aware splitting so that target names containing colons
|
|
838
|
+
// (e.g. "test:integration") are parsed correctly instead of being
|
|
839
|
+
// mistaken for a target + configuration pair.
|
|
840
|
+
const projectNodes = Object.fromEntries(depGraphClientResponse.projects.map((p) => [p.name, p]));
|
|
841
|
+
const [projectName, targetName, configuration] = (0, split_target_1.splitTargetFromNodes)(taskId, projectNodes, { silent: true });
|
|
833
842
|
const taskGraphResponse = await createTaskGraphForTargetsAndProjects([targetName], [projectName], configuration);
|
|
834
843
|
const allWorkspaceFiles = await (0, all_file_data_1.allFileData)();
|
|
835
844
|
const inputs = taskGraphResponse.plans?.[taskId];
|
|
836
845
|
let result = {};
|
|
837
846
|
if (inputs) {
|
|
838
|
-
result = expandInputs(inputs,
|
|
847
|
+
result = expandInputs(inputs, depGraphClientResponse.projects.find((p) => p.name === projectName), allWorkspaceFiles, depGraphClientResponse);
|
|
839
848
|
}
|
|
840
849
|
// Cache the result
|
|
841
850
|
expandedTaskInputsCache.set(taskId, result);
|
|
@@ -1,12 +1,9 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.setupIntegratedWorkspace = setupIntegratedWorkspace;
|
|
4
|
-
const child_process_1 = require("
|
|
5
|
-
const package_manager_1 = require("../../../../utils/package-manager");
|
|
4
|
+
const child_process_1 = require("../../../../utils/child-process");
|
|
6
5
|
function setupIntegratedWorkspace() {
|
|
7
|
-
|
|
8
|
-
(0, child_process_1.execSync)(`${pmc.exec} nx g @nx/angular:ng-add`, {
|
|
6
|
+
(0, child_process_1.runNxSync)(`g @nx/angular:ng-add`, {
|
|
9
7
|
stdio: [0, 1, 2],
|
|
10
|
-
windowsHide: true,
|
|
11
8
|
});
|
|
12
9
|
}
|
|
@@ -107,6 +107,9 @@ async function getLegacyMigrationFunctionIfApplicable(repoRoot, options) {
|
|
|
107
107
|
unscopedPkgName,
|
|
108
108
|
}, pmc);
|
|
109
109
|
output_1.output.log({ title: '📝 Setting up workspace' });
|
|
110
|
+
// Intentionally not runNxSync: legacyMigrationCommand is either the Angular
|
|
111
|
+
// CLI (`ng g ...:ng-add`) or a version-pinned `nx@<version> init`, neither
|
|
112
|
+
// of which is the local nx that runNxSync would resolve.
|
|
110
113
|
(0, child_process_1.execSync)(`${pmc.exec} ${legacyMigrationCommand}`, {
|
|
111
114
|
stdio: [0, 1, 2],
|
|
112
115
|
windowsHide: true,
|
|
@@ -69,7 +69,10 @@ function generateDotNxSetup(version) {
|
|
|
69
69
|
(0, tree_1.flushChanges)(host.root, changes);
|
|
70
70
|
// Ensure that the dot-nx installation is available.
|
|
71
71
|
// This is needed when using a global nx with dot-nx, otherwise running any nx command using global command will fail due to missing modules.
|
|
72
|
-
//
|
|
72
|
+
// Intentionally not runNxSync: when the repo has a package.json it would run
|
|
73
|
+
// `<pm> exec nx` instead of the wrapper, but this call must run the
|
|
74
|
+
// just-written wrapper itself so it bootstraps .nx/installation.
|
|
75
|
+
// Pipe stderr so failures surface in telemetry instead of bare "Command failed".
|
|
73
76
|
try {
|
|
74
77
|
(0, child_process_1.execSync)(getDotNxWrapperVersionCommand(), {
|
|
75
78
|
stdio: ['ignore', 'ignore', 'pipe'],
|
|
@@ -1047,6 +1047,15 @@ function createFetcher(pmc) {
|
|
|
1047
1047
|
migrationsCache[packageName + '-' + packageVersion] = migrations;
|
|
1048
1048
|
}
|
|
1049
1049
|
migrations = fetchMigrations(packageName, packageVersion, setCache).then((result) => {
|
|
1050
|
+
// An exact requested version must come back verbatim; a mismatch means
|
|
1051
|
+
// a config surface (registry proxy, override, cooldown gate) silently
|
|
1052
|
+
// substituted another version, which would corrupt the whole plan.
|
|
1053
|
+
if ((0, semver_1.valid)(packageVersion) &&
|
|
1054
|
+
result.version &&
|
|
1055
|
+
result.version !== packageVersion) {
|
|
1056
|
+
throw new Error(`Fetching ${packageName}@${packageVersion} resolved to version ${result.version}. ` +
|
|
1057
|
+
`Check for registry, override, or minimum-release-age configuration that hides the requested version.`);
|
|
1058
|
+
}
|
|
1050
1059
|
if (result.schematics) {
|
|
1051
1060
|
result.generators = { ...result.schematics, ...result.generators };
|
|
1052
1061
|
delete result.schematics;
|
|
@@ -1107,7 +1116,13 @@ async function downloadPackageMigrationsFromRegistry(packageName, packageVersion
|
|
|
1107
1116
|
const { dir, cleanup } = (0, package_manager_1.createTempNpmDirectory)();
|
|
1108
1117
|
let result;
|
|
1109
1118
|
try {
|
|
1110
|
-
const { tarballPath } = await (0, package_manager_1.packageRegistryPack)(dir, packageName, packageVersion
|
|
1119
|
+
const { tarballPath } = await (0, package_manager_1.packageRegistryPack)(dir, packageName, packageVersion,
|
|
1120
|
+
// packageVersion is exact and already resolved through the workspace
|
|
1121
|
+
// package manager's min-release-age policy by the fetcher. In an npm
|
|
1122
|
+
// workspace the pack gate IS that policy, so leave it enforcing; for
|
|
1123
|
+
// other package managers npm's gate is foreign config with no
|
|
1124
|
+
// exclusions and would wrongly re-judge the vetted version.
|
|
1125
|
+
{ bypassMinReleaseAge: (0, package_manager_1.detectPackageManager)() !== 'npm' });
|
|
1111
1126
|
const fullTarballPath = (0, path_1.join)(dir, tarballPath);
|
|
1112
1127
|
let migrations;
|
|
1113
1128
|
try {
|
|
@@ -2307,6 +2322,10 @@ async function runMigration() {
|
|
|
2307
2322
|
process.env.npm_config_registry.match(/^https:\/\/registry\.(npmjs\.org|yarnpkg\.com)/)) {
|
|
2308
2323
|
delete process.env.npm_config_registry;
|
|
2309
2324
|
}
|
|
2325
|
+
// Intentionally not runNxSync: `p` is an nx CLI freshly installed into a
|
|
2326
|
+
// temp dir by nxCliPath() (latest, or NX_MIGRATE_CLI_VERSION), so
|
|
2327
|
+
// migrations run with an up-to-date migrate implementation instead of
|
|
2328
|
+
// the workspace's current nx.
|
|
2310
2329
|
return runOrReturnExitCode(() => (0, child_process_1.execSync)(`${p} _migrate ${process.argv.slice(3).join(' ')}`, {
|
|
2311
2330
|
stdio: ['inherit', 'inherit', 'inherit'],
|
|
2312
2331
|
windowsHide: true,
|
|
@@ -26,7 +26,6 @@ const workspace_root_1 = require("../../../utils/workspace-root");
|
|
|
26
26
|
const git_utils_1 = require("../../../utils/git-utils");
|
|
27
27
|
const pc = tslib_1.__importStar(require("picocolors"));
|
|
28
28
|
const ora = require('ora');
|
|
29
|
-
const open = require('open');
|
|
30
29
|
function onlyDefaultRunnerIsUsed(nxJson) {
|
|
31
30
|
const defaultRunner = nxJson.tasksRunnerOptions?.default?.runner;
|
|
32
31
|
if (!defaultRunner) {
|
|
@@ -161,6 +160,7 @@ async function runConnectToNxCloud(options, command) {
|
|
|
161
160
|
try {
|
|
162
161
|
const cloudConnectSpinner = ora(`Opening Nx Cloud ${connectCloudUrl} in your browser to connect your workspace.`).start();
|
|
163
162
|
await sleep(2000);
|
|
163
|
+
const { default: open } = await new Function('return import("open")')();
|
|
164
164
|
await open(connectCloudUrl);
|
|
165
165
|
cloudConnectSpinner.succeed();
|
|
166
166
|
}
|
|
@@ -39,6 +39,8 @@ async function viewLogs() {
|
|
|
39
39
|
return 1;
|
|
40
40
|
}
|
|
41
41
|
const pmc = (0, package_manager_1.getPackageManagerCommand)();
|
|
42
|
+
// Intentionally not runNxSync: this invokes the separate `nx-cloud` binary,
|
|
43
|
+
// not the nx CLI that runNxSync resolves.
|
|
42
44
|
(0, child_process_1.execSync)(`${pmc.exec} nx-cloud upload-and-show-run-details`, {
|
|
43
45
|
stdio: [0, 1, 2],
|
|
44
46
|
windowsHide: true,
|
|
@@ -235,7 +235,7 @@ class GithubRemoteReleaseClient extends remote_release_client_1.RemoteReleaseCli
|
|
|
235
235
|
if (!shouldContinueInGitHub) {
|
|
236
236
|
return;
|
|
237
237
|
}
|
|
238
|
-
const open =
|
|
238
|
+
const { default: open } = await new Function('return import("open")')();
|
|
239
239
|
await open(result.url)
|
|
240
240
|
.then(() => {
|
|
241
241
|
console.info(`\nFollow up in the browser to manually create the release:\n\n` +
|
|
@@ -157,7 +157,7 @@ class GitLabRemoteReleaseClient extends remote_release_client_1.RemoteReleaseCli
|
|
|
157
157
|
if (!shouldContinueInGitLab) {
|
|
158
158
|
return;
|
|
159
159
|
}
|
|
160
|
-
const open =
|
|
160
|
+
const { default: open } = await new Function('return import("open")')();
|
|
161
161
|
await open(result.url)
|
|
162
162
|
.then(() => {
|
|
163
163
|
console.info(`\nFollow up in the browser to manually create the release:\n\n` +
|
|
@@ -1,185 +1,82 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.showTargetInputsHandler = showTargetInputsHandler;
|
|
4
|
-
const
|
|
5
|
-
const
|
|
6
|
-
const
|
|
4
|
+
const check_task_files_1 = require("../../../hasher/check-task-files");
|
|
5
|
+
const utils_1 = require("../../../tasks-runner/utils");
|
|
6
|
+
const utils_2 = require("./utils");
|
|
7
7
|
// ── Handler ─────────────────────────────────────────────────────────
|
|
8
8
|
async function showTargetInputsHandler(args) {
|
|
9
|
-
const t = await (0,
|
|
10
|
-
const
|
|
11
|
-
if (
|
|
12
|
-
renderCustomHasherWarning(
|
|
9
|
+
const t = await (0, utils_2.resolveTarget)(args);
|
|
10
|
+
const { projectName, targetName, configuration } = t;
|
|
11
|
+
if ((0, utils_2.hasCustomHasher)(projectName, targetName, t.graph)) {
|
|
12
|
+
renderCustomHasherWarning(projectName, targetName, args);
|
|
13
13
|
process.exitCode = 1;
|
|
14
14
|
return;
|
|
15
15
|
}
|
|
16
|
-
const
|
|
16
|
+
const taskId = (0, utils_1.createTaskId)(projectName, targetName, configuration);
|
|
17
|
+
const hashInputs = await (0, check_task_files_1.getTaskRawInputs)(taskId, {
|
|
18
|
+
projectGraph: t.graph,
|
|
19
|
+
nxJson: t.nxJson,
|
|
20
|
+
});
|
|
21
|
+
if (!hashInputs) {
|
|
22
|
+
throw new Error(`Could not find hash plan for task "${taskId}".`);
|
|
23
|
+
}
|
|
17
24
|
if (args.check !== undefined) {
|
|
18
|
-
const
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
renderBatchCheckInputs(results, t.projectName, t.targetName);
|
|
22
|
-
}
|
|
23
|
-
else {
|
|
24
|
-
for (const data of results)
|
|
25
|
-
renderCheckInput(data);
|
|
26
|
-
}
|
|
27
|
-
for (const data of results) {
|
|
28
|
-
process.exitCode ||=
|
|
29
|
-
data.isInput || data.containedInputFiles.length ? 0 : 1;
|
|
30
|
-
}
|
|
25
|
+
const results = await checkInputs(taskId, args.check, hashInputs);
|
|
26
|
+
(0, utils_2.renderCheckResults)(results, projectName, targetName, 'input');
|
|
27
|
+
(0, utils_2.setCheckExitCode)(results);
|
|
31
28
|
return;
|
|
32
29
|
}
|
|
33
|
-
renderInputs({ project:
|
|
30
|
+
renderInputs({ project: projectName, target: targetName, ...hashInputs }, t.node.data.targets[targetName].inputs, args);
|
|
34
31
|
}
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
const
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
32
|
+
// ── Data resolution ─────────────────────────────────────────────────
|
|
33
|
+
async function checkInputs(taskId, check, hashInputs) {
|
|
34
|
+
// checkFilesAreInputs matches environment/runtime/external names against the
|
|
35
|
+
// raw argument and paths against the workspace-relative form, so both are
|
|
36
|
+
// passed through — it has no cwd of its own.
|
|
37
|
+
const candidates = (0, utils_2.deduplicateFolderEntries)(check).map((value) => ({
|
|
38
|
+
value,
|
|
39
|
+
path: (0, utils_2.normalizePath)(value),
|
|
40
|
+
}));
|
|
41
|
+
const { categories } = await (0, check_task_files_1.checkFilesAreInputs)(taskId, candidates);
|
|
42
|
+
return candidates.map(({ value, path }) => {
|
|
43
|
+
const category = categories.get(value);
|
|
44
|
+
return {
|
|
45
|
+
value,
|
|
46
|
+
file: path,
|
|
47
|
+
matched: !!category,
|
|
48
|
+
category,
|
|
49
|
+
contained: category ? [] : (0, utils_2.pathsUnder)(path, hashInputs.files),
|
|
50
|
+
};
|
|
44
51
|
});
|
|
45
|
-
const targetConfig = graph.nodes[projectName]?.data?.targets?.[targetName];
|
|
46
|
-
const effectiveConfig = configuration ?? targetConfig?.defaultConfiguration;
|
|
47
|
-
const taskId = effectiveConfig
|
|
48
|
-
? `${projectName}:${targetName}:${effectiveConfig}`
|
|
49
|
-
: `${projectName}:${targetName}`;
|
|
50
|
-
const result = plan[taskId];
|
|
51
|
-
if (!result) {
|
|
52
|
-
throw new Error(`Could not find hash plan for task "${taskId}". Available tasks: ${Object.keys(plan).join(', ')}`);
|
|
53
|
-
}
|
|
54
|
-
return result;
|
|
55
|
-
}
|
|
56
|
-
function resolveCheckFromInputs(rawValue, projectName, targetName, inputs) {
|
|
57
|
-
for (const [category, arr] of [
|
|
58
|
-
['environment', inputs.environment],
|
|
59
|
-
['runtime', inputs.runtime],
|
|
60
|
-
['external', inputs.external],
|
|
61
|
-
['depOutputs', inputs.depOutputs],
|
|
62
|
-
]) {
|
|
63
|
-
if (arr.includes(rawValue)) {
|
|
64
|
-
return {
|
|
65
|
-
value: rawValue,
|
|
66
|
-
file: rawValue,
|
|
67
|
-
project: projectName,
|
|
68
|
-
target: targetName,
|
|
69
|
-
isInput: true,
|
|
70
|
-
matchedCategory: category,
|
|
71
|
-
containedInputFiles: [],
|
|
72
|
-
};
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
const fileToCheck = (0, utils_1.normalizePath)(rawValue);
|
|
76
|
-
const isFile = inputs.files.includes(fileToCheck);
|
|
77
|
-
let containedInputFiles = [];
|
|
78
|
-
if (!isFile) {
|
|
79
|
-
if (fileToCheck === '') {
|
|
80
|
-
containedInputFiles = inputs.files;
|
|
81
|
-
}
|
|
82
|
-
else {
|
|
83
|
-
const dirPrefix = fileToCheck.endsWith('/')
|
|
84
|
-
? fileToCheck
|
|
85
|
-
: fileToCheck + '/';
|
|
86
|
-
containedInputFiles = inputs.files.filter((f) => f.startsWith(dirPrefix));
|
|
87
|
-
}
|
|
88
|
-
}
|
|
89
|
-
return {
|
|
90
|
-
value: rawValue,
|
|
91
|
-
file: fileToCheck,
|
|
92
|
-
project: projectName,
|
|
93
|
-
target: targetName,
|
|
94
|
-
isInput: isFile,
|
|
95
|
-
matchedCategory: isFile || containedInputFiles.length > 0
|
|
96
|
-
? 'files'
|
|
97
|
-
: null,
|
|
98
|
-
containedInputFiles,
|
|
99
|
-
};
|
|
100
52
|
}
|
|
101
53
|
// ── Render ──────────────────────────────────────────────────────────
|
|
102
54
|
function renderInputs(data, configuredInputs, args) {
|
|
103
55
|
if (args.json) {
|
|
104
|
-
|
|
105
|
-
const result = {};
|
|
106
|
-
for (const [k, v] of Object.entries(jsonData)) {
|
|
107
|
-
if (Array.isArray(v) && v.length === 0)
|
|
108
|
-
continue;
|
|
109
|
-
result[k] = v;
|
|
110
|
-
}
|
|
111
|
-
console.log(JSON.stringify(result, null, 2));
|
|
56
|
+
(0, utils_2.printJson)(data);
|
|
112
57
|
return;
|
|
113
58
|
}
|
|
114
|
-
const c = (0,
|
|
59
|
+
const c = (0, utils_2.pc)();
|
|
115
60
|
console.log(`${c.bold('Inputs for')} ${c.cyan(data.project)}:${c.green(data.target)}`);
|
|
116
|
-
if (configuredInputs
|
|
117
|
-
(0,
|
|
118
|
-
}
|
|
119
|
-
(0, utils_1.printList)('External dependencies', [...data.external].sort());
|
|
120
|
-
(0, utils_1.printList)('Runtime inputs', [...data.runtime].sort());
|
|
121
|
-
(0, utils_1.printList)('Environment variables', [...data.environment].sort());
|
|
122
|
-
(0, utils_1.printList)(`Files (${data.files.length})`, [...data.files, ...data.depOutputs].sort());
|
|
123
|
-
}
|
|
124
|
-
function renderCheckInput(data) {
|
|
125
|
-
const c = (0, utils_1.pc)();
|
|
126
|
-
const categoryLabel = data.matchedCategory
|
|
127
|
-
? ` (${data.matchedCategory})`
|
|
128
|
-
: '';
|
|
129
|
-
if (data.isInput) {
|
|
130
|
-
console.log(`${c.green('✓')} ${c.bold(data.value)} is an input for ${c.cyan(data.project)}:${c.green(data.target)}${categoryLabel}`);
|
|
131
|
-
}
|
|
132
|
-
else if (data.containedInputFiles.length > 0) {
|
|
133
|
-
console.log(`${c.yellow('~')} ${c.bold(data.file)} is a directory containing ${c.bold(String(data.containedInputFiles.length))} input file(s) for ${c.cyan(data.project)}:${c.green(data.target)}`);
|
|
134
|
-
for (const f of [...data.containedInputFiles].sort())
|
|
135
|
-
console.log(` ${f}`);
|
|
136
|
-
}
|
|
137
|
-
else {
|
|
138
|
-
console.log(`${c.red('✗')} ${c.bold(data.value)} is ${c.red('not')} an input for ${c.cyan(data.project)}:${c.green(data.target)}`);
|
|
139
|
-
}
|
|
140
|
-
}
|
|
141
|
-
function renderBatchCheckInputs(results, projectName, targetName) {
|
|
142
|
-
const c = (0, utils_1.pc)();
|
|
143
|
-
const label = `${c.cyan(projectName)}:${c.green(targetName)}`;
|
|
144
|
-
const matched = [];
|
|
145
|
-
const directories = [];
|
|
146
|
-
const unmatched = [];
|
|
147
|
-
for (const r of results) {
|
|
148
|
-
if (r.isInput) {
|
|
149
|
-
matched.push(r.value);
|
|
150
|
-
}
|
|
151
|
-
else if (r.containedInputFiles.length > 0) {
|
|
152
|
-
directories.push({ value: r.file, count: r.containedInputFiles.length });
|
|
153
|
-
}
|
|
154
|
-
else {
|
|
155
|
-
unmatched.push(r.value);
|
|
156
|
-
}
|
|
157
|
-
}
|
|
158
|
-
if (matched.length > 0 || directories.length > 0) {
|
|
159
|
-
console.log(`\n${c.green('✓')} These arguments were inputs for ${label}:`);
|
|
160
|
-
for (const v of matched)
|
|
161
|
-
console.log(` ${v}`);
|
|
162
|
-
for (const d of directories) {
|
|
163
|
-
console.log(` ${d.value} (directory containing ${d.count} input files)`);
|
|
164
|
-
}
|
|
165
|
-
}
|
|
166
|
-
if (unmatched.length > 0) {
|
|
167
|
-
console.log(`\n${c.red('✗')} These arguments were ${c.red('not')} inputs for ${label}:`);
|
|
168
|
-
for (const v of unmatched)
|
|
169
|
-
console.log(` ${v}`);
|
|
61
|
+
if (configuredInputs?.length) {
|
|
62
|
+
(0, utils_2.printList)('Configured inputs', configuredInputs.map((i) => typeof i === 'string' ? i : JSON.stringify(i)));
|
|
170
63
|
}
|
|
64
|
+
(0, utils_2.printList)('External dependencies', [...data.external].sort());
|
|
65
|
+
(0, utils_2.printList)('Runtime inputs', [...data.runtime].sort());
|
|
66
|
+
(0, utils_2.printList)('Environment variables', [...data.environment].sort());
|
|
67
|
+
(0, utils_2.printList)(`Files (${data.files.length})`, [...data.files, ...data.depOutputs].sort());
|
|
171
68
|
}
|
|
172
69
|
function renderCustomHasherWarning(projectName, targetName, args) {
|
|
173
|
-
const c = (0,
|
|
174
|
-
const label = `${c.cyan(projectName)}:${c.green(targetName)}`;
|
|
70
|
+
const c = (0, utils_2.pc)();
|
|
175
71
|
if (args.json) {
|
|
176
|
-
|
|
72
|
+
(0, utils_2.printJson)({
|
|
177
73
|
project: projectName,
|
|
178
74
|
target: targetName,
|
|
179
75
|
warning: 'This target uses a custom hasher. Configured inputs do not affect the cache hash.',
|
|
180
|
-
}
|
|
76
|
+
});
|
|
181
77
|
return;
|
|
182
78
|
}
|
|
79
|
+
const label = `${c.cyan(projectName)}:${c.green(targetName)}`;
|
|
183
80
|
console.log(`\n${c.yellow('⚠')} ${label} uses a ${c.yellow('custom hasher')}.`);
|
|
184
81
|
console.log(` Configured inputs do not affect the cache hash for this target.`);
|
|
185
82
|
console.log(` The executor's hasher determines what is included in the hash.`);
|