nx 19.7.3 → 19.7.5
Sign up to get free protection for your applications and to get access to all the features.
- package/bin/post-install.js +2 -2
- package/package.json +12 -12
- package/schemas/nx-schema.json +2 -2
- package/src/command-line/import/import.js +3 -2
- package/src/command-line/import/utils/prepare-source-repo.js +7 -35
- package/src/command-line/init/init-v2.js +6 -2
- package/src/command-line/release/command-object.d.ts +2 -2
- package/src/command-line/release/config/config.js +10 -3
- package/src/command-line/release/utils/git.d.ts +2 -2
- package/src/command-line/release/utils/git.js +12 -2
- package/src/command-line/release/utils/shared.d.ts +1 -1
- package/src/command-line/release/version.js +4 -0
- package/src/config/nx-json.d.ts +13 -5
- package/src/hasher/hash-task.js +2 -2
- package/src/native/nx.wasi-browser.js +42 -54
- package/src/native/nx.wasi.cjs +42 -54
- package/src/native/nx.wasm32-wasi.wasm +0 -0
- package/src/plugins/js/utils/register.js +7 -0
- package/src/tasks-runner/cache.js +2 -1
- package/src/tasks-runner/run-command.js +3 -1
- package/src/tasks-runner/task-orchestrator.d.ts +0 -1
- package/src/tasks-runner/task-orchestrator.js +3 -6
- package/src/utils/git-utils.d.ts +3 -2
- package/src/utils/git-utils.index-filter.d.ts +0 -0
- package/src/utils/git-utils.index-filter.js +20 -0
- package/src/utils/git-utils.js +44 -13
- package/src/utils/git-utils.tree-filter.d.ts +11 -0
- package/src/utils/git-utils.tree-filter.js +43 -0
package/bin/post-install.js
CHANGED
@@ -10,14 +10,14 @@ const update_manager_1 = require("../src/nx-cloud/update-manager");
|
|
10
10
|
const get_cloud_options_1 = require("../src/nx-cloud/utilities/get-cloud-options");
|
11
11
|
const nx_cloud_utils_1 = require("../src/utils/nx-cloud-utils");
|
12
12
|
const nx_json_1 = require("../src/config/nx-json");
|
13
|
-
const workspace_context_1 = require("../src/utils/workspace-context");
|
14
13
|
const logger_1 = require("../src/utils/logger");
|
14
|
+
const workspace_context_1 = require("../src/utils/workspace-context");
|
15
15
|
(async () => {
|
16
16
|
const start = new Date();
|
17
17
|
try {
|
18
|
-
(0, workspace_context_1.setupWorkspaceContext)(workspace_root_1.workspaceRoot);
|
19
18
|
if (isMainNxPackage() && (0, fileutils_1.fileExists)((0, path_1.join)(workspace_root_1.workspaceRoot, 'nx.json'))) {
|
20
19
|
(0, assert_supported_platform_1.assertSupportedPlatform)();
|
20
|
+
(0, workspace_context_1.setupWorkspaceContext)(workspace_root_1.workspaceRoot);
|
21
21
|
try {
|
22
22
|
await client_1.daemonClient.stop();
|
23
23
|
}
|
package/package.json
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
{
|
2
2
|
"name": "nx",
|
3
|
-
"version": "19.7.
|
3
|
+
"version": "19.7.5",
|
4
4
|
"private": false,
|
5
5
|
"description": "The core Nx plugin contains the core functionality of Nx like the project graph, nx commands and task orchestration.",
|
6
6
|
"repository": {
|
@@ -71,7 +71,7 @@
|
|
71
71
|
"yargs-parser": "21.1.1",
|
72
72
|
"node-machine-id": "1.1.12",
|
73
73
|
"ora": "5.3.0",
|
74
|
-
"@nrwl/tao": "19.7.
|
74
|
+
"@nrwl/tao": "19.7.5"
|
75
75
|
},
|
76
76
|
"peerDependencies": {
|
77
77
|
"@swc-node/register": "^1.8.0",
|
@@ -86,16 +86,16 @@
|
|
86
86
|
}
|
87
87
|
},
|
88
88
|
"optionalDependencies": {
|
89
|
-
"@nx/nx-darwin-x64": "19.7.
|
90
|
-
"@nx/nx-darwin-arm64": "19.7.
|
91
|
-
"@nx/nx-linux-x64-gnu": "19.7.
|
92
|
-
"@nx/nx-linux-x64-musl": "19.7.
|
93
|
-
"@nx/nx-win32-x64-msvc": "19.7.
|
94
|
-
"@nx/nx-linux-arm64-gnu": "19.7.
|
95
|
-
"@nx/nx-linux-arm64-musl": "19.7.
|
96
|
-
"@nx/nx-linux-arm-gnueabihf": "19.7.
|
97
|
-
"@nx/nx-win32-arm64-msvc": "19.7.
|
98
|
-
"@nx/nx-freebsd-x64": "19.7.
|
89
|
+
"@nx/nx-darwin-x64": "19.7.5",
|
90
|
+
"@nx/nx-darwin-arm64": "19.7.5",
|
91
|
+
"@nx/nx-linux-x64-gnu": "19.7.5",
|
92
|
+
"@nx/nx-linux-x64-musl": "19.7.5",
|
93
|
+
"@nx/nx-win32-x64-msvc": "19.7.5",
|
94
|
+
"@nx/nx-linux-arm64-gnu": "19.7.5",
|
95
|
+
"@nx/nx-linux-arm64-musl": "19.7.5",
|
96
|
+
"@nx/nx-linux-arm-gnueabihf": "19.7.5",
|
97
|
+
"@nx/nx-win32-arm64-msvc": "19.7.5",
|
98
|
+
"@nx/nx-freebsd-x64": "19.7.5"
|
99
99
|
},
|
100
100
|
"nx-migrations": {
|
101
101
|
"migrations": "./migrations.json",
|
package/schemas/nx-schema.json
CHANGED
@@ -634,7 +634,7 @@
|
|
634
634
|
"description": "Custom git commit message to use when committing the changes made by this command"
|
635
635
|
},
|
636
636
|
"commitArgs": {
|
637
|
-
"type": "string",
|
637
|
+
"type": ["string", "array"],
|
638
638
|
"description": "Additional arguments (added after the --message argument, which may or may not be customized with --git-commit-message) to pass to the `git commit` command invoked behind the scenes"
|
639
639
|
},
|
640
640
|
"stageChanges": {
|
@@ -650,7 +650,7 @@
|
|
650
650
|
"description": "Custom git tag message to use when tagging the changes made by this command. This defaults to be the same value as the tag itself."
|
651
651
|
},
|
652
652
|
"tagArgs": {
|
653
|
-
"type": "string",
|
653
|
+
"type": ["string", "array"],
|
654
654
|
"description": "Additional arguments to pass to the `git tag` command invoked behind the scenes"
|
655
655
|
}
|
656
656
|
}
|
@@ -232,8 +232,9 @@ async function importHandler(options) {
|
|
232
232
|
title: `Merging these changes into ${(0, command_line_utils_1.getBaseRef)(nxJson)}`,
|
233
233
|
bodyLines: [
|
234
234
|
`MERGE these changes when merging these changes.`,
|
235
|
-
`Do NOT squash
|
236
|
-
`If you
|
235
|
+
`Do NOT squash these commits when merging these changes.`,
|
236
|
+
`If you rebase, make sure to use "--rebase-merges" to preserve merge commits.`,
|
237
|
+
`To UNDO these changes, run "git reset HEAD~1 --hard"`,
|
237
238
|
],
|
238
239
|
});
|
239
240
|
}
|
@@ -3,46 +3,18 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.prepareSourceRepo = prepareSourceRepo;
|
4
4
|
const createSpinner = require("ora");
|
5
5
|
const path_1 = require("path");
|
6
|
-
const promises_1 = require("node:fs/promises");
|
7
6
|
async function prepareSourceRepo(gitClient, ref, source, relativeDestination, tempImportBranch, sourceRemoteUrl) {
|
8
7
|
const spinner = createSpinner().start(`Fetching ${ref} from ${sourceRemoteUrl}`);
|
9
8
|
const relativeSourceDir = (0, path_1.relative)(gitClient.root, (0, path_1.join)(gitClient.root, source));
|
10
|
-
if (
|
11
|
-
|
12
|
-
|
13
|
-
await gitClient.filterRepo(relativeSourceDir);
|
14
|
-
}
|
15
|
-
else {
|
16
|
-
spinner.start(`Filtering git history to only include files in ${relativeSourceDir} (this might take a few minutes -- install git-filter-repo for faster performance)`);
|
17
|
-
await gitClient.filterBranch(relativeSourceDir, tempImportBranch);
|
18
|
-
}
|
19
|
-
spinner.succeed(`Filtered git history to only include files in ${relativeSourceDir}`);
|
9
|
+
if (await gitClient.hasFilterRepoInstalled()) {
|
10
|
+
spinner.start(`Filtering git history to only include files in ${relativeSourceDir}`);
|
11
|
+
await gitClient.filterRepo(relativeSourceDir, relativeDestination);
|
20
12
|
}
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
const files = await gitClient.getGitFiles('.');
|
25
|
-
try {
|
26
|
-
await (0, promises_1.rm)(destinationInSource, {
|
27
|
-
recursive: true,
|
28
|
-
});
|
13
|
+
else {
|
14
|
+
spinner.start(`Filtering git history to only include files in ${relativeSourceDir} (this might take a few minutes -- install git-filter-repo for faster performance)`);
|
15
|
+
await gitClient.filterBranch(relativeSourceDir, relativeDestination, tempImportBranch);
|
29
16
|
}
|
30
|
-
|
31
|
-
await (0, promises_1.mkdir)(destinationInSource, { recursive: true });
|
32
|
-
for (const file of files) {
|
33
|
-
spinner.start(`Moving files and git history to ${destinationInSource}: ${file}`);
|
34
|
-
const newPath = (0, path_1.join)(destinationInSource, file);
|
35
|
-
await (0, promises_1.mkdir)((0, path_1.dirname)(newPath), { recursive: true });
|
36
|
-
try {
|
37
|
-
await gitClient.move(file, newPath);
|
38
|
-
}
|
39
|
-
catch {
|
40
|
-
await wait(100);
|
41
|
-
await gitClient.move(file, newPath);
|
42
|
-
}
|
43
|
-
}
|
44
|
-
await gitClient.commit(`chore(repo): move ${source} to ${relativeDestination} to prepare to be imported`);
|
45
|
-
await gitClient.amendCommit();
|
17
|
+
spinner.succeed(`Filtered git history to only include files in ${relativeSourceDir}`);
|
46
18
|
spinner.succeed(`${sourceRemoteUrl} has been prepared to be imported into this workspace on a temporary branch: ${tempImportBranch} in ${gitClient.root}`);
|
47
19
|
}
|
48
20
|
function wait(ms) {
|
@@ -128,7 +128,7 @@ const npmPackageToPluginMap = {
|
|
128
128
|
'@remix-run/dev': '@nx/remix',
|
129
129
|
};
|
130
130
|
async function detectPlugins(nxJson, interactive) {
|
131
|
-
let files = ['package.json'].concat(
|
131
|
+
let files = ['package.json'].concat((0, workspace_context_1.globWithWorkspaceContextSync)(process.cwd(), ['**/*/package.json']));
|
132
132
|
const currentPlugins = new Set((nxJson.plugins ?? []).map((p) => {
|
133
133
|
const plugin = typeof p === 'string' ? p : p.plugin;
|
134
134
|
return (0, get_package_name_from_import_path_1.getPackageNameFromImportPath)(plugin);
|
@@ -155,7 +155,11 @@ async function detectPlugins(nxJson, interactive) {
|
|
155
155
|
}
|
156
156
|
}
|
157
157
|
}
|
158
|
-
|
158
|
+
let gradlewFiles = ['gradlew', 'gradlew.bat'].concat((0, workspace_context_1.globWithWorkspaceContextSync)(process.cwd(), [
|
159
|
+
'**/gradlew',
|
160
|
+
'**/gradlew.bat',
|
161
|
+
]));
|
162
|
+
if (gradlewFiles.some((f) => (0, fs_1.existsSync)(f))) {
|
159
163
|
detectedPlugins.add('@nx/gradle');
|
160
164
|
}
|
161
165
|
// Remove existing plugins
|
@@ -14,10 +14,10 @@ interface GitCommitAndTagOptions {
|
|
14
14
|
stageChanges?: boolean;
|
15
15
|
gitCommit?: boolean;
|
16
16
|
gitCommitMessage?: string;
|
17
|
-
gitCommitArgs?: string;
|
17
|
+
gitCommitArgs?: string | string[];
|
18
18
|
gitTag?: boolean;
|
19
19
|
gitTagMessage?: string;
|
20
|
-
gitTagArgs?: string;
|
20
|
+
gitTagArgs?: string | string[];
|
21
21
|
}
|
22
22
|
export type VersionOptions = NxReleaseArgs & GitCommitAndTagOptions & VersionPlanArgs & FirstReleaseArgs & {
|
23
23
|
specifier?: string;
|
@@ -21,6 +21,7 @@ const fileutils_1 = require("../../../utils/fileutils");
|
|
21
21
|
const find_matching_projects_1 = require("../../../utils/find-matching-projects");
|
22
22
|
const output_1 = require("../../../utils/output");
|
23
23
|
const workspace_root_1 = require("../../../utils/workspace-root");
|
24
|
+
const path_1 = require("../../../utils/path");
|
24
25
|
const resolve_changelog_renderer_1 = require("../utils/resolve-changelog-renderer");
|
25
26
|
const resolve_nx_json_error_message_1 = require("../utils/resolve-nx-json-error-message");
|
26
27
|
const conventional_commits_1 = require("./conventional-commits");
|
@@ -154,6 +155,7 @@ async function createNxReleaseConfig(projectGraph, projectFileMap, userConfig =
|
|
154
155
|
conventionalCommits: false,
|
155
156
|
generator: '@nx/js:release-version',
|
156
157
|
generatorOptions: {},
|
158
|
+
groupPreVersionCommand: '',
|
157
159
|
},
|
158
160
|
changelog: {
|
159
161
|
createRelease: false,
|
@@ -205,7 +207,9 @@ async function createNxReleaseConfig(projectGraph, projectFileMap, userConfig =
|
|
205
207
|
WORKSPACE_DEFAULTS.versionPlans);
|
206
208
|
const rootConventionalCommitsConfig = deepMergeDefaults([WORKSPACE_DEFAULTS.conventionalCommits], fillUnspecifiedConventionalCommitsProperties(normalizeConventionalCommitsConfig(userConfig.conventionalCommits)));
|
207
209
|
// these options are not supported at the group level, only the root/command level
|
208
|
-
const rootVersionWithoutGlobalOptions = {
|
210
|
+
const rootVersionWithoutGlobalOptions = {
|
211
|
+
...rootVersionConfig,
|
212
|
+
};
|
209
213
|
delete rootVersionWithoutGlobalOptions.git;
|
210
214
|
delete rootVersionWithoutGlobalOptions.preVersionCommand;
|
211
215
|
// Apply conventionalCommits shorthand to the final group defaults if explicitly configured in the original user config
|
@@ -315,7 +319,10 @@ async function createNxReleaseConfig(projectGraph, projectFileMap, userConfig =
|
|
315
319
|
projects: matchingProjects,
|
316
320
|
version: deepMergeDefaults(
|
317
321
|
// First apply any group level defaults, then apply actual root level config, then group level config
|
318
|
-
[
|
322
|
+
[
|
323
|
+
GROUP_DEFAULTS.version,
|
324
|
+
{ ...rootVersionWithoutGlobalOptions, groupPreVersionCommand: '' },
|
325
|
+
], releaseGroup.version),
|
319
326
|
// If the user has set any changelog config at all, including at the root level, then use one set of defaults, otherwise default to false for the whole feature
|
320
327
|
changelog: releaseGroup.changelog || rootChangelogConfig.projectChangelogs
|
321
328
|
? deepMergeDefaults(groupChangelogDefaults, releaseGroup.changelog || {})
|
@@ -657,7 +664,7 @@ async function getDefaultProjects(projectGraph, projectFileMap) {
|
|
657
664
|
function isProjectPublic(project, projectGraph, projectFileMap) {
|
658
665
|
const projectNode = projectGraph.nodes[project];
|
659
666
|
const packageJsonPath = (0, node_path_1.join)(projectNode.data.root, 'package.json');
|
660
|
-
if (!projectFileMap[project]?.find((f) => f.file === packageJsonPath)) {
|
667
|
+
if (!projectFileMap[project]?.find((f) => f.file === (0, path_1.normalizePath)(packageJsonPath))) {
|
661
668
|
return false;
|
662
669
|
}
|
663
670
|
try {
|
@@ -37,7 +37,7 @@ export declare function gitAdd({ changedFiles, deletedFiles, dryRun, verbose, lo
|
|
37
37
|
}): Promise<string>;
|
38
38
|
export declare function gitCommit({ messages, additionalArgs, dryRun, verbose, logFn, }: {
|
39
39
|
messages: string[];
|
40
|
-
additionalArgs?: string;
|
40
|
+
additionalArgs?: string | string[];
|
41
41
|
dryRun?: boolean;
|
42
42
|
verbose?: boolean;
|
43
43
|
logFn?: (message: string) => void;
|
@@ -45,7 +45,7 @@ export declare function gitCommit({ messages, additionalArgs, dryRun, verbose, l
|
|
45
45
|
export declare function gitTag({ tag, message, additionalArgs, dryRun, verbose, logFn, }: {
|
46
46
|
tag: string;
|
47
47
|
message?: string;
|
48
|
-
additionalArgs?: string;
|
48
|
+
additionalArgs?: string | string[];
|
49
49
|
dryRun?: boolean;
|
50
50
|
verbose?: boolean;
|
51
51
|
logFn?: (message: string) => void;
|
@@ -188,7 +188,12 @@ async function gitCommit({ messages, additionalArgs, dryRun, verbose, logFn, })
|
|
188
188
|
commandArgs.push('--message', message);
|
189
189
|
}
|
190
190
|
if (additionalArgs) {
|
191
|
-
|
191
|
+
if (Array.isArray(additionalArgs)) {
|
192
|
+
commandArgs.push(...additionalArgs);
|
193
|
+
}
|
194
|
+
else {
|
195
|
+
commandArgs.push(...additionalArgs.split(' '));
|
196
|
+
}
|
192
197
|
}
|
193
198
|
if (verbose) {
|
194
199
|
logFn(dryRun
|
@@ -224,7 +229,12 @@ async function gitTag({ tag, message, additionalArgs, dryRun, verbose, logFn, })
|
|
224
229
|
message || tag,
|
225
230
|
];
|
226
231
|
if (additionalArgs) {
|
227
|
-
|
232
|
+
if (Array.isArray(additionalArgs)) {
|
233
|
+
commandArgs.push(...additionalArgs);
|
234
|
+
}
|
235
|
+
else {
|
236
|
+
commandArgs.push(...additionalArgs.split(' '));
|
237
|
+
}
|
228
238
|
}
|
229
239
|
if (verbose) {
|
230
240
|
logFn(dryRun
|
@@ -45,7 +45,7 @@ export declare function commitChanges({ changedFiles, deletedFiles, isDryRun, is
|
|
45
45
|
isDryRun?: boolean;
|
46
46
|
isVerbose?: boolean;
|
47
47
|
gitCommitMessages?: string[];
|
48
|
-
gitCommitArgs?: string;
|
48
|
+
gitCommitArgs?: string | string[];
|
49
49
|
}): Promise<void>;
|
50
50
|
export declare function createCommitMessageValues(releaseGroups: ReleaseGroupWithName[], releaseGroupToFilteredProjects: Map<ReleaseGroupWithName, Set<string>>, versionData: VersionData, commitMessage: string): string[];
|
51
51
|
export declare function createGitTagValues(releaseGroups: ReleaseGroupWithName[], releaseGroupToFilteredProjects: Map<ReleaseGroupWithName, Set<string>>, versionData: VersionData): string[];
|
@@ -207,6 +207,10 @@ function createAPI(overrideReleaseConfig) {
|
|
207
207
|
*/
|
208
208
|
for (const releaseGroup of releaseGroups) {
|
209
209
|
const releaseGroupName = releaseGroup.name;
|
210
|
+
runPreVersionCommand(releaseGroup.version.groupPreVersionCommand, {
|
211
|
+
dryRun: args.dryRun,
|
212
|
+
verbose: args.verbose,
|
213
|
+
});
|
210
214
|
const projectBatches = (0, batch_projects_by_generator_config_1.batchProjectsByGeneratorConfig)(projectGraph, releaseGroup,
|
211
215
|
// Batch based on all projects within the release group
|
212
216
|
releaseGroup.projects);
|
package/src/config/nx-json.d.ts
CHANGED
@@ -101,9 +101,9 @@ export interface NxReleaseGitConfiguration {
|
|
101
101
|
*/
|
102
102
|
commitMessage?: string;
|
103
103
|
/**
|
104
|
-
* Additional arguments (added after the --message argument, which may or may not be customized with --git-commit-message) to pass to the `git commit` command invoked behind the scenes
|
104
|
+
* Additional arguments (added after the --message argument, which may or may not be customized with --git-commit-message) to pass to the `git commit` command invoked behind the scenes. May be a string or array of strings.
|
105
105
|
*/
|
106
|
-
commitArgs?: string;
|
106
|
+
commitArgs?: string | string[];
|
107
107
|
/**
|
108
108
|
* Whether or not to stage the changes made by this command. Always treated as true if commit is true.
|
109
109
|
*/
|
@@ -117,9 +117,9 @@ export interface NxReleaseGitConfiguration {
|
|
117
117
|
*/
|
118
118
|
tagMessage?: string;
|
119
119
|
/**
|
120
|
-
* Additional arguments to pass to the `git tag` command invoked behind the scenes
|
120
|
+
* Additional arguments to pass to the `git tag` command invoked behind the scenes. . May be a string or array of strings.
|
121
121
|
*/
|
122
|
-
tagArgs?: string;
|
122
|
+
tagArgs?: string | string[];
|
123
123
|
}
|
124
124
|
export interface NxReleaseConventionalCommitsConfiguration {
|
125
125
|
types?: Record<string,
|
@@ -179,7 +179,15 @@ export interface NxReleaseConfiguration {
|
|
179
179
|
*
|
180
180
|
* NOTE: git configuration is not supported at the group level, only the root/command level
|
181
181
|
*/
|
182
|
-
version?: NxReleaseVersionConfiguration
|
182
|
+
version?: NxReleaseVersionConfiguration & {
|
183
|
+
/**
|
184
|
+
* A command to run after validation of nx release configuration, but before versioning begins.
|
185
|
+
* Used for preparing build artifacts. If --dry-run is passed, the command is still executed, but
|
186
|
+
* with the NX_DRY_RUN environment variable set to 'true'.
|
187
|
+
* It will run in addition to the global `preVersionCommand`
|
188
|
+
*/
|
189
|
+
groupPreVersionCommand?: string;
|
190
|
+
};
|
183
191
|
/**
|
184
192
|
* Project changelogs are disabled by default.
|
185
193
|
*
|
package/src/hasher/hash-task.js
CHANGED
@@ -11,7 +11,7 @@ const db_connection_1 = require("../utils/db-connection");
|
|
11
11
|
let taskDetails;
|
12
12
|
function getTaskDetails() {
|
13
13
|
// TODO: Remove when wasm supports sqlite
|
14
|
-
if (native_1.IS_WASM) {
|
14
|
+
if (process.env.NX_DISABLE_DB === 'true' || native_1.IS_WASM) {
|
15
15
|
return null;
|
16
16
|
}
|
17
17
|
if (!taskDetails) {
|
@@ -42,7 +42,7 @@ async function hashTasksThatDoNotDependOnOutputsOfOtherTasks(hasher, projectGrap
|
|
42
42
|
tasksToHash[i].hash = hashes[i].value;
|
43
43
|
tasksToHash[i].hashDetails = hashes[i].details;
|
44
44
|
}
|
45
|
-
// TODO: Remove if when
|
45
|
+
// TODO: Remove if when sqlite is always on
|
46
46
|
if (taskDetails) {
|
47
47
|
taskDetails.recordTaskDetails(tasksToHash.map((task) => ({
|
48
48
|
hash: task.hash,
|
@@ -51,63 +51,51 @@ const {
|
|
51
51
|
})
|
52
52
|
|
53
53
|
function __napi_rs_initialize_modules(__napiInstance) {
|
54
|
-
__napiInstance.exports['
|
55
|
-
__napiInstance.exports['
|
56
|
-
__napiInstance.exports['
|
57
|
-
__napiInstance.exports['
|
58
|
-
__napiInstance.exports['
|
59
|
-
__napiInstance.exports['
|
60
|
-
__napiInstance.exports['
|
61
|
-
__napiInstance.exports['
|
62
|
-
__napiInstance.exports['
|
63
|
-
__napiInstance.exports['
|
64
|
-
__napiInstance.exports['
|
65
|
-
__napiInstance.exports['
|
66
|
-
__napiInstance.exports['
|
67
|
-
__napiInstance.exports['
|
68
|
-
__napiInstance.exports['
|
69
|
-
__napiInstance.exports['
|
70
|
-
__napiInstance.exports['
|
71
|
-
__napiInstance.exports['
|
72
|
-
__napiInstance.exports['
|
73
|
-
__napiInstance.exports['
|
74
|
-
__napiInstance.exports['
|
75
|
-
__napiInstance.exports['
|
76
|
-
__napiInstance.exports['
|
77
|
-
__napiInstance.exports['
|
78
|
-
__napiInstance.exports['
|
79
|
-
__napiInstance.exports['
|
80
|
-
__napiInstance.exports['
|
81
|
-
__napiInstance.exports['
|
82
|
-
__napiInstance.exports['
|
83
|
-
__napiInstance.exports['
|
84
|
-
__napiInstance.exports['
|
85
|
-
__napiInstance.exports['
|
86
|
-
__napiInstance.exports['
|
87
|
-
__napiInstance.exports['
|
88
|
-
__napiInstance.exports['
|
89
|
-
__napiInstance.exports['
|
90
|
-
__napiInstance.exports['
|
91
|
-
__napiInstance.exports['
|
92
|
-
__napiInstance.exports['
|
93
|
-
__napiInstance.exports['
|
94
|
-
__napiInstance.exports['
|
95
|
-
__napiInstance.exports['
|
96
|
-
__napiInstance.exports['__napi_register__NxJson_struct_59']?.()
|
97
|
-
__napiInstance.exports['__napi_register__WorkspaceContext_struct_60']?.()
|
98
|
-
__napiInstance.exports['__napi_register__WorkspaceContext_impl_69']?.()
|
99
|
-
__napiInstance.exports['__napi_register__WorkspaceErrors_70']?.()
|
100
|
-
__napiInstance.exports['__napi_register__NxWorkspaceFiles_struct_71']?.()
|
101
|
-
__napiInstance.exports['__napi_register__NxWorkspaceFilesExternals_struct_72']?.()
|
102
|
-
__napiInstance.exports['__napi_register__UpdatedWorkspaceFiles_struct_73']?.()
|
103
|
-
__napiInstance.exports['__napi_register__FileMap_struct_74']?.()
|
104
|
-
__napiInstance.exports['__napi_register____test_only_transfer_file_map_75']?.()
|
54
|
+
__napiInstance.exports['__napi_register__expand_outputs_0']?.()
|
55
|
+
__napiInstance.exports['__napi_register__get_files_for_outputs_1']?.()
|
56
|
+
__napiInstance.exports['__napi_register__remove_2']?.()
|
57
|
+
__napiInstance.exports['__napi_register__copy_3']?.()
|
58
|
+
__napiInstance.exports['__napi_register__validate_outputs_4']?.()
|
59
|
+
__napiInstance.exports['__napi_register__get_transformable_outputs_5']?.()
|
60
|
+
__napiInstance.exports['__napi_register__hash_array_6']?.()
|
61
|
+
__napiInstance.exports['__napi_register__hash_file_7']?.()
|
62
|
+
__napiInstance.exports['__napi_register__IS_WASM_8']?.()
|
63
|
+
__napiInstance.exports['__napi_register__get_binary_target_9']?.()
|
64
|
+
__napiInstance.exports['__napi_register__ImportResult_struct_10']?.()
|
65
|
+
__napiInstance.exports['__napi_register__find_imports_11']?.()
|
66
|
+
__napiInstance.exports['__napi_register__transfer_project_graph_12']?.()
|
67
|
+
__napiInstance.exports['__napi_register__ExternalNode_struct_13']?.()
|
68
|
+
__napiInstance.exports['__napi_register__Target_struct_14']?.()
|
69
|
+
__napiInstance.exports['__napi_register__Project_struct_15']?.()
|
70
|
+
__napiInstance.exports['__napi_register__ProjectGraph_struct_16']?.()
|
71
|
+
__napiInstance.exports['__napi_register__HashPlanner_struct_17']?.()
|
72
|
+
__napiInstance.exports['__napi_register__HashPlanner_impl_21']?.()
|
73
|
+
__napiInstance.exports['__napi_register__HashDetails_struct_22']?.()
|
74
|
+
__napiInstance.exports['__napi_register__HasherOptions_struct_23']?.()
|
75
|
+
__napiInstance.exports['__napi_register__TaskHasher_struct_24']?.()
|
76
|
+
__napiInstance.exports['__napi_register__TaskHasher_impl_27']?.()
|
77
|
+
__napiInstance.exports['__napi_register__Task_struct_28']?.()
|
78
|
+
__napiInstance.exports['__napi_register__TaskTarget_struct_29']?.()
|
79
|
+
__napiInstance.exports['__napi_register__TaskGraph_struct_30']?.()
|
80
|
+
__napiInstance.exports['__napi_register__FileData_struct_31']?.()
|
81
|
+
__napiInstance.exports['__napi_register__InputsInput_struct_32']?.()
|
82
|
+
__napiInstance.exports['__napi_register__FileSetInput_struct_33']?.()
|
83
|
+
__napiInstance.exports['__napi_register__RuntimeInput_struct_34']?.()
|
84
|
+
__napiInstance.exports['__napi_register__EnvironmentInput_struct_35']?.()
|
85
|
+
__napiInstance.exports['__napi_register__ExternalDependenciesInput_struct_36']?.()
|
86
|
+
__napiInstance.exports['__napi_register__DepsOutputsInput_struct_37']?.()
|
87
|
+
__napiInstance.exports['__napi_register__NxJson_struct_38']?.()
|
88
|
+
__napiInstance.exports['__napi_register__WorkspaceContext_struct_39']?.()
|
89
|
+
__napiInstance.exports['__napi_register__WorkspaceContext_impl_48']?.()
|
90
|
+
__napiInstance.exports['__napi_register__WorkspaceErrors_49']?.()
|
91
|
+
__napiInstance.exports['__napi_register__NxWorkspaceFiles_struct_50']?.()
|
92
|
+
__napiInstance.exports['__napi_register__NxWorkspaceFilesExternals_struct_51']?.()
|
93
|
+
__napiInstance.exports['__napi_register__UpdatedWorkspaceFiles_struct_52']?.()
|
94
|
+
__napiInstance.exports['__napi_register__FileMap_struct_53']?.()
|
95
|
+
__napiInstance.exports['__napi_register____test_only_transfer_file_map_54']?.()
|
105
96
|
}
|
106
97
|
export const HashPlanner = __napiModule.exports.HashPlanner
|
107
98
|
export const ImportResult = __napiModule.exports.ImportResult
|
108
|
-
export const NxCache = __napiModule.exports.NxCache
|
109
|
-
export const NxTaskHistory = __napiModule.exports.NxTaskHistory
|
110
|
-
export const TaskDetails = __napiModule.exports.TaskDetails
|
111
99
|
export const TaskHasher = __napiModule.exports.TaskHasher
|
112
100
|
export const WorkspaceContext = __napiModule.exports.WorkspaceContext
|
113
101
|
export const copy = __napiModule.exports.copy
|
package/src/native/nx.wasi.cjs
CHANGED
@@ -82,63 +82,51 @@ const { instance: __napiInstance, module: __wasiModule, napiModule: __napiModule
|
|
82
82
|
})
|
83
83
|
|
84
84
|
function __napi_rs_initialize_modules(__napiInstance) {
|
85
|
-
__napiInstance.exports['
|
86
|
-
__napiInstance.exports['
|
87
|
-
__napiInstance.exports['
|
88
|
-
__napiInstance.exports['
|
89
|
-
__napiInstance.exports['
|
90
|
-
__napiInstance.exports['
|
91
|
-
__napiInstance.exports['
|
92
|
-
__napiInstance.exports['
|
93
|
-
__napiInstance.exports['
|
94
|
-
__napiInstance.exports['
|
95
|
-
__napiInstance.exports['
|
96
|
-
__napiInstance.exports['
|
97
|
-
__napiInstance.exports['
|
98
|
-
__napiInstance.exports['
|
99
|
-
__napiInstance.exports['
|
100
|
-
__napiInstance.exports['
|
101
|
-
__napiInstance.exports['
|
102
|
-
__napiInstance.exports['
|
103
|
-
__napiInstance.exports['
|
104
|
-
__napiInstance.exports['
|
105
|
-
__napiInstance.exports['
|
106
|
-
__napiInstance.exports['
|
107
|
-
__napiInstance.exports['
|
108
|
-
__napiInstance.exports['
|
109
|
-
__napiInstance.exports['
|
110
|
-
__napiInstance.exports['
|
111
|
-
__napiInstance.exports['
|
112
|
-
__napiInstance.exports['
|
113
|
-
__napiInstance.exports['
|
114
|
-
__napiInstance.exports['
|
115
|
-
__napiInstance.exports['
|
116
|
-
__napiInstance.exports['
|
117
|
-
__napiInstance.exports['
|
118
|
-
__napiInstance.exports['
|
119
|
-
__napiInstance.exports['
|
120
|
-
__napiInstance.exports['
|
121
|
-
__napiInstance.exports['
|
122
|
-
__napiInstance.exports['
|
123
|
-
__napiInstance.exports['
|
124
|
-
__napiInstance.exports['
|
125
|
-
__napiInstance.exports['
|
126
|
-
__napiInstance.exports['
|
127
|
-
__napiInstance.exports['__napi_register__NxJson_struct_59']?.()
|
128
|
-
__napiInstance.exports['__napi_register__WorkspaceContext_struct_60']?.()
|
129
|
-
__napiInstance.exports['__napi_register__WorkspaceContext_impl_69']?.()
|
130
|
-
__napiInstance.exports['__napi_register__WorkspaceErrors_70']?.()
|
131
|
-
__napiInstance.exports['__napi_register__NxWorkspaceFiles_struct_71']?.()
|
132
|
-
__napiInstance.exports['__napi_register__NxWorkspaceFilesExternals_struct_72']?.()
|
133
|
-
__napiInstance.exports['__napi_register__UpdatedWorkspaceFiles_struct_73']?.()
|
134
|
-
__napiInstance.exports['__napi_register__FileMap_struct_74']?.()
|
135
|
-
__napiInstance.exports['__napi_register____test_only_transfer_file_map_75']?.()
|
85
|
+
__napiInstance.exports['__napi_register__expand_outputs_0']?.()
|
86
|
+
__napiInstance.exports['__napi_register__get_files_for_outputs_1']?.()
|
87
|
+
__napiInstance.exports['__napi_register__remove_2']?.()
|
88
|
+
__napiInstance.exports['__napi_register__copy_3']?.()
|
89
|
+
__napiInstance.exports['__napi_register__validate_outputs_4']?.()
|
90
|
+
__napiInstance.exports['__napi_register__get_transformable_outputs_5']?.()
|
91
|
+
__napiInstance.exports['__napi_register__hash_array_6']?.()
|
92
|
+
__napiInstance.exports['__napi_register__hash_file_7']?.()
|
93
|
+
__napiInstance.exports['__napi_register__IS_WASM_8']?.()
|
94
|
+
__napiInstance.exports['__napi_register__get_binary_target_9']?.()
|
95
|
+
__napiInstance.exports['__napi_register__ImportResult_struct_10']?.()
|
96
|
+
__napiInstance.exports['__napi_register__find_imports_11']?.()
|
97
|
+
__napiInstance.exports['__napi_register__transfer_project_graph_12']?.()
|
98
|
+
__napiInstance.exports['__napi_register__ExternalNode_struct_13']?.()
|
99
|
+
__napiInstance.exports['__napi_register__Target_struct_14']?.()
|
100
|
+
__napiInstance.exports['__napi_register__Project_struct_15']?.()
|
101
|
+
__napiInstance.exports['__napi_register__ProjectGraph_struct_16']?.()
|
102
|
+
__napiInstance.exports['__napi_register__HashPlanner_struct_17']?.()
|
103
|
+
__napiInstance.exports['__napi_register__HashPlanner_impl_21']?.()
|
104
|
+
__napiInstance.exports['__napi_register__HashDetails_struct_22']?.()
|
105
|
+
__napiInstance.exports['__napi_register__HasherOptions_struct_23']?.()
|
106
|
+
__napiInstance.exports['__napi_register__TaskHasher_struct_24']?.()
|
107
|
+
__napiInstance.exports['__napi_register__TaskHasher_impl_27']?.()
|
108
|
+
__napiInstance.exports['__napi_register__Task_struct_28']?.()
|
109
|
+
__napiInstance.exports['__napi_register__TaskTarget_struct_29']?.()
|
110
|
+
__napiInstance.exports['__napi_register__TaskGraph_struct_30']?.()
|
111
|
+
__napiInstance.exports['__napi_register__FileData_struct_31']?.()
|
112
|
+
__napiInstance.exports['__napi_register__InputsInput_struct_32']?.()
|
113
|
+
__napiInstance.exports['__napi_register__FileSetInput_struct_33']?.()
|
114
|
+
__napiInstance.exports['__napi_register__RuntimeInput_struct_34']?.()
|
115
|
+
__napiInstance.exports['__napi_register__EnvironmentInput_struct_35']?.()
|
116
|
+
__napiInstance.exports['__napi_register__ExternalDependenciesInput_struct_36']?.()
|
117
|
+
__napiInstance.exports['__napi_register__DepsOutputsInput_struct_37']?.()
|
118
|
+
__napiInstance.exports['__napi_register__NxJson_struct_38']?.()
|
119
|
+
__napiInstance.exports['__napi_register__WorkspaceContext_struct_39']?.()
|
120
|
+
__napiInstance.exports['__napi_register__WorkspaceContext_impl_48']?.()
|
121
|
+
__napiInstance.exports['__napi_register__WorkspaceErrors_49']?.()
|
122
|
+
__napiInstance.exports['__napi_register__NxWorkspaceFiles_struct_50']?.()
|
123
|
+
__napiInstance.exports['__napi_register__NxWorkspaceFilesExternals_struct_51']?.()
|
124
|
+
__napiInstance.exports['__napi_register__UpdatedWorkspaceFiles_struct_52']?.()
|
125
|
+
__napiInstance.exports['__napi_register__FileMap_struct_53']?.()
|
126
|
+
__napiInstance.exports['__napi_register____test_only_transfer_file_map_54']?.()
|
136
127
|
}
|
137
128
|
module.exports.HashPlanner = __napiModule.exports.HashPlanner
|
138
129
|
module.exports.ImportResult = __napiModule.exports.ImportResult
|
139
|
-
module.exports.NxCache = __napiModule.exports.NxCache
|
140
|
-
module.exports.NxTaskHistory = __napiModule.exports.NxTaskHistory
|
141
|
-
module.exports.TaskDetails = __napiModule.exports.TaskDetails
|
142
130
|
module.exports.TaskHasher = __napiModule.exports.TaskHasher
|
143
131
|
module.exports.WorkspaceContext = __napiModule.exports.WorkspaceContext
|
144
132
|
module.exports.copy = __napiModule.exports.copy
|
Binary file
|
@@ -63,6 +63,13 @@ function registerTsProject(path, configFilename) {
|
|
63
63
|
// Based on limited testing, it doesn't seem to matter if we register it multiple times, but just in
|
64
64
|
// case let's keep a flag to prevent it.
|
65
65
|
if (!isTsEsmLoaderRegistered) {
|
66
|
+
// We need a way to ensure that `.ts` files are treated as ESM not CJS.
|
67
|
+
// Since there is no way to pass compilerOptions like we do with the programmatic API, we should default
|
68
|
+
// the environment variable that ts-node checks.
|
69
|
+
process.env.TS_NODE_COMPILER_OPTIONS ??= JSON.stringify({
|
70
|
+
moduleResolution: 'nodenext',
|
71
|
+
module: 'nodenext',
|
72
|
+
});
|
66
73
|
const module = require('node:module');
|
67
74
|
if (module.register && packageIsInstalled('ts-node/esm')) {
|
68
75
|
const url = require('node:url');
|
@@ -17,7 +17,8 @@ const nx_json_1 = require("../config/nx-json");
|
|
17
17
|
const update_manager_1 = require("../nx-cloud/update-manager");
|
18
18
|
const get_cloud_options_1 = require("../nx-cloud/utilities/get-cloud-options");
|
19
19
|
function getCache(options) {
|
20
|
-
return process.env.
|
20
|
+
return process.env.NX_DISABLE_DB !== 'true' &&
|
21
|
+
process.env.NX_DB_CACHE === 'true'
|
21
22
|
? new DbCache({
|
22
23
|
// Remove this in Nx 21
|
23
24
|
nxCloudRemoteCache: (0, nx_cloud_utils_1.isNxCloudUsed)((0, nx_json_1.readNxJson)())
|
@@ -439,7 +439,9 @@ function constructLifeCycles(lifeCycle) {
|
|
439
439
|
lifeCycles.push(new task_profiling_life_cycle_1.TaskProfilingLifeCycle(process.env.NX_PROFILE));
|
440
440
|
}
|
441
441
|
if (!(0, nx_cloud_utils_1.isNxCloudUsed)((0, nx_json_1.readNxJson)())) {
|
442
|
-
lifeCycles.push(
|
442
|
+
lifeCycles.push(process.env.NX_DISABLE_DB !== 'true' && !native_1.IS_WASM
|
443
|
+
? new task_history_life_cycle_1.TaskHistoryLifeCycle()
|
444
|
+
: new task_history_life_cycle_old_1.LegacyTaskHistoryLifeCycle());
|
443
445
|
}
|
444
446
|
return lifeCycles;
|
445
447
|
}
|
@@ -43,7 +43,7 @@ class TaskOrchestrator {
|
|
43
43
|
// Init the ForkedProcessTaskRunner
|
44
44
|
await this.forkedProcessTaskRunner.init();
|
45
45
|
// initial scheduling
|
46
|
-
await this.scheduleNextTasks();
|
46
|
+
await this.tasksSchedule.scheduleNextTasks();
|
47
47
|
perf_hooks_1.performance.mark('task-execution:start');
|
48
48
|
const threads = [];
|
49
49
|
process.stdout.setMaxListeners(this.options.parallel + events_1.defaultMaxListeners);
|
@@ -65,6 +65,7 @@ class TaskOrchestrator {
|
|
65
65
|
}
|
66
66
|
const doNotSkipCache = this.options.skipNxCache === false ||
|
67
67
|
this.options.skipNxCache === undefined;
|
68
|
+
this.processAllScheduledTasks();
|
68
69
|
const batch = this.tasksSchedule.nextBatch();
|
69
70
|
if (batch) {
|
70
71
|
const groupId = this.closeGroup();
|
@@ -373,15 +374,11 @@ class TaskOrchestrator {
|
|
373
374
|
status,
|
374
375
|
};
|
375
376
|
}));
|
376
|
-
await this.scheduleNextTasks();
|
377
|
+
await this.tasksSchedule.scheduleNextTasks();
|
377
378
|
// release blocked threads
|
378
379
|
this.waitingForTasks.forEach((f) => f(null));
|
379
380
|
this.waitingForTasks.length = 0;
|
380
381
|
}
|
381
|
-
async scheduleNextTasks() {
|
382
|
-
await this.tasksSchedule.scheduleNextTasks();
|
383
|
-
this.processAllScheduledTasks();
|
384
|
-
}
|
385
382
|
complete(taskResults) {
|
386
383
|
this.tasksSchedule.complete(taskResults.map(({ taskId }) => taskId));
|
387
384
|
for (const { taskId, status } of taskResults) {
|
package/src/utils/git-utils.d.ts
CHANGED
@@ -25,10 +25,11 @@ export declare class GitRepository {
|
|
25
25
|
deleteGitRemote(name: string): Promise<string>;
|
26
26
|
addGitRemote(name: string, url: string): Promise<string>;
|
27
27
|
hasFilterRepoInstalled(): Promise<boolean>;
|
28
|
-
filterRepo(
|
29
|
-
filterBranch(
|
28
|
+
filterRepo(source: string, destination: string): Promise<void>;
|
29
|
+
filterBranch(source: string, destination: string, branchName: string): Promise<void>;
|
30
30
|
private execAsync;
|
31
31
|
private quotePath;
|
32
|
+
private quoteArg;
|
32
33
|
}
|
33
34
|
/**
|
34
35
|
* This is currently duplicated in Nx Console. Please let @MaxKless know if you make changes here.
|
File without changes
|
@@ -0,0 +1,20 @@
|
|
1
|
+
/**
|
2
|
+
* This is meant to be used with `git filter-branch --index-filter` to rewrite
|
3
|
+
* history such that only commits related to the subdirectory is kept.
|
4
|
+
*
|
5
|
+
* Example:
|
6
|
+
* NX_IMPORT_SOURCE=<source> git filter-branch --index-filter 'node git-utils.index-filter.js' --prune-empty -- --all
|
7
|
+
*/
|
8
|
+
try {
|
9
|
+
const { execSync } = require('child_process');
|
10
|
+
// NOTE: Using env vars because Windows PowerShell has its own handling of quotes (") messes up quotes in args, even if escaped.
|
11
|
+
const src = process.env.NX_IMPORT_SOURCE;
|
12
|
+
execSync('git read-tree --empty', { stdio: 'inherit' });
|
13
|
+
execSync(`git reset ${process.env.GIT_COMMIT} -- "${src}"`, {
|
14
|
+
stdio: 'inherit',
|
15
|
+
});
|
16
|
+
}
|
17
|
+
catch (error) {
|
18
|
+
console.error(`Error executing Git commands: ${error}`);
|
19
|
+
process.exit(1);
|
20
|
+
}
|
package/src/utils/git-utils.js
CHANGED
@@ -105,32 +105,63 @@ class GitRepository {
|
|
105
105
|
}
|
106
106
|
// git-filter-repo is much faster than filter-branch, but needs to be installed by user
|
107
107
|
// Use `hasFilterRepoInstalled` to check if it's installed
|
108
|
-
async filterRepo(
|
109
|
-
// filter-repo requires POSIX path to work
|
110
|
-
const
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
108
|
+
async filterRepo(source, destination) {
|
109
|
+
// NOTE: filter-repo requires POSIX path to work
|
110
|
+
const sourcePosixPath = source.split(path_1.sep).join(path_1.posix.sep);
|
111
|
+
const destinationPosixPath = destination.split(path_1.sep).join(path_1.posix.sep);
|
112
|
+
await this.execAsync(`git filter-repo -f ${source !== '' ? `--path ${this.quotePath(sourcePosixPath)}` : ''} ${source !== destination
|
113
|
+
? `--path-rename ${this.quotePath(sourcePosixPath, true)}:${this.quotePath(destinationPosixPath, true)}`
|
114
|
+
: ''}`);
|
115
|
+
}
|
116
|
+
async filterBranch(source, destination, branchName) {
|
116
117
|
// We need non-ASCII file names to not be quoted, or else filter-branch will exclude them.
|
117
118
|
await this.execAsync(`git config core.quotepath false`);
|
118
|
-
|
119
|
+
// NOTE: filter-repo requires POSIX path to work
|
120
|
+
const sourcePosixPath = source.split(path_1.sep).join(path_1.posix.sep);
|
121
|
+
const destinationPosixPath = destination.split(path_1.sep).join(path_1.posix.sep);
|
122
|
+
// First, if the source is not a root project, then only include commits relevant to the subdirectory.
|
123
|
+
if (source !== '') {
|
124
|
+
const indexFilterCommand = this.quoteArg(`node ${(0, path_1.join)(__dirname, 'git-utils.index-filter.js')}`);
|
125
|
+
await this.execAsync(`git filter-branch -f --index-filter ${indexFilterCommand} --prune-empty -- ${branchName}`, {
|
126
|
+
NX_IMPORT_SOURCE: sourcePosixPath,
|
127
|
+
NX_IMPORT_DESTINATION: destinationPosixPath,
|
128
|
+
});
|
129
|
+
}
|
130
|
+
// Then, move files to their new location if necessary.
|
131
|
+
if (source === '' || source !== destination) {
|
132
|
+
const treeFilterCommand = this.quoteArg(`node ${(0, path_1.join)(__dirname, 'git-utils.tree-filter.js')}`);
|
133
|
+
await this.execAsync(`git filter-branch -f --tree-filter ${treeFilterCommand} -- ${branchName}`, {
|
134
|
+
NX_IMPORT_SOURCE: sourcePosixPath,
|
135
|
+
NX_IMPORT_DESTINATION: destinationPosixPath,
|
136
|
+
});
|
137
|
+
}
|
119
138
|
}
|
120
|
-
execAsync(command) {
|
139
|
+
execAsync(command, env) {
|
121
140
|
return execAsync(command, {
|
122
141
|
cwd: this.root,
|
123
142
|
maxBuffer: 10 * 1024 * 1024,
|
143
|
+
env: {
|
144
|
+
...process.env,
|
145
|
+
...env,
|
146
|
+
},
|
124
147
|
});
|
125
148
|
}
|
126
|
-
quotePath(path) {
|
149
|
+
quotePath(path, ensureTrailingSlash) {
|
150
|
+
return this.quoteArg(ensureTrailingSlash && path !== '' && !path.endsWith('/')
|
151
|
+
? `${path}/`
|
152
|
+
: path);
|
153
|
+
}
|
154
|
+
quoteArg(arg) {
|
127
155
|
return process.platform === 'win32'
|
128
156
|
? // Windows/CMD only understands double-quotes, single-quotes are treated as part of the file name
|
129
157
|
// Bash and other shells will substitute `$` in file names with a variable value.
|
130
|
-
`"${
|
158
|
+
`"${arg
|
159
|
+
// Need to keep two slashes for Windows or else the path will be invalid.
|
160
|
+
// e.g. 'C:\Users\bob\projects\repo' is invalid, but 'C:\\Users\\bob\\projects\\repo' is valid
|
161
|
+
.replaceAll('\\', '\\\\')}"`
|
131
162
|
: // e.g. `git mv "$$file.txt" "libs/a/$$file.txt"` will not work since `$$` is swapped with the PID of the last process.
|
132
163
|
// Using single-quotes prevents this substitution.
|
133
|
-
`'${
|
164
|
+
`'${arg}'`;
|
134
165
|
}
|
135
166
|
}
|
136
167
|
exports.GitRepository = GitRepository;
|
@@ -0,0 +1,11 @@
|
|
1
|
+
/**
|
2
|
+
* This is meant to be used with `git filter-branch --tree-filter` to rewrite
|
3
|
+
* history to only include commits related to the source project folder. If the
|
4
|
+
* destination folder is different, this script also moves the files over.
|
5
|
+
*
|
6
|
+
* Example:
|
7
|
+
* NX_IMPORT_SOURCE=<source> NX_IMPORT_DESTINATION=<destination> git filter-branch --tree-filter 'node git-utils.tree-filter.js' --prune-empty -- --all
|
8
|
+
*/
|
9
|
+
declare const execSync: any;
|
10
|
+
declare const existsSync: any, mkdirSync: any, renameSync: any, rmSync: any;
|
11
|
+
declare const posix: any;
|
@@ -0,0 +1,43 @@
|
|
1
|
+
/**
|
2
|
+
* This is meant to be used with `git filter-branch --tree-filter` to rewrite
|
3
|
+
* history to only include commits related to the source project folder. If the
|
4
|
+
* destination folder is different, this script also moves the files over.
|
5
|
+
*
|
6
|
+
* Example:
|
7
|
+
* NX_IMPORT_SOURCE=<source> NX_IMPORT_DESTINATION=<destination> git filter-branch --tree-filter 'node git-utils.tree-filter.js' --prune-empty -- --all
|
8
|
+
*/
|
9
|
+
const { execSync } = require('child_process');
|
10
|
+
const { existsSync, mkdirSync, renameSync, rmSync } = require('fs');
|
11
|
+
// NOTE: The path passed to `git filter-branch` is POSIX, so we need to use the `posix` module.
|
12
|
+
const { posix } = require('path');
|
13
|
+
try {
|
14
|
+
// NOTE: Using env vars because Windows PowerShell has its own handling of quotes (") messes up quotes in args, even if escaped.
|
15
|
+
const src = process.env.NX_IMPORT_SOURCE;
|
16
|
+
const dest = process.env.NX_IMPORT_DESTINATION;
|
17
|
+
const files = execSync(`git ls-files -z ${src}`)
|
18
|
+
.toString()
|
19
|
+
.trim()
|
20
|
+
.split('\x00')
|
21
|
+
.map((s) => s.trim())
|
22
|
+
.filter(Boolean);
|
23
|
+
for (const file of files) {
|
24
|
+
if (src === '' || file.startsWith(src)) {
|
25
|
+
// If source and destination are the same, then keep the file as is.
|
26
|
+
if (src === dest)
|
27
|
+
continue;
|
28
|
+
const destFile = posix.join(dest, file.replace(src, ''));
|
29
|
+
const dir = posix.dirname(destFile);
|
30
|
+
if (!existsSync(dir))
|
31
|
+
mkdirSync(dir, { recursive: true });
|
32
|
+
renameSync(file, destFile);
|
33
|
+
}
|
34
|
+
else {
|
35
|
+
// If not matching the source we are filtering, remove it.
|
36
|
+
rmSync(file);
|
37
|
+
}
|
38
|
+
}
|
39
|
+
}
|
40
|
+
catch (error) {
|
41
|
+
console.error(`Error executing Git commands: ${error}`);
|
42
|
+
process.exit(1);
|
43
|
+
}
|