nx 18.1.1 → 18.2.0-beta.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/package.json +12 -12
- package/src/adapter/compat.d.ts +1 -1
- package/src/adapter/compat.js +1 -0
- package/src/command-line/add/add.js +1 -1
- package/src/command-line/affected/command-object.js +49 -22
- package/src/command-line/generate/generate.js +3 -3
- package/src/command-line/init/init-v2.js +43 -31
- package/src/command-line/run/command-object.js +9 -2
- package/src/command-line/run/run-one.js +1 -1
- package/src/command-line/run/run.js +15 -5
- package/src/command-line/run-many/command-object.js +4 -1
- package/src/command-line/show/command-object.d.ts +2 -0
- package/src/command-line/show/command-object.js +19 -2
- package/src/config/workspace-json-project-json.d.ts +4 -0
- package/src/core/graph/main.js +1 -1
- package/src/core/graph/polyfills.js +1 -1
- package/src/daemon/client/client.js +19 -7
- package/src/daemon/daemon-project-graph-error.d.ts +8 -0
- package/src/daemon/daemon-project-graph-error.js +13 -0
- package/src/daemon/server/handle-hash-tasks.js +11 -1
- package/src/daemon/server/project-graph-incremental-recomputation.d.ts +1 -0
- package/src/daemon/server/project-graph-incremental-recomputation.js +55 -6
- package/src/daemon/server/shutdown-utils.js +1 -3
- package/src/daemon/socket-utils.js +7 -1
- package/src/executors/run-commands/run-commands.impl.js +15 -9
- package/src/executors/run-script/run-script.impl.js +1 -1
- package/src/plugins/js/index.js +1 -1
- package/src/plugins/js/lock-file/lock-file.d.ts +2 -2
- package/src/plugins/js/lock-file/lock-file.js +2 -2
- package/src/plugins/js/versions.d.ts +1 -1
- package/src/plugins/js/versions.js +1 -1
- package/src/project-graph/build-project-graph.d.ts +18 -1
- package/src/project-graph/build-project-graph.js +71 -24
- package/src/project-graph/project-graph.d.ts +23 -2
- package/src/project-graph/project-graph.js +117 -14
- package/src/project-graph/utils/project-configuration-utils.d.ts +27 -4
- package/src/project-graph/utils/project-configuration-utils.js +176 -45
- package/src/project-graph/utils/retrieve-workspace-files.d.ts +6 -14
- package/src/project-graph/utils/retrieve-workspace-files.js +3 -16
- package/src/tasks-runner/forked-process-task-runner.d.ts +2 -1
- package/src/tasks-runner/forked-process-task-runner.js +19 -8
- package/src/tasks-runner/pseudo-terminal.d.ts +2 -1
- package/src/tasks-runner/pseudo-terminal.js +27 -1
- package/src/tasks-runner/task-orchestrator.js +4 -22
- package/src/utils/output.d.ts +1 -1
- package/src/utils/params.d.ts +2 -2
- package/src/utils/params.js +14 -0
@@ -1,6 +1,8 @@
|
|
1
1
|
"use strict";
|
2
|
+
var _ProjectGraphError_errors, _ProjectGraphError_partialProjectGraph, _ProjectGraphError_partialSourceMaps;
|
2
3
|
Object.defineProperty(exports, "__esModule", { value: true });
|
3
|
-
exports.createProjectGraphAndSourceMapsAsync = exports.createProjectGraphAsync = exports.buildProjectGraphAndSourceMapsWithoutDaemon = exports.readProjectsConfigurationFromProjectGraph = exports.readCachedProjectConfiguration = exports.readCachedProjectGraph = void 0;
|
4
|
+
exports.createProjectGraphAndSourceMapsAsync = exports.createProjectGraphAsync = exports.ProjectGraphError = exports.buildProjectGraphAndSourceMapsWithoutDaemon = exports.readProjectsConfigurationFromProjectGraph = exports.readCachedProjectConfiguration = exports.readCachedProjectGraph = void 0;
|
5
|
+
const tslib_1 = require("tslib");
|
4
6
|
const nx_deps_cache_1 = require("./nx-deps-cache");
|
5
7
|
const build_project_graph_1 = require("./build-project-graph");
|
6
8
|
const output_1 = require("../utils/output");
|
@@ -13,6 +15,7 @@ const perf_hooks_1 = require("perf_hooks");
|
|
13
15
|
const retrieve_workspace_files_1 = require("./utils/retrieve-workspace-files");
|
14
16
|
const nx_json_1 = require("../config/nx-json");
|
15
17
|
const nx_plugin_1 = require("../utils/nx-plugin");
|
18
|
+
const project_configuration_utils_1 = require("./utils/project-configuration-utils");
|
16
19
|
/**
|
17
20
|
* Synchronously reads the latest cached copy of the workspace's ProjectGraph.
|
18
21
|
* @throws {Error} if there is no cached ProjectGraph to read from
|
@@ -70,29 +73,127 @@ async function buildProjectGraphAndSourceMapsWithoutDaemon() {
|
|
70
73
|
global.NX_GRAPH_CREATION = true;
|
71
74
|
const nxJson = (0, nx_json_1.readNxJson)();
|
72
75
|
perf_hooks_1.performance.mark('retrieve-project-configurations:start');
|
73
|
-
|
76
|
+
let configurationResult;
|
77
|
+
let projectConfigurationsError;
|
78
|
+
try {
|
79
|
+
configurationResult = await (0, retrieve_workspace_files_1.retrieveProjectConfigurations)(workspace_root_1.workspaceRoot, nxJson);
|
80
|
+
}
|
81
|
+
catch (e) {
|
82
|
+
if (e instanceof project_configuration_utils_1.ProjectConfigurationsError) {
|
83
|
+
projectConfigurationsError = e;
|
84
|
+
configurationResult = e.partialProjectConfigurationsResult;
|
85
|
+
}
|
86
|
+
else {
|
87
|
+
throw e;
|
88
|
+
}
|
89
|
+
}
|
90
|
+
const { projects, externalNodes, sourceMaps, projectRootMap } = configurationResult;
|
74
91
|
perf_hooks_1.performance.mark('retrieve-project-configurations:end');
|
75
92
|
perf_hooks_1.performance.mark('retrieve-workspace-files:start');
|
76
93
|
const { allWorkspaceFiles, fileMap, rustReferences } = await (0, retrieve_workspace_files_1.retrieveWorkspaceFiles)(workspace_root_1.workspaceRoot, projectRootMap);
|
77
94
|
perf_hooks_1.performance.mark('retrieve-workspace-files:end');
|
78
95
|
const cacheEnabled = process.env.NX_CACHE_PROJECT_GRAPH !== 'false';
|
79
96
|
perf_hooks_1.performance.mark('build-project-graph-using-project-file-map:start');
|
80
|
-
|
97
|
+
let createDependenciesError;
|
98
|
+
let projectGraphResult;
|
99
|
+
try {
|
100
|
+
projectGraphResult = await (0, build_project_graph_1.buildProjectGraphUsingProjectFileMap)(projects, externalNodes, fileMap, allWorkspaceFiles, rustReferences, cacheEnabled ? (0, nx_deps_cache_1.readFileMapCache)() : null);
|
101
|
+
}
|
102
|
+
catch (e) {
|
103
|
+
if (e instanceof build_project_graph_1.CreateDependenciesError) {
|
104
|
+
projectGraphResult = {
|
105
|
+
projectGraph: e.partialProjectGraph,
|
106
|
+
projectFileMapCache: null,
|
107
|
+
};
|
108
|
+
createDependenciesError = e;
|
109
|
+
}
|
110
|
+
else {
|
111
|
+
throw e;
|
112
|
+
}
|
113
|
+
}
|
114
|
+
const { projectGraph, projectFileMapCache } = projectGraphResult;
|
81
115
|
perf_hooks_1.performance.mark('build-project-graph-using-project-file-map:end');
|
82
116
|
(0, nx_plugin_1.unregisterPluginTSTranspiler)();
|
83
117
|
delete global.NX_GRAPH_CREATION;
|
84
|
-
|
118
|
+
const errors = [
|
119
|
+
...(projectConfigurationsError?.errors ?? []),
|
120
|
+
...(createDependenciesError?.errors ?? []),
|
121
|
+
];
|
122
|
+
if (errors.length > 0) {
|
123
|
+
throw new ProjectGraphError(errors, projectGraph, sourceMaps);
|
124
|
+
}
|
125
|
+
else {
|
126
|
+
if (cacheEnabled) {
|
127
|
+
(0, nx_deps_cache_1.writeCache)(projectFileMapCache, projectGraph);
|
128
|
+
}
|
129
|
+
return { projectGraph, sourceMaps };
|
130
|
+
}
|
85
131
|
}
|
86
132
|
exports.buildProjectGraphAndSourceMapsWithoutDaemon = buildProjectGraphAndSourceMapsWithoutDaemon;
|
133
|
+
class ProjectGraphError extends Error {
|
134
|
+
constructor(errors, partialProjectGraph, partialSourceMaps) {
|
135
|
+
super(`Failed to process project graph.`);
|
136
|
+
_ProjectGraphError_errors.set(this, void 0);
|
137
|
+
_ProjectGraphError_partialProjectGraph.set(this, void 0);
|
138
|
+
_ProjectGraphError_partialSourceMaps.set(this, void 0);
|
139
|
+
this.name = this.constructor.name;
|
140
|
+
tslib_1.__classPrivateFieldSet(this, _ProjectGraphError_errors, errors, "f");
|
141
|
+
tslib_1.__classPrivateFieldSet(this, _ProjectGraphError_partialProjectGraph, partialProjectGraph, "f");
|
142
|
+
tslib_1.__classPrivateFieldSet(this, _ProjectGraphError_partialSourceMaps, partialSourceMaps, "f");
|
143
|
+
this.stack = `${this.message}\n ${errors
|
144
|
+
.map((error) => error.stack.split('\n').join('\n '))
|
145
|
+
.join('\n')}`;
|
146
|
+
}
|
147
|
+
/**
|
148
|
+
* The daemon cannot throw errors which contain methods as they are not serializable.
|
149
|
+
*
|
150
|
+
* This method creates a new {@link ProjectGraphError} from a {@link DaemonProjectGraphError} with the methods based on the same serialized data.
|
151
|
+
*/
|
152
|
+
static fromDaemonProjectGraphError(e) {
|
153
|
+
return new ProjectGraphError(e.errors, e.projectGraph, e.sourceMaps);
|
154
|
+
}
|
155
|
+
/**
|
156
|
+
* This gets the partial project graph despite the errors which occured.
|
157
|
+
* This partial project graph may be missing nodes, properties of nodes, or dependencies.
|
158
|
+
* This is useful mostly for visualization/debugging. It should not be used for running tasks.
|
159
|
+
*/
|
160
|
+
getPartialProjectGraph() {
|
161
|
+
return tslib_1.__classPrivateFieldGet(this, _ProjectGraphError_partialProjectGraph, "f");
|
162
|
+
}
|
163
|
+
getPartialSourcemaps() {
|
164
|
+
return tslib_1.__classPrivateFieldGet(this, _ProjectGraphError_partialSourceMaps, "f");
|
165
|
+
}
|
166
|
+
getErrors() {
|
167
|
+
return tslib_1.__classPrivateFieldGet(this, _ProjectGraphError_errors, "f");
|
168
|
+
}
|
169
|
+
}
|
170
|
+
exports.ProjectGraphError = ProjectGraphError;
|
171
|
+
_ProjectGraphError_errors = new WeakMap(), _ProjectGraphError_partialProjectGraph = new WeakMap(), _ProjectGraphError_partialSourceMaps = new WeakMap();
|
87
172
|
function handleProjectGraphError(opts, e) {
|
88
173
|
if (opts.exitOnError) {
|
89
|
-
const
|
90
|
-
|
91
|
-
title
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
174
|
+
const isVerbose = process.env.NX_VERBOSE_LOGGING === 'true';
|
175
|
+
if (e instanceof ProjectGraphError) {
|
176
|
+
let title = e.message;
|
177
|
+
if (isVerbose) {
|
178
|
+
title += ' See errors below.';
|
179
|
+
}
|
180
|
+
const bodyLines = isVerbose
|
181
|
+
? [e.stack]
|
182
|
+
: ['Pass --verbose to see the stacktraces.'];
|
183
|
+
output_1.output.error({
|
184
|
+
title,
|
185
|
+
bodyLines: bodyLines,
|
186
|
+
});
|
187
|
+
}
|
188
|
+
else {
|
189
|
+
const lines = e.message.split('\n');
|
190
|
+
output_1.output.error({
|
191
|
+
title: lines[0],
|
192
|
+
bodyLines: lines.slice(1),
|
193
|
+
});
|
194
|
+
if (isVerbose) {
|
195
|
+
console.error(e);
|
196
|
+
}
|
96
197
|
}
|
97
198
|
process.exit(1);
|
98
199
|
}
|
@@ -151,9 +252,6 @@ async function createProjectGraphAndSourceMapsAsync(opts = {
|
|
151
252
|
else {
|
152
253
|
try {
|
153
254
|
const projectGraphAndSourceMaps = await client_1.daemonClient.getProjectGraphAndSourceMaps();
|
154
|
-
if (opts.resetDaemonClient) {
|
155
|
-
client_1.daemonClient.reset();
|
156
|
-
}
|
157
255
|
perf_hooks_1.performance.mark('create-project-graph-async:end');
|
158
256
|
perf_hooks_1.performance.measure('create-project-graph-async', 'create-project-graph-async:start', 'create-project-graph-async:end');
|
159
257
|
return projectGraphAndSourceMaps;
|
@@ -186,6 +284,11 @@ async function createProjectGraphAndSourceMapsAsync(opts = {
|
|
186
284
|
}
|
187
285
|
handleProjectGraphError(opts, e);
|
188
286
|
}
|
287
|
+
finally {
|
288
|
+
if (opts.resetDaemonClient) {
|
289
|
+
client_1.daemonClient.reset();
|
290
|
+
}
|
291
|
+
}
|
189
292
|
}
|
190
293
|
}
|
191
294
|
exports.createProjectGraphAndSourceMapsAsync = createProjectGraphAndSourceMapsAsync;
|
@@ -13,20 +13,43 @@ export declare function mergeProjectConfigurationIntoRootMap(projectRootMap: Map
|
|
13
13
|
export type ConfigurationResult = {
|
14
14
|
projects: Record<string, ProjectConfiguration>;
|
15
15
|
externalNodes: Record<string, ProjectGraphExternalNode>;
|
16
|
-
|
16
|
+
projectRootMap: Record<string, string>;
|
17
17
|
sourceMaps: ConfigurationSourceMaps;
|
18
18
|
};
|
19
19
|
/**
|
20
20
|
* Transforms a list of project paths into a map of project configurations.
|
21
21
|
*
|
22
|
+
* @param root The workspace root
|
22
23
|
* @param nxJson The NxJson configuration
|
23
24
|
* @param workspaceFiles A list of non-ignored workspace files
|
24
25
|
* @param plugins The plugins that should be used to infer project configuration
|
25
|
-
* @param root The workspace root
|
26
26
|
*/
|
27
|
-
export declare function
|
28
|
-
plugins: LoadedNxPlugin[]
|
27
|
+
export declare function createProjectConfigurations(root: string, nxJson: NxJsonConfiguration, workspaceFiles: string[], // making this parameter allows devkit to pick up newly created projects
|
28
|
+
plugins: LoadedNxPlugin[]): Promise<ConfigurationResult>;
|
29
29
|
export declare function readProjectConfigurationsFromRootMap(projectRootMap: Map<string, ProjectConfiguration>): Record<string, ProjectConfiguration>;
|
30
|
+
export declare class ProjectConfigurationsError extends Error {
|
31
|
+
readonly errors: Array<MergeNodesError | CreateNodesError>;
|
32
|
+
readonly partialProjectConfigurationsResult: ConfigurationResult;
|
33
|
+
constructor(errors: Array<MergeNodesError | CreateNodesError>, partialProjectConfigurationsResult: ConfigurationResult);
|
34
|
+
}
|
35
|
+
export declare class CreateNodesError extends Error {
|
36
|
+
file: string;
|
37
|
+
pluginName: string;
|
38
|
+
constructor({ file, pluginName, error, }: {
|
39
|
+
file: string;
|
40
|
+
pluginName: string;
|
41
|
+
error: Error;
|
42
|
+
});
|
43
|
+
}
|
44
|
+
export declare class MergeNodesError extends Error {
|
45
|
+
file: string;
|
46
|
+
pluginName: string;
|
47
|
+
constructor({ file, pluginName, error, }: {
|
48
|
+
file: string;
|
49
|
+
pluginName: string;
|
50
|
+
error: Error;
|
51
|
+
});
|
52
|
+
}
|
30
53
|
/**
|
31
54
|
* Merges two targets.
|
32
55
|
*
|
@@ -1,12 +1,13 @@
|
|
1
1
|
"use strict";
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
3
|
-
exports.readTargetDefaultsForTarget = exports.resolveNxTokensInOptions = exports.isCompatibleTarget = exports.mergeTargetConfigurations = exports.readProjectConfigurationsFromRootMap = exports.
|
3
|
+
exports.readTargetDefaultsForTarget = exports.resolveNxTokensInOptions = exports.isCompatibleTarget = exports.mergeTargetConfigurations = exports.MergeNodesError = exports.CreateNodesError = exports.ProjectConfigurationsError = exports.readProjectConfigurationsFromRootMap = exports.createProjectConfigurations = exports.mergeProjectConfigurationIntoRootMap = void 0;
|
4
4
|
const logger_1 = require("../../utils/logger");
|
5
5
|
const fileutils_1 = require("../../utils/fileutils");
|
6
6
|
const workspace_root_1 = require("../../utils/workspace-root");
|
7
7
|
const target_defaults_plugin_1 = require("../../plugins/target-defaults/target-defaults-plugin");
|
8
8
|
const minimatch_1 = require("minimatch");
|
9
9
|
const path_1 = require("path");
|
10
|
+
const perf_hooks_1 = require("perf_hooks");
|
10
11
|
function mergeProjectConfigurationIntoRootMap(projectRootMap, project, configurationSourceMaps, sourceInformation,
|
11
12
|
// This function is used when reading project configuration
|
12
13
|
// in generators, where we don't want to do this.
|
@@ -32,17 +33,27 @@ skipCommandNormalization) {
|
|
32
33
|
// a project.json in which case it was already updated above.
|
33
34
|
const updatedProjectConfiguration = {
|
34
35
|
...matchingProject,
|
35
|
-
...project,
|
36
36
|
};
|
37
|
-
|
38
|
-
|
39
|
-
|
37
|
+
for (const k in project) {
|
38
|
+
if (![
|
39
|
+
'tags',
|
40
|
+
'implicitDependencies',
|
41
|
+
'generators',
|
42
|
+
'targets',
|
43
|
+
'metadata',
|
44
|
+
'namedInputs',
|
45
|
+
].includes(k)) {
|
46
|
+
updatedProjectConfiguration[k] = project[k];
|
47
|
+
if (sourceMap) {
|
48
|
+
sourceMap[`${k}`] = sourceInformation;
|
49
|
+
}
|
40
50
|
}
|
41
51
|
}
|
42
52
|
// The next blocks handle properties that should be themselves merged (e.g. targets, tags, and implicit dependencies)
|
43
53
|
if (project.tags) {
|
44
54
|
updatedProjectConfiguration.tags = Array.from(new Set((matchingProject.tags ?? []).concat(project.tags)));
|
45
55
|
if (sourceMap) {
|
56
|
+
sourceMap['tags'] ??= sourceInformation;
|
46
57
|
project.tags.forEach((tag) => {
|
47
58
|
sourceMap[`tags.${tag}`] = sourceInformation;
|
48
59
|
});
|
@@ -51,6 +62,7 @@ skipCommandNormalization) {
|
|
51
62
|
if (project.implicitDependencies) {
|
52
63
|
updatedProjectConfiguration.implicitDependencies = (matchingProject.implicitDependencies ?? []).concat(project.implicitDependencies);
|
53
64
|
if (sourceMap) {
|
65
|
+
sourceMap['implicitDependencies'] ??= sourceInformation;
|
54
66
|
project.implicitDependencies.forEach((implicitDependency) => {
|
55
67
|
sourceMap[`implicitDependencies.${implicitDependency}`] =
|
56
68
|
sourceInformation;
|
@@ -61,6 +73,7 @@ skipCommandNormalization) {
|
|
61
73
|
// Start with generators config in new project.
|
62
74
|
updatedProjectConfiguration.generators = { ...project.generators };
|
63
75
|
if (sourceMap) {
|
76
|
+
sourceMap['generators'] ??= sourceInformation;
|
64
77
|
for (const generator in project.generators) {
|
65
78
|
sourceMap[`generators.${generator}`] = sourceInformation;
|
66
79
|
for (const property in project.generators[generator]) {
|
@@ -85,6 +98,7 @@ skipCommandNormalization) {
|
|
85
98
|
...project.namedInputs,
|
86
99
|
};
|
87
100
|
if (sourceMap) {
|
101
|
+
sourceMap['namedInputs'] ??= sourceInformation;
|
88
102
|
for (const namedInput in project.namedInputs) {
|
89
103
|
sourceMap[`namedInputs.${namedInput}`] = sourceInformation;
|
90
104
|
}
|
@@ -94,6 +108,9 @@ skipCommandNormalization) {
|
|
94
108
|
// We merge the targets with special handling, so clear this back to the
|
95
109
|
// targets as defined originally before merging.
|
96
110
|
updatedProjectConfiguration.targets = matchingProject?.targets ?? {};
|
111
|
+
if (sourceMap) {
|
112
|
+
sourceMap['targets'] ??= sourceInformation;
|
113
|
+
}
|
97
114
|
// For each target defined in the new config
|
98
115
|
for (const targetName in project.targets) {
|
99
116
|
// Always set source map info for the target, but don't overwrite info already there
|
@@ -117,31 +134,102 @@ skipCommandNormalization) {
|
|
117
134
|
updatedProjectConfiguration.targets[targetName] = mergedTarget;
|
118
135
|
}
|
119
136
|
}
|
137
|
+
if (project.metadata) {
|
138
|
+
if (sourceMap) {
|
139
|
+
sourceMap['targets'] ??= sourceInformation;
|
140
|
+
}
|
141
|
+
for (const [metadataKey, value] of Object.entries({
|
142
|
+
...project.metadata,
|
143
|
+
})) {
|
144
|
+
const existingValue = matchingProject.metadata?.[metadataKey];
|
145
|
+
if (Array.isArray(value) && Array.isArray(existingValue)) {
|
146
|
+
for (const item of [...value]) {
|
147
|
+
const newLength = updatedProjectConfiguration.metadata[metadataKey].push(item);
|
148
|
+
if (sourceMap) {
|
149
|
+
sourceMap[`metadata.${metadataKey}.${newLength - 1}`] =
|
150
|
+
sourceInformation;
|
151
|
+
}
|
152
|
+
}
|
153
|
+
}
|
154
|
+
else if (Array.isArray(value) && existingValue === undefined) {
|
155
|
+
updatedProjectConfiguration.metadata ??= {};
|
156
|
+
updatedProjectConfiguration.metadata[metadataKey] ??= value;
|
157
|
+
if (sourceMap) {
|
158
|
+
sourceMap[`metadata.${metadataKey}`] = sourceInformation;
|
159
|
+
}
|
160
|
+
for (let i = 0; i < value.length; i++) {
|
161
|
+
if (sourceMap) {
|
162
|
+
sourceMap[`metadata.${metadataKey}.${i}`] = sourceInformation;
|
163
|
+
}
|
164
|
+
}
|
165
|
+
}
|
166
|
+
else if (typeof value === 'object' &&
|
167
|
+
typeof existingValue === 'object') {
|
168
|
+
for (const key in value) {
|
169
|
+
const existingValue = matchingProject.metadata?.[metadataKey]?.[key];
|
170
|
+
if (Array.isArray(value[key]) && Array.isArray(existingValue)) {
|
171
|
+
for (const item of value[key]) {
|
172
|
+
const i = updatedProjectConfiguration.metadata[metadataKey][key].push(item);
|
173
|
+
if (sourceMap) {
|
174
|
+
sourceMap[`metadata.${metadataKey}.${key}.${i - 1}`] =
|
175
|
+
sourceInformation;
|
176
|
+
}
|
177
|
+
}
|
178
|
+
}
|
179
|
+
else {
|
180
|
+
updatedProjectConfiguration.metadata[metadataKey] = value;
|
181
|
+
if (sourceMap) {
|
182
|
+
sourceMap[`metadata.${metadataKey}`] = sourceInformation;
|
183
|
+
}
|
184
|
+
}
|
185
|
+
}
|
186
|
+
}
|
187
|
+
else {
|
188
|
+
updatedProjectConfiguration.metadata[metadataKey] = value;
|
189
|
+
if (sourceMap) {
|
190
|
+
sourceMap[`metadata.${metadataKey}`] = sourceInformation;
|
191
|
+
if (typeof value === 'object') {
|
192
|
+
for (const k in value) {
|
193
|
+
sourceMap[`metadata.${metadataKey}.${k}`] = sourceInformation;
|
194
|
+
if (Array.isArray(value[k])) {
|
195
|
+
for (let i = 0; i < value[k].length; i++) {
|
196
|
+
sourceMap[`metadata.${metadataKey}.${k}.${i}`] =
|
197
|
+
sourceInformation;
|
198
|
+
}
|
199
|
+
}
|
200
|
+
}
|
201
|
+
}
|
202
|
+
}
|
203
|
+
}
|
204
|
+
}
|
205
|
+
}
|
120
206
|
projectRootMap.set(updatedProjectConfiguration.root, updatedProjectConfiguration);
|
121
207
|
}
|
122
208
|
exports.mergeProjectConfigurationIntoRootMap = mergeProjectConfigurationIntoRootMap;
|
123
209
|
/**
|
124
210
|
* Transforms a list of project paths into a map of project configurations.
|
125
211
|
*
|
212
|
+
* @param root The workspace root
|
126
213
|
* @param nxJson The NxJson configuration
|
127
214
|
* @param workspaceFiles A list of non-ignored workspace files
|
128
215
|
* @param plugins The plugins that should be used to infer project configuration
|
129
|
-
* @param root The workspace root
|
130
216
|
*/
|
131
|
-
function
|
132
|
-
plugins
|
217
|
+
function createProjectConfigurations(root = workspace_root_1.workspaceRoot, nxJson, workspaceFiles, // making this parameter allows devkit to pick up newly created projects
|
218
|
+
plugins) {
|
219
|
+
perf_hooks_1.performance.mark('build-project-configs:start');
|
133
220
|
const results = [];
|
221
|
+
const errors = [];
|
134
222
|
// We iterate over plugins first - this ensures that plugins specified first take precedence.
|
135
223
|
for (const { plugin, options } of plugins) {
|
136
224
|
const [pattern, createNodes] = plugin.createNodes ?? [];
|
137
225
|
const pluginResults = [];
|
138
|
-
performance.mark(`${plugin.name}:createNodes - start`);
|
226
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes - start`);
|
139
227
|
if (!pattern) {
|
140
228
|
continue;
|
141
229
|
}
|
142
230
|
const matchingConfigFiles = workspaceFiles.filter(minimatch_1.minimatch.filter(pattern, { dot: true }));
|
143
231
|
for (const file of matchingConfigFiles) {
|
144
|
-
performance.mark(`${plugin.name}:createNodes:${file} - start`);
|
232
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes:${file} - start`);
|
145
233
|
try {
|
146
234
|
let r = createNodes(file, options, {
|
147
235
|
nxJsonConfiguration: nxJson,
|
@@ -150,19 +238,26 @@ plugins, root = workspace_root_1.workspaceRoot) {
|
|
150
238
|
});
|
151
239
|
if (r instanceof Promise) {
|
152
240
|
pluginResults.push(r
|
153
|
-
.catch((
|
154
|
-
performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
155
|
-
|
241
|
+
.catch((error) => {
|
242
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
243
|
+
errors.push(new CreateNodesError({
|
244
|
+
file,
|
245
|
+
pluginName: plugin.name,
|
246
|
+
error,
|
247
|
+
}));
|
248
|
+
return {
|
249
|
+
projects: {},
|
250
|
+
};
|
156
251
|
})
|
157
252
|
.then((r) => {
|
158
|
-
performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
159
|
-
performance.measure(`${plugin.name}:createNodes:${file}`, `${plugin.name}:createNodes:${file} - start`, `${plugin.name}:createNodes:${file} - end`);
|
253
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
254
|
+
perf_hooks_1.performance.measure(`${plugin.name}:createNodes:${file}`, `${plugin.name}:createNodes:${file} - start`, `${plugin.name}:createNodes:${file} - end`);
|
160
255
|
return { ...r, file, pluginName: plugin.name };
|
161
256
|
}));
|
162
257
|
}
|
163
258
|
else {
|
164
|
-
performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
165
|
-
performance.measure(`${plugin.name}:createNodes:${file}`, `${plugin.name}:createNodes:${file} - start`, `${plugin.name}:createNodes:${file} - end`);
|
259
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes:${file} - end`);
|
260
|
+
perf_hooks_1.performance.measure(`${plugin.name}:createNodes:${file}`, `${plugin.name}:createNodes:${file} - start`, `${plugin.name}:createNodes:${file} - end`);
|
166
261
|
pluginResults.push({
|
167
262
|
...r,
|
168
263
|
file,
|
@@ -170,19 +265,22 @@ plugins, root = workspace_root_1.workspaceRoot) {
|
|
170
265
|
});
|
171
266
|
}
|
172
267
|
}
|
173
|
-
catch (
|
174
|
-
|
268
|
+
catch (error) {
|
269
|
+
errors.push(new CreateNodesError({
|
270
|
+
file,
|
271
|
+
pluginName: plugin.name,
|
272
|
+
error,
|
273
|
+
}));
|
175
274
|
}
|
176
275
|
}
|
177
|
-
// If there are no promises (counter undefined) or all promises have resolved (counter === 0)
|
178
276
|
results.push(Promise.all(pluginResults).then((results) => {
|
179
|
-
performance.mark(`${plugin.name}:createNodes - end`);
|
180
|
-
performance.measure(`${plugin.name}:createNodes`, `${plugin.name}:createNodes - start`, `${plugin.name}:createNodes - end`);
|
277
|
+
perf_hooks_1.performance.mark(`${plugin.name}:createNodes - end`);
|
278
|
+
perf_hooks_1.performance.measure(`${plugin.name}:createNodes`, `${plugin.name}:createNodes - start`, `${plugin.name}:createNodes - end`);
|
181
279
|
return results;
|
182
280
|
}));
|
183
281
|
}
|
184
282
|
return Promise.all(results).then((results) => {
|
185
|
-
performance.mark('createNodes:merge - start');
|
283
|
+
perf_hooks_1.performance.mark('createNodes:merge - start');
|
186
284
|
const projectRootMap = new Map();
|
187
285
|
const externalNodes = {};
|
188
286
|
const configurationSourceMaps = {};
|
@@ -200,25 +298,41 @@ plugins, root = workspace_root_1.workspaceRoot) {
|
|
200
298
|
try {
|
201
299
|
mergeProjectConfigurationIntoRootMap(projectRootMap, project, configurationSourceMaps, sourceInfo);
|
202
300
|
}
|
203
|
-
catch (
|
204
|
-
|
301
|
+
catch (error) {
|
302
|
+
errors.push(new MergeNodesError({
|
303
|
+
file,
|
304
|
+
pluginName,
|
305
|
+
error,
|
306
|
+
}));
|
205
307
|
}
|
206
308
|
}
|
207
309
|
Object.assign(externalNodes, pluginExternalNodes);
|
208
310
|
}
|
209
311
|
const projects = readProjectConfigurationsFromRootMap(projectRootMap);
|
210
312
|
const rootMap = createRootMap(projectRootMap);
|
211
|
-
performance.mark('createNodes:merge - end');
|
212
|
-
performance.measure('createNodes:merge', 'createNodes:merge - start', 'createNodes:merge - end');
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
313
|
+
perf_hooks_1.performance.mark('createNodes:merge - end');
|
314
|
+
perf_hooks_1.performance.measure('createNodes:merge', 'createNodes:merge - start', 'createNodes:merge - end');
|
315
|
+
perf_hooks_1.performance.mark('build-project-configs:end');
|
316
|
+
perf_hooks_1.performance.measure('build-project-configs', 'build-project-configs:start', 'build-project-configs:end');
|
317
|
+
if (errors.length === 0) {
|
318
|
+
return {
|
319
|
+
projects,
|
320
|
+
externalNodes,
|
321
|
+
projectRootMap: rootMap,
|
322
|
+
sourceMaps: configurationSourceMaps,
|
323
|
+
};
|
324
|
+
}
|
325
|
+
else {
|
326
|
+
throw new ProjectConfigurationsError(errors, {
|
327
|
+
projects,
|
328
|
+
externalNodes,
|
329
|
+
projectRootMap: rootMap,
|
330
|
+
sourceMaps: configurationSourceMaps,
|
331
|
+
});
|
332
|
+
}
|
219
333
|
});
|
220
334
|
}
|
221
|
-
exports.
|
335
|
+
exports.createProjectConfigurations = createProjectConfigurations;
|
222
336
|
function readProjectConfigurationsFromRootMap(projectRootMap) {
|
223
337
|
const projects = {};
|
224
338
|
// If there are projects that have the same name, that is an error.
|
@@ -261,20 +375,37 @@ function readProjectConfigurationsFromRootMap(projectRootMap) {
|
|
261
375
|
return projects;
|
262
376
|
}
|
263
377
|
exports.readProjectConfigurationsFromRootMap = readProjectConfigurationsFromRootMap;
|
378
|
+
class ProjectConfigurationsError extends Error {
|
379
|
+
constructor(errors, partialProjectConfigurationsResult) {
|
380
|
+
super('Failed to create project configurations');
|
381
|
+
this.errors = errors;
|
382
|
+
this.partialProjectConfigurationsResult = partialProjectConfigurationsResult;
|
383
|
+
this.name = this.constructor.name;
|
384
|
+
}
|
385
|
+
}
|
386
|
+
exports.ProjectConfigurationsError = ProjectConfigurationsError;
|
264
387
|
class CreateNodesError extends Error {
|
265
|
-
constructor(
|
266
|
-
const
|
267
|
-
|
268
|
-
|
269
|
-
|
270
|
-
|
271
|
-
|
272
|
-
|
273
|
-
|
274
|
-
|
275
|
-
|
388
|
+
constructor({ file, pluginName, error, }) {
|
389
|
+
const msg = `The "${pluginName}" plugin threw an error while creating nodes from ${file}:`;
|
390
|
+
super(msg, { cause: error });
|
391
|
+
this.name = this.constructor.name;
|
392
|
+
this.file = file;
|
393
|
+
this.pluginName = pluginName;
|
394
|
+
this.stack = `${this.message}\n ${error.stack.split('\n').join('\n ')}`;
|
395
|
+
}
|
396
|
+
}
|
397
|
+
exports.CreateNodesError = CreateNodesError;
|
398
|
+
class MergeNodesError extends Error {
|
399
|
+
constructor({ file, pluginName, error, }) {
|
400
|
+
const msg = `The nodes created from ${file} by the "${pluginName}" could not be merged into the project graph:`;
|
401
|
+
super(msg, { cause: error });
|
402
|
+
this.name = this.constructor.name;
|
403
|
+
this.file = file;
|
404
|
+
this.pluginName = pluginName;
|
405
|
+
this.stack = `${this.message}\n ${error.stack.split('\n').join('\n ')}`;
|
276
406
|
}
|
277
407
|
}
|
408
|
+
exports.MergeNodesError = MergeNodesError;
|
278
409
|
/**
|
279
410
|
* Merges two targets.
|
280
411
|
*
|
@@ -1,7 +1,6 @@
|
|
1
1
|
import { ProjectConfiguration } from '../../config/workspace-json-project-json';
|
2
2
|
import { NxJsonConfiguration } from '../../config/nx-json';
|
3
|
-
import {
|
4
|
-
import { ConfigurationSourceMaps } from './project-configuration-utils';
|
3
|
+
import { ConfigurationResult } from './project-configuration-utils';
|
5
4
|
import { LoadedNxPlugin } from '../../utils/nx-plugin';
|
6
5
|
/**
|
7
6
|
* Walks the workspace directory to create the `projectFileMap`, `ProjectConfigurations` and `allWorkspaceFiles`
|
@@ -10,12 +9,12 @@ import { LoadedNxPlugin } from '../../utils/nx-plugin';
|
|
10
9
|
* @param nxJson
|
11
10
|
*/
|
12
11
|
export declare function retrieveWorkspaceFiles(workspaceRoot: string, projectRootMap: Record<string, string>): Promise<{
|
13
|
-
allWorkspaceFiles: import("
|
12
|
+
allWorkspaceFiles: import("nx/src/devkit-exports").FileData[];
|
14
13
|
fileMap: {
|
15
14
|
projectFileMap: ProjectFiles;
|
16
|
-
nonProjectFiles: import("
|
15
|
+
nonProjectFiles: import("nx/src/native").FileData[];
|
17
16
|
};
|
18
|
-
rustReferences: import("
|
17
|
+
rustReferences: import("nx/src/native").NxWorkspaceFilesExternals;
|
19
18
|
}>;
|
20
19
|
/**
|
21
20
|
* Walk through the workspace and return `ProjectConfigurations`. Only use this if the projectFileMap is not needed.
|
@@ -23,15 +22,8 @@ export declare function retrieveWorkspaceFiles(workspaceRoot: string, projectRoo
|
|
23
22
|
* @param workspaceRoot
|
24
23
|
* @param nxJson
|
25
24
|
*/
|
26
|
-
export declare function retrieveProjectConfigurations(workspaceRoot: string, nxJson: NxJsonConfiguration): Promise<
|
27
|
-
export declare function retrieveProjectConfigurationsWithAngularProjects(workspaceRoot: string, nxJson: NxJsonConfiguration): Promise<
|
28
|
-
export type RetrievedGraphNodes = {
|
29
|
-
externalNodes: Record<string, ProjectGraphExternalNode>;
|
30
|
-
projects: Record<string, ProjectConfiguration>;
|
31
|
-
sourceMaps: ConfigurationSourceMaps;
|
32
|
-
projectRootMap: Record<string, string>;
|
33
|
-
};
|
25
|
+
export declare function retrieveProjectConfigurations(workspaceRoot: string, nxJson: NxJsonConfiguration): Promise<ConfigurationResult>;
|
26
|
+
export declare function retrieveProjectConfigurationsWithAngularProjects(workspaceRoot: string, nxJson: NxJsonConfiguration): Promise<ConfigurationResult>;
|
34
27
|
export declare function retrieveProjectConfigurationPaths(root: string, plugins: LoadedNxPlugin[]): string[];
|
35
28
|
export declare function retrieveProjectConfigurationsWithoutPluginInference(root: string): Promise<Record<string, ProjectConfiguration>>;
|
36
|
-
export declare function createProjectConfigurations(workspaceRoot: string, nxJson: NxJsonConfiguration, configFiles: string[], plugins: LoadedNxPlugin[]): Promise<RetrievedGraphNodes>;
|
37
29
|
export declare function configurationGlobs(plugins: LoadedNxPlugin[]): string[];
|