@nx/eslint 0.0.0-pr-31231-180f614 → 0.0.0-pr-31222-862e973
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/LICENSE +1 -1
- package/README.md +1 -1
- package/migrations.json +112 -69
- package/package.json +7 -6
- package/src/executors/lint/utility/eslint-utils.js +0 -6
- package/src/generators/convert-to-flat-config/converters/json-converter.d.ts +1 -1
- package/src/generators/convert-to-flat-config/converters/json-converter.js +18 -10
- package/src/generators/convert-to-flat-config/generator.js +17 -18
- package/src/generators/convert-to-flat-config/schema.d.ts +0 -2
- package/src/generators/convert-to-inferred/convert-to-inferred.js +1 -2
- package/src/generators/init/global-eslint-config.d.ts +1 -1
- package/src/generators/init/global-eslint-config.js +6 -17
- package/src/generators/init/init-migration.d.ts +1 -1
- package/src/generators/init/init-migration.js +13 -18
- package/src/generators/init/init.d.ts +0 -1
- package/src/generators/init/init.js +6 -31
- package/src/generators/lint-project/lint-project.d.ts +0 -1
- package/src/generators/lint-project/lint-project.js +15 -37
- package/src/generators/lint-project/setup-root-eslint.d.ts +0 -1
- package/src/generators/lint-project/setup-root-eslint.js +1 -2
- package/src/generators/utils/eslint-file.d.ts +2 -3
- package/src/generators/utils/eslint-file.js +28 -160
- package/src/generators/utils/flat-config/ast-utils.d.ts +4 -12
- package/src/generators/utils/flat-config/ast-utils.js +63 -412
- package/src/generators/utils/linter.d.ts +0 -3
- package/src/generators/utils/linter.js +2 -2
- package/src/generators/workspace-rules-project/workspace-rules-project.js +1 -3
- package/src/migrations/update-16-0-0-add-nx-packages/update-16-0-0-add-nx-packages.d.ts +2 -0
- package/src/migrations/update-16-0-0-add-nx-packages/update-16-0-0-add-nx-packages.js +9 -0
- package/src/migrations/update-16-8-0-add-ignored-files/update-16-8-0-add-ignored-files.d.ts +2 -0
- package/src/migrations/update-16-8-0-add-ignored-files/update-16-8-0-add-ignored-files.js +44 -0
- package/src/migrations/update-17-0-0-rename-to-eslint/update-17-0-0-rename-to-eslint.d.ts +2 -0
- package/src/migrations/update-17-0-0-rename-to-eslint/update-17-0-0-rename-to-eslint.js +47 -0
- package/src/migrations/update-17-1-0/update-typescript-eslint.d.ts +2 -0
- package/src/migrations/update-17-1-0/update-typescript-eslint.js +74 -0
- package/src/migrations/update-17-2-0/simplify-eslint-patterns.d.ts +2 -0
- package/src/migrations/update-17-2-0/simplify-eslint-patterns.js +46 -0
- package/src/migrations/update-17-2-9/move-options-to-target-defaults.d.ts +2 -0
- package/src/migrations/update-17-2-9/move-options-to-target-defaults.js +107 -0
- package/src/plugins/plugin.js +10 -21
- package/src/utils/config-file.d.ts +1 -3
- package/src/utils/config-file.js +2 -5
- package/src/utils/flat-config.d.ts +0 -1
- package/src/utils/flat-config.js +3 -9
- package/src/utils/version-utils.d.ts +0 -1
- package/src/utils/version-utils.js +9 -13
- package/src/utils/versions.d.ts +2 -3
- package/src/utils/versions.js +3 -4
- package/src/migrations/update-20-2-0/update-typescript-eslint-v8-13-0.d.ts +0 -2
- package/src/migrations/update-20-2-0/update-typescript-eslint-v8-13-0.js +0 -23
- package/src/migrations/update-20-3-0/add-file-extensions-to-overrides.d.ts +0 -2
- package/src/migrations/update-20-3-0/add-file-extensions-to-overrides.js +0 -49
|
@@ -4,7 +4,6 @@ export interface LinterInitOptions {
|
|
|
4
4
|
keepExistingVersions?: boolean;
|
|
5
5
|
updatePackageScripts?: boolean;
|
|
6
6
|
addPlugin?: boolean;
|
|
7
|
-
eslintConfigFormat?: 'mjs' | 'cjs';
|
|
8
7
|
}
|
|
9
8
|
export declare function initEsLint(tree: Tree, options: LinterInitOptions): Promise<GeneratorCallback>;
|
|
10
9
|
export declare function lintInitGenerator(tree: Tree, options: LinterInitOptions): Promise<GeneratorCallback>;
|
|
@@ -8,19 +8,18 @@ const versions_1 = require("../../utils/versions");
|
|
|
8
8
|
const eslint_file_1 = require("../utils/eslint-file");
|
|
9
9
|
const plugin_1 = require("../../plugins/plugin");
|
|
10
10
|
const plugin_2 = require("../utils/plugin");
|
|
11
|
-
|
|
12
|
-
function updateProductionFileset(tree, format = 'mjs') {
|
|
11
|
+
function updateProductionFileset(tree) {
|
|
13
12
|
const nxJson = (0, devkit_1.readNxJson)(tree);
|
|
14
13
|
const productionFileSet = nxJson.namedInputs?.production;
|
|
15
14
|
if (productionFileSet) {
|
|
16
15
|
productionFileSet.push('!{projectRoot}/.eslintrc.json');
|
|
17
|
-
productionFileSet.push(
|
|
16
|
+
productionFileSet.push('!{projectRoot}/eslint.config.js');
|
|
18
17
|
// Dedupe and set
|
|
19
18
|
nxJson.namedInputs.production = Array.from(new Set(productionFileSet));
|
|
20
19
|
}
|
|
21
20
|
(0, devkit_1.updateNxJson)(tree, nxJson);
|
|
22
21
|
}
|
|
23
|
-
function addTargetDefaults(tree
|
|
22
|
+
function addTargetDefaults(tree) {
|
|
24
23
|
const nxJson = (0, devkit_1.readNxJson)(tree);
|
|
25
24
|
nxJson.targetDefaults ??= {};
|
|
26
25
|
nxJson.targetDefaults['@nx/eslint:lint'] ??= {};
|
|
@@ -29,40 +28,17 @@ function addTargetDefaults(tree, format) {
|
|
|
29
28
|
'default',
|
|
30
29
|
`{workspaceRoot}/.eslintrc.json`,
|
|
31
30
|
`{workspaceRoot}/.eslintignore`,
|
|
32
|
-
`{workspaceRoot}/eslint.config
|
|
31
|
+
`{workspaceRoot}/eslint.config.js`,
|
|
33
32
|
];
|
|
34
33
|
(0, devkit_1.updateNxJson)(tree, nxJson);
|
|
35
34
|
}
|
|
36
|
-
function updateVsCodeRecommendedExtensions(host) {
|
|
37
|
-
if (!host.exists('.vscode/extensions.json')) {
|
|
38
|
-
return;
|
|
39
|
-
}
|
|
40
|
-
(0, devkit_1.updateJson)(host, '.vscode/extensions.json', (json) => {
|
|
41
|
-
json.recommendations = json.recommendations || [];
|
|
42
|
-
const extension = 'dbaeumer.vscode-eslint';
|
|
43
|
-
if (!json.recommendations.includes(extension)) {
|
|
44
|
-
json.recommendations.push(extension);
|
|
45
|
-
}
|
|
46
|
-
return json;
|
|
47
|
-
});
|
|
48
|
-
}
|
|
49
35
|
async function initEsLint(tree, options) {
|
|
50
36
|
const nxJson = (0, devkit_1.readNxJson)(tree);
|
|
51
37
|
const addPluginDefault = process.env.NX_ADD_PLUGINS !== 'false' &&
|
|
52
38
|
nxJson.useInferencePlugins !== false;
|
|
53
39
|
options.addPlugin ??= addPluginDefault;
|
|
54
|
-
options.eslintConfigFormat ??= 'mjs';
|
|
55
40
|
const hasPlugin = (0, plugin_2.hasEslintPlugin)(tree);
|
|
56
41
|
const rootEslintFile = (0, eslint_file_1.findEslintFile)(tree);
|
|
57
|
-
if (rootEslintFile) {
|
|
58
|
-
const fileExtension = (0, path_1.extname)(rootEslintFile);
|
|
59
|
-
if (fileExtension === '.mjs' || fileExtension === '.cjs') {
|
|
60
|
-
options.eslintConfigFormat = fileExtension.slice(1);
|
|
61
|
-
}
|
|
62
|
-
else {
|
|
63
|
-
options.eslintConfigFormat = (0, eslint_file_1.determineEslintConfigFormat)(tree.read(rootEslintFile, 'utf-8'));
|
|
64
|
-
}
|
|
65
|
-
}
|
|
66
42
|
const graph = await (0, devkit_1.createProjectGraphAsync)();
|
|
67
43
|
const lintTargetNames = [
|
|
68
44
|
'lint',
|
|
@@ -81,15 +57,14 @@ async function initEsLint(tree, options) {
|
|
|
81
57
|
if (rootEslintFile) {
|
|
82
58
|
return () => { };
|
|
83
59
|
}
|
|
84
|
-
updateProductionFileset(tree
|
|
85
|
-
updateVsCodeRecommendedExtensions(tree);
|
|
60
|
+
updateProductionFileset(tree);
|
|
86
61
|
if (options.addPlugin) {
|
|
87
62
|
await (0, add_plugin_1.addPlugin)(tree, graph, '@nx/eslint/plugin', plugin_1.createNodesV2, {
|
|
88
63
|
targetName: lintTargetNames,
|
|
89
64
|
}, options.updatePackageScripts);
|
|
90
65
|
}
|
|
91
66
|
else {
|
|
92
|
-
addTargetDefaults(tree
|
|
67
|
+
addTargetDefaults(tree);
|
|
93
68
|
}
|
|
94
69
|
const tasks = [];
|
|
95
70
|
if (!options.skipPackageJson) {
|
|
@@ -12,15 +12,12 @@ const flat_config_1 = require("../../utils/flat-config");
|
|
|
12
12
|
const ast_utils_1 = require("../utils/flat-config/ast-utils");
|
|
13
13
|
const config_file_1 = require("../../utils/config-file");
|
|
14
14
|
const plugin_1 = require("../utils/plugin");
|
|
15
|
-
const versions_1 = require("../../utils/versions");
|
|
16
15
|
const setup_root_eslint_1 = require("./setup-root-eslint");
|
|
17
|
-
const ts_solution_setup_1 = require("@nx/js/src/utils/typescript/ts-solution-setup");
|
|
18
16
|
function lintProjectGenerator(tree, options) {
|
|
19
17
|
return lintProjectGeneratorInternal(tree, { addPlugin: false, ...options });
|
|
20
18
|
}
|
|
21
19
|
async function lintProjectGeneratorInternal(tree, options) {
|
|
22
20
|
const nxJson = (0, devkit_1.readNxJson)(tree);
|
|
23
|
-
options.eslintConfigFormat ??= 'mjs';
|
|
24
21
|
const addPluginDefault = process.env.NX_ADD_PLUGINS !== 'false' &&
|
|
25
22
|
nxJson.useInferencePlugins !== false;
|
|
26
23
|
options.addPlugin ??= addPluginDefault;
|
|
@@ -28,14 +25,12 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
28
25
|
const initTask = await (0, init_1.lintInitGenerator)(tree, {
|
|
29
26
|
skipPackageJson: options.skipPackageJson,
|
|
30
27
|
addPlugin: options.addPlugin,
|
|
31
|
-
eslintConfigFormat: options.eslintConfigFormat,
|
|
32
28
|
});
|
|
33
29
|
tasks.push(initTask);
|
|
34
30
|
const rootEsLintTask = (0, setup_root_eslint_1.setupRootEsLint)(tree, {
|
|
35
31
|
unitTestRunner: options.unitTestRunner,
|
|
36
32
|
skipPackageJson: options.skipPackageJson,
|
|
37
33
|
rootProject: options.rootProject,
|
|
38
|
-
eslintConfigFormat: options.eslintConfigFormat,
|
|
39
34
|
});
|
|
40
35
|
tasks.push(rootEsLintTask);
|
|
41
36
|
const projectConfig = (0, devkit_1.readProjectConfiguration)(tree, options.project);
|
|
@@ -46,7 +41,7 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
46
41
|
if (lintFilePatterns &&
|
|
47
42
|
lintFilePatterns.length &&
|
|
48
43
|
!lintFilePatterns.includes('{projectRoot}') &&
|
|
49
|
-
isBuildableLibraryProject(
|
|
44
|
+
isBuildableLibraryProject(projectConfig)) {
|
|
50
45
|
lintFilePatterns.push(`{projectRoot}/package.json`);
|
|
51
46
|
}
|
|
52
47
|
const hasPlugin = (0, plugin_1.hasEslintPlugin)(tree);
|
|
@@ -54,7 +49,6 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
54
49
|
if (lintFilePatterns &&
|
|
55
50
|
lintFilePatterns.length &&
|
|
56
51
|
lintFilePatterns.some((p) => !['./src', '{projectRoot}', projectConfig.root].includes(p))) {
|
|
57
|
-
projectConfig.targets ??= {};
|
|
58
52
|
projectConfig.targets['lint'] = {
|
|
59
53
|
command: `eslint ${lintFilePatterns
|
|
60
54
|
.join(' ')
|
|
@@ -63,7 +57,6 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
63
57
|
}
|
|
64
58
|
}
|
|
65
59
|
else {
|
|
66
|
-
projectConfig.targets ??= {};
|
|
67
60
|
projectConfig.targets['lint'] = {
|
|
68
61
|
executor: '@nx/eslint:lint',
|
|
69
62
|
};
|
|
@@ -89,7 +82,7 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
89
82
|
filteredProjects.push(project);
|
|
90
83
|
}
|
|
91
84
|
});
|
|
92
|
-
const migrateTask = (0, init_migration_1.migrateConfigToMonorepoStyle)(filteredProjects, tree, options.unitTestRunner, options.
|
|
85
|
+
const migrateTask = (0, init_migration_1.migrateConfigToMonorepoStyle)(filteredProjects, tree, options.unitTestRunner, options.keepExistingVersions);
|
|
93
86
|
tasks.push(migrateTask);
|
|
94
87
|
}
|
|
95
88
|
}
|
|
@@ -97,15 +90,10 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
97
90
|
// additionally, the companion e2e app would have `rootProject: true`
|
|
98
91
|
// so we need to check for the root path as well
|
|
99
92
|
if (!options.rootProject || projectConfig.root !== '.') {
|
|
100
|
-
|
|
101
|
-
isBuildableLibraryProject(tree, projectConfig);
|
|
102
|
-
createEsLintConfiguration(tree, options, projectConfig, options.setParserOptionsProject, options.rootProject, addDependencyChecks);
|
|
103
|
-
if (addDependencyChecks) {
|
|
104
|
-
tasks.push((0, devkit_1.addDependenciesToPackageJson)(tree, {}, { 'jsonc-eslint-parser': versions_1.jsoncEslintParserVersion }, undefined, true));
|
|
105
|
-
}
|
|
93
|
+
createEsLintConfiguration(tree, options, projectConfig, options.setParserOptionsProject, options.rootProject);
|
|
106
94
|
}
|
|
107
95
|
// Buildable libs need source analysis enabled for linting `package.json`.
|
|
108
|
-
if (isBuildableLibraryProject(
|
|
96
|
+
if (isBuildableLibraryProject(projectConfig) &&
|
|
109
97
|
!isJsAnalyzeSourceFilesEnabled(tree)) {
|
|
110
98
|
(0, devkit_1.updateJson)(tree, 'nx.json', (json) => {
|
|
111
99
|
json.pluginsConfig ??= {};
|
|
@@ -120,24 +108,14 @@ async function lintProjectGeneratorInternal(tree, options) {
|
|
|
120
108
|
}
|
|
121
109
|
return (0, devkit_1.runTasksInSerial)(...tasks);
|
|
122
110
|
}
|
|
123
|
-
function createEsLintConfiguration(tree, options, projectConfig, setParserOptionsProject, rootProject
|
|
111
|
+
function createEsLintConfiguration(tree, options, projectConfig, setParserOptionsProject, rootProject) {
|
|
124
112
|
// we are only extending root for non-standalone projects or their complementary e2e apps
|
|
125
113
|
const extendedRootConfig = rootProject ? undefined : (0, eslint_file_1.findEslintFile)(tree);
|
|
126
114
|
const pathToRootConfig = extendedRootConfig
|
|
127
115
|
? `${(0, devkit_1.offsetFromRoot)(projectConfig.root)}${extendedRootConfig}`
|
|
128
116
|
: undefined;
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
// if the base file extension is `.mjs` we should use `mjs` for the new file
|
|
132
|
-
// or if base the file extension is `.cjs` then the format should be `cjs`
|
|
133
|
-
const fileExtension = (0, path_1.extname)(extendedRootConfig);
|
|
134
|
-
if (fileExtension === '.mjs' || fileExtension === '.cjs') {
|
|
135
|
-
options.eslintConfigFormat = fileExtension.slice(1);
|
|
136
|
-
}
|
|
137
|
-
else {
|
|
138
|
-
options.eslintConfigFormat = (0, eslint_file_1.determineEslintConfigFormat)(tree.read(extendedRootConfig, 'utf-8'));
|
|
139
|
-
}
|
|
140
|
-
}
|
|
117
|
+
const addDependencyChecks = options.addPackageJsonDependencyChecks ||
|
|
118
|
+
isBuildableLibraryProject(projectConfig);
|
|
141
119
|
const overrides = (0, flat_config_1.useFlatConfig)(tree)
|
|
142
120
|
? // For flat configs, we don't need to generate different overrides for each file. Users should add their own overrides as needed.
|
|
143
121
|
[]
|
|
@@ -200,11 +178,11 @@ function createEsLintConfiguration(tree, options, projectConfig, setParserOption
|
|
|
200
178
|
nodes.push((0, ast_utils_1.generateSpreadElement)('baseConfig'));
|
|
201
179
|
}
|
|
202
180
|
overrides.forEach((override) => {
|
|
203
|
-
nodes.push((0, ast_utils_1.generateFlatOverride)(override
|
|
181
|
+
nodes.push((0, ast_utils_1.generateFlatOverride)(override));
|
|
204
182
|
});
|
|
205
|
-
const nodeList = (0, ast_utils_1.createNodeList)(importMap, nodes
|
|
183
|
+
const nodeList = (0, ast_utils_1.createNodeList)(importMap, nodes);
|
|
206
184
|
const content = (0, ast_utils_1.stringifyNodeList)(nodeList);
|
|
207
|
-
tree.write((0, path_1.join)(projectConfig.root,
|
|
185
|
+
tree.write((0, path_1.join)(projectConfig.root, 'eslint.config.js'), content);
|
|
208
186
|
}
|
|
209
187
|
else {
|
|
210
188
|
(0, devkit_1.writeJson)(tree, (0, path_1.join)(projectConfig.root, `.eslintrc.json`), {
|
|
@@ -221,9 +199,8 @@ function isJsAnalyzeSourceFilesEnabled(tree) {
|
|
|
221
199
|
return (jsPluginConfig?.analyzeSourceFiles ??
|
|
222
200
|
nxJson.extends !== 'nx/presets/npm.json');
|
|
223
201
|
}
|
|
224
|
-
function isBuildableLibraryProject(
|
|
225
|
-
return (
|
|
226
|
-
'library' &&
|
|
202
|
+
function isBuildableLibraryProject(projectConfig) {
|
|
203
|
+
return (projectConfig.projectType === 'library' &&
|
|
227
204
|
projectConfig.targets?.build &&
|
|
228
205
|
!!projectConfig.targets.build);
|
|
229
206
|
}
|
|
@@ -233,7 +210,8 @@ function isBuildableLibraryProject(tree, projectConfig) {
|
|
|
233
210
|
*/
|
|
234
211
|
function isMigrationToMonorepoNeeded(tree, graph) {
|
|
235
212
|
// the base config is already created, migration has been done
|
|
236
|
-
if (
|
|
213
|
+
if (tree.exists(config_file_1.baseEsLintConfigFile) ||
|
|
214
|
+
tree.exists(config_file_1.baseEsLintFlatConfigFile)) {
|
|
237
215
|
return false;
|
|
238
216
|
}
|
|
239
217
|
const nodes = Object.values(graph.nodes);
|
|
@@ -243,7 +221,7 @@ function isMigrationToMonorepoNeeded(tree, graph) {
|
|
|
243
221
|
return false;
|
|
244
222
|
}
|
|
245
223
|
for (const targetConfig of Object.values(rootProject.data.targets ?? {})) {
|
|
246
|
-
if (['@nx/eslint:lint', '@nx/linter:eslint'].includes(targetConfig.executor) ||
|
|
224
|
+
if (['@nx/eslint:lint', '@nrwl/linter:eslint', '@nx/linter:eslint'].includes(targetConfig.executor) ||
|
|
247
225
|
(targetConfig.executor === 'nx:run-commands' &&
|
|
248
226
|
targetConfig.options?.command &&
|
|
249
227
|
targetConfig.options?.command.startsWith('eslint '))) {
|
|
@@ -11,7 +11,6 @@ function setupRootEsLint(tree, options) {
|
|
|
11
11
|
if (rootEslintFile) {
|
|
12
12
|
return () => { };
|
|
13
13
|
}
|
|
14
|
-
options.eslintConfigFormat ??= 'mjs';
|
|
15
14
|
if (!(0, flat_config_1.useFlatConfig)(tree)) {
|
|
16
15
|
return setUpLegacyRootEslintRc(tree, options);
|
|
17
16
|
}
|
|
@@ -39,7 +38,7 @@ function setUpLegacyRootEslintRc(tree, options) {
|
|
|
39
38
|
: () => { };
|
|
40
39
|
}
|
|
41
40
|
function setUpRootFlatConfig(tree, options) {
|
|
42
|
-
tree.write(
|
|
41
|
+
tree.write('eslint.config.js', (0, global_eslint_config_1.getGlobalFlatEslintConfiguration)(options.rootProject));
|
|
43
42
|
return !options.skipPackageJson
|
|
44
43
|
? (0, devkit_1.addDependenciesToPackageJson)(tree, {}, {
|
|
45
44
|
'@eslint/js': versions_1.eslint9__eslintVersion,
|
|
@@ -3,13 +3,12 @@ import type { Linter } from 'eslint';
|
|
|
3
3
|
export declare function findEslintFile(tree: Tree, projectRoot?: string): string | null;
|
|
4
4
|
export declare function isEslintConfigSupported(tree: Tree, projectRoot?: string): boolean;
|
|
5
5
|
export declare function updateRelativePathsInConfig(tree: Tree, sourcePath: string, destinationPath: string): void;
|
|
6
|
-
export declare function determineEslintConfigFormat(content: string): 'mjs' | 'cjs';
|
|
7
6
|
export declare function addOverrideToLintConfig(tree: Tree, root: string, override: Partial<Linter.ConfigOverride<Linter.RulesRecord>>, options?: {
|
|
8
7
|
insertAtTheEnd?: boolean;
|
|
9
8
|
checkBaseConfig?: boolean;
|
|
10
9
|
}): void;
|
|
11
|
-
export declare function updateOverrideInLintConfig(tree: Tree,
|
|
12
|
-
export declare function lintConfigHasOverride(tree: Tree,
|
|
10
|
+
export declare function updateOverrideInLintConfig(tree: Tree, root: string, lookup: (override: Linter.ConfigOverride<Linter.RulesRecord>) => boolean, update: (override: Linter.ConfigOverride<Linter.RulesRecord>) => Linter.ConfigOverride<Linter.RulesRecord>): void;
|
|
11
|
+
export declare function lintConfigHasOverride(tree: Tree, root: string, lookup: (override: Linter.ConfigOverride<Linter.RulesRecord>) => boolean, checkBaseConfig?: boolean): boolean;
|
|
13
12
|
export declare function replaceOverridesInLintConfig(tree: Tree, root: string, overrides: Linter.ConfigOverride<Linter.RulesRecord>[]): void;
|
|
14
13
|
export declare function addExtendsToLintConfig(tree: Tree, root: string, plugin: string | {
|
|
15
14
|
name: string;
|
|
@@ -3,7 +3,6 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.findEslintFile = findEslintFile;
|
|
4
4
|
exports.isEslintConfigSupported = isEslintConfigSupported;
|
|
5
5
|
exports.updateRelativePathsInConfig = updateRelativePathsInConfig;
|
|
6
|
-
exports.determineEslintConfigFormat = determineEslintConfigFormat;
|
|
7
6
|
exports.addOverrideToLintConfig = addOverrideToLintConfig;
|
|
8
7
|
exports.updateOverrideInLintConfig = updateOverrideInLintConfig;
|
|
9
8
|
exports.lintConfigHasOverride = lintConfigHasOverride;
|
|
@@ -21,18 +20,12 @@ const version_utils_1 = require("../../utils/version-utils");
|
|
|
21
20
|
const versions_1 = require("../../utils/versions");
|
|
22
21
|
const ast_utils_1 = require("./flat-config/ast-utils");
|
|
23
22
|
const path_utils_1 = require("./flat-config/path-utils");
|
|
24
|
-
const ts = require("typescript");
|
|
25
|
-
const posix_1 = require("node:path/posix");
|
|
26
23
|
function findEslintFile(tree, projectRoot) {
|
|
27
|
-
if (projectRoot === undefined) {
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
if (tree.exists(file)) {
|
|
33
|
-
return file;
|
|
34
|
-
}
|
|
35
|
-
}
|
|
24
|
+
if (projectRoot === undefined && tree.exists(config_file_1.baseEsLintConfigFile)) {
|
|
25
|
+
return config_file_1.baseEsLintConfigFile;
|
|
26
|
+
}
|
|
27
|
+
if (projectRoot === undefined && tree.exists(config_file_1.baseEsLintFlatConfigFile)) {
|
|
28
|
+
return config_file_1.baseEsLintFlatConfigFile;
|
|
36
29
|
}
|
|
37
30
|
projectRoot ??= '';
|
|
38
31
|
for (const file of config_file_1.ESLINT_CONFIG_FILENAMES) {
|
|
@@ -47,10 +40,7 @@ function isEslintConfigSupported(tree, projectRoot = '') {
|
|
|
47
40
|
if (!eslintFile) {
|
|
48
41
|
return false;
|
|
49
42
|
}
|
|
50
|
-
return
|
|
51
|
-
eslintFile.endsWith('.config.js') ||
|
|
52
|
-
eslintFile.endsWith('.config.cjs') ||
|
|
53
|
-
eslintFile.endsWith('.config.mjs'));
|
|
43
|
+
return eslintFile.endsWith('.json') || eslintFile.endsWith('.config.js');
|
|
54
44
|
}
|
|
55
45
|
function updateRelativePathsInConfig(tree, sourcePath, destinationPath) {
|
|
56
46
|
if (sourcePath === destinationPath ||
|
|
@@ -94,17 +84,6 @@ function replaceFlatConfigPaths(config, sourceRoot, offset, destinationRoot, tre
|
|
|
94
84
|
`require('${newPath}')` +
|
|
95
85
|
newConfig.slice(match.index + match[0].length);
|
|
96
86
|
}
|
|
97
|
-
// Handle import statements
|
|
98
|
-
const importRegex = RegExp(/import\s+.*?\s+from\s+['"](.*)['"]/g);
|
|
99
|
-
while ((match = importRegex.exec(newConfig)) !== null) {
|
|
100
|
-
const oldPath = match[1];
|
|
101
|
-
const newPath = offsetFilePath(sourceRoot, oldPath, offset, tree);
|
|
102
|
-
// Replace the old path with the updated path
|
|
103
|
-
newConfig =
|
|
104
|
-
newConfig.slice(0, match.index + match[0].indexOf(oldPath)) +
|
|
105
|
-
newPath +
|
|
106
|
-
newConfig.slice(match.index + match[0].indexOf(oldPath) + oldPath.length);
|
|
107
|
-
}
|
|
108
87
|
// replace projects
|
|
109
88
|
const projectRegex = RegExp(/project:\s?\[?['"](.*)['"]\]?/g);
|
|
110
89
|
while ((match = projectRegex.exec(newConfig)) !== null) {
|
|
@@ -130,37 +109,14 @@ function offsetFilePath(projectRoot, pathToFile, offset, tree) {
|
|
|
130
109
|
}
|
|
131
110
|
return (0, devkit_1.joinPathFragments)(offset, projectRoot, pathToFile);
|
|
132
111
|
}
|
|
133
|
-
function determineEslintConfigFormat(content) {
|
|
134
|
-
const sourceFile = ts.createSourceFile('', content, ts.ScriptTarget.Latest, true);
|
|
135
|
-
// Check if there's an `export default` in the AST
|
|
136
|
-
const hasExportDefault = sourceFile.statements.some((statement) => ts.isExportAssignment(statement) && !statement.isExportEquals);
|
|
137
|
-
return hasExportDefault ? 'mjs' : 'cjs';
|
|
138
|
-
}
|
|
139
112
|
function addOverrideToLintConfig(tree, root, override, options = {
|
|
140
113
|
insertAtTheEnd: true,
|
|
141
114
|
}) {
|
|
142
115
|
const isBase = options.checkBaseConfig && findEslintFile(tree, root).includes('.base');
|
|
143
116
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
for (const file of config_file_1.BASE_ESLINT_CONFIG_FILENAMES) {
|
|
147
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, file))) {
|
|
148
|
-
fileName = (0, devkit_1.joinPathFragments)(root, file);
|
|
149
|
-
break;
|
|
150
|
-
}
|
|
151
|
-
}
|
|
152
|
-
}
|
|
153
|
-
else {
|
|
154
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
155
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
156
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
157
|
-
break;
|
|
158
|
-
}
|
|
159
|
-
}
|
|
160
|
-
}
|
|
117
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, isBase ? config_file_1.baseEsLintFlatConfigFile : (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
118
|
+
const flatOverride = (0, ast_utils_1.generateFlatOverride)(override);
|
|
161
119
|
let content = tree.read(fileName, 'utf8');
|
|
162
|
-
const format = content.includes('export default') ? 'mjs' : 'cjs';
|
|
163
|
-
const flatOverride = (0, ast_utils_1.generateFlatOverride)(override, format);
|
|
164
120
|
// Check if the provided override using legacy eslintrc properties or plugins, if so we need to add compat
|
|
165
121
|
if ((0, ast_utils_1.overrideNeedsCompat)(override)) {
|
|
166
122
|
content = (0, ast_utils_1.addFlatCompatToFlatConfig)(content);
|
|
@@ -181,28 +137,15 @@ function addOverrideToLintConfig(tree, root, override, options = {
|
|
|
181
137
|
});
|
|
182
138
|
}
|
|
183
139
|
}
|
|
184
|
-
function updateOverrideInLintConfig(tree,
|
|
185
|
-
let fileName;
|
|
186
|
-
let root = rootOrFile;
|
|
187
|
-
if (tree.exists(rootOrFile) && tree.isFile(rootOrFile)) {
|
|
188
|
-
fileName = rootOrFile;
|
|
189
|
-
root = (0, posix_1.dirname)(rootOrFile);
|
|
190
|
-
}
|
|
140
|
+
function updateOverrideInLintConfig(tree, root, lookup, update) {
|
|
191
141
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
192
|
-
|
|
193
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
194
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
195
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
196
|
-
break;
|
|
197
|
-
}
|
|
198
|
-
}
|
|
199
|
-
}
|
|
142
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
200
143
|
let content = tree.read(fileName, 'utf8');
|
|
201
144
|
content = (0, ast_utils_1.replaceOverride)(content, root, lookup, update);
|
|
202
145
|
tree.write(fileName, content);
|
|
203
146
|
}
|
|
204
147
|
else {
|
|
205
|
-
fileName
|
|
148
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, '.eslintrc.json');
|
|
206
149
|
if (!tree.exists(fileName)) {
|
|
207
150
|
return;
|
|
208
151
|
}
|
|
@@ -225,62 +168,32 @@ function updateOverrideInLintConfig(tree, rootOrFile, lookup, update) {
|
|
|
225
168
|
});
|
|
226
169
|
}
|
|
227
170
|
}
|
|
228
|
-
function lintConfigHasOverride(tree,
|
|
229
|
-
|
|
230
|
-
let root = rootOrFile;
|
|
231
|
-
if (tree.exists(rootOrFile) && tree.isFile(rootOrFile)) {
|
|
232
|
-
fileName = rootOrFile;
|
|
233
|
-
root = (0, posix_1.dirname)(rootOrFile);
|
|
234
|
-
}
|
|
235
|
-
if (!fileName && !isEslintConfigSupported(tree, root)) {
|
|
171
|
+
function lintConfigHasOverride(tree, root, lookup, checkBaseConfig = false) {
|
|
172
|
+
if (!isEslintConfigSupported(tree, root)) {
|
|
236
173
|
return false;
|
|
237
174
|
}
|
|
238
|
-
const isBase =
|
|
239
|
-
checkBaseConfig &&
|
|
240
|
-
findEslintFile(tree, root).includes('.base');
|
|
241
|
-
if (isBase) {
|
|
242
|
-
for (const file of config_file_1.BASE_ESLINT_CONFIG_FILENAMES) {
|
|
243
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, file))) {
|
|
244
|
-
fileName = (0, devkit_1.joinPathFragments)(root, file);
|
|
245
|
-
break;
|
|
246
|
-
}
|
|
247
|
-
}
|
|
248
|
-
}
|
|
175
|
+
const isBase = checkBaseConfig && findEslintFile(tree, root).includes('.base');
|
|
249
176
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
250
|
-
|
|
251
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
252
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
253
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
254
|
-
break;
|
|
255
|
-
}
|
|
256
|
-
}
|
|
257
|
-
}
|
|
177
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, isBase ? config_file_1.baseEsLintFlatConfigFile : (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
258
178
|
const content = tree.read(fileName, 'utf8');
|
|
259
179
|
return (0, ast_utils_1.hasOverride)(content, lookup);
|
|
260
180
|
}
|
|
261
181
|
else {
|
|
262
|
-
fileName
|
|
182
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, isBase ? config_file_1.baseEsLintConfigFile : '.eslintrc.json');
|
|
263
183
|
return (0, devkit_1.readJson)(tree, fileName).overrides?.some(lookup) || false;
|
|
264
184
|
}
|
|
265
185
|
}
|
|
266
186
|
function replaceOverridesInLintConfig(tree, root, overrides) {
|
|
267
187
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
268
|
-
|
|
269
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
270
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
271
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
272
|
-
break;
|
|
273
|
-
}
|
|
274
|
-
}
|
|
188
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
275
189
|
let content = tree.read(fileName, 'utf8');
|
|
276
|
-
const format = content.includes('export default') ? 'mjs' : 'cjs';
|
|
277
190
|
// Check if any of the provided overrides using legacy eslintrc properties or plugins, if so we need to add compat
|
|
278
191
|
if (overrides.some(ast_utils_1.overrideNeedsCompat)) {
|
|
279
192
|
content = (0, ast_utils_1.addFlatCompatToFlatConfig)(content);
|
|
280
193
|
}
|
|
281
194
|
content = (0, ast_utils_1.removeOverridesFromLintConfig)(content);
|
|
282
195
|
overrides.forEach((override) => {
|
|
283
|
-
const flatOverride = (0, ast_utils_1.generateFlatOverride)(override
|
|
196
|
+
const flatOverride = (0, ast_utils_1.generateFlatOverride)(override);
|
|
284
197
|
content = (0, ast_utils_1.addBlockToFlatConfigExport)(content, flatOverride);
|
|
285
198
|
});
|
|
286
199
|
tree.write(fileName, content);
|
|
@@ -296,21 +209,7 @@ function replaceOverridesInLintConfig(tree, root, overrides) {
|
|
|
296
209
|
function addExtendsToLintConfig(tree, root, plugin, insertAtTheEnd = false) {
|
|
297
210
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
298
211
|
const pluginExtends = [];
|
|
299
|
-
|
|
300
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
301
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
302
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
303
|
-
break;
|
|
304
|
-
}
|
|
305
|
-
}
|
|
306
|
-
// Check the file extension to determine the format of the config if it is .js we look for the export
|
|
307
|
-
const eslintConfigFormat = fileName.endsWith('.mjs')
|
|
308
|
-
? 'mjs'
|
|
309
|
-
: fileName.endsWith('.cjs')
|
|
310
|
-
? 'cjs'
|
|
311
|
-
: tree.read(fileName, 'utf-8').includes('module.exports')
|
|
312
|
-
? 'cjs'
|
|
313
|
-
: 'mjs';
|
|
212
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
314
213
|
let shouldImportEslintCompat = false;
|
|
315
214
|
// assume eslint version is 9 if not found, as it's what we'd be generating by default
|
|
316
215
|
const eslintVersion = (0, version_utils_1.getInstalledEslintVersion)(tree) ?? versions_1.eslint9__eslintVersion;
|
|
@@ -357,9 +256,9 @@ function addExtendsToLintConfig(tree, root, plugin, insertAtTheEnd = false) {
|
|
|
357
256
|
}
|
|
358
257
|
tree.write(fileName, content);
|
|
359
258
|
if (shouldImportEslintCompat) {
|
|
360
|
-
return (0, devkit_1.addDependenciesToPackageJson)(tree, {}, { '@eslint/compat': versions_1.eslintCompat
|
|
259
|
+
return (0, devkit_1.addDependenciesToPackageJson)(tree, {}, { '@eslint/compat': versions_1.eslintCompat }, undefined, true);
|
|
361
260
|
}
|
|
362
|
-
return (
|
|
261
|
+
return () => { };
|
|
363
262
|
}
|
|
364
263
|
else {
|
|
365
264
|
const plugins = (Array.isArray(plugin) ? plugin : [plugin]).map((p) => typeof p === 'string' ? p : p.name);
|
|
@@ -378,13 +277,7 @@ function addExtendsToLintConfig(tree, root, plugin, insertAtTheEnd = false) {
|
|
|
378
277
|
function addPredefinedConfigToFlatLintConfig(tree, root, predefinedConfigName, moduleName = 'nx', moduleImportPath = '@nx/eslint-plugin', spread = true, insertAtTheEnd = true) {
|
|
379
278
|
if (!(0, flat_config_1.useFlatConfig)(tree))
|
|
380
279
|
throw new Error('Predefined configs can only be used with flat configs');
|
|
381
|
-
|
|
382
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
383
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
384
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
385
|
-
break;
|
|
386
|
-
}
|
|
387
|
-
}
|
|
280
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
388
281
|
let content = tree.read(fileName, 'utf8');
|
|
389
282
|
content = (0, ast_utils_1.addImportToFlatConfig)(content, moduleName, moduleImportPath);
|
|
390
283
|
content = (0, ast_utils_1.addBlockToFlatConfigExport)(content, (0, ast_utils_1.generateFlatPredefinedConfig)(predefinedConfigName, moduleName, spread), { insertAtTheEnd });
|
|
@@ -393,13 +286,7 @@ function addPredefinedConfigToFlatLintConfig(tree, root, predefinedConfigName, m
|
|
|
393
286
|
function addPluginsToLintConfig(tree, root, plugin) {
|
|
394
287
|
const plugins = Array.isArray(plugin) ? plugin : [plugin];
|
|
395
288
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
396
|
-
|
|
397
|
-
for (const f of flat_config_1.eslintFlatConfigFilenames) {
|
|
398
|
-
if (tree.exists((0, devkit_1.joinPathFragments)(root, f))) {
|
|
399
|
-
fileName = (0, devkit_1.joinPathFragments)(root, f);
|
|
400
|
-
break;
|
|
401
|
-
}
|
|
402
|
-
}
|
|
289
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
403
290
|
let content = tree.read(fileName, 'utf8');
|
|
404
291
|
const mappedPlugins = [];
|
|
405
292
|
plugins.forEach((name) => {
|
|
@@ -423,33 +310,14 @@ function addPluginsToLintConfig(tree, root, plugin) {
|
|
|
423
310
|
}
|
|
424
311
|
function addIgnoresToLintConfig(tree, root, ignorePatterns) {
|
|
425
312
|
if ((0, flat_config_1.useFlatConfig)(tree)) {
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
429
|
-
|
|
430
|
-
|
|
431
|
-
}
|
|
432
|
-
}
|
|
433
|
-
if (!fileName) {
|
|
434
|
-
return;
|
|
435
|
-
}
|
|
436
|
-
let content = tree.read(fileName, 'utf8');
|
|
437
|
-
if ((0, ast_utils_1.hasFlatConfigIgnoresBlock)(content)) {
|
|
438
|
-
content = (0, ast_utils_1.addPatternsToFlatConfigIgnoresBlock)(content, ignorePatterns);
|
|
439
|
-
tree.write(fileName, content);
|
|
440
|
-
}
|
|
441
|
-
else {
|
|
442
|
-
const block = (0, ast_utils_1.generateAst)({
|
|
443
|
-
ignores: ignorePatterns.map((path) => (0, path_utils_1.mapFilePath)(path)),
|
|
444
|
-
});
|
|
445
|
-
tree.write(fileName, (0, ast_utils_1.addBlockToFlatConfigExport)(content, block));
|
|
446
|
-
}
|
|
313
|
+
const fileName = (0, devkit_1.joinPathFragments)(root, (0, flat_config_1.getRootESLintFlatConfigFilename)(tree));
|
|
314
|
+
const block = (0, ast_utils_1.generateAst)({
|
|
315
|
+
ignores: ignorePatterns.map((path) => (0, path_utils_1.mapFilePath)(path)),
|
|
316
|
+
});
|
|
317
|
+
tree.write(fileName, (0, ast_utils_1.addBlockToFlatConfigExport)(tree.read(fileName, 'utf8'), block));
|
|
447
318
|
}
|
|
448
319
|
else {
|
|
449
320
|
const fileName = (0, devkit_1.joinPathFragments)(root, '.eslintrc.json');
|
|
450
|
-
if (!tree.exists(fileName)) {
|
|
451
|
-
return;
|
|
452
|
-
}
|
|
453
321
|
(0, devkit_1.updateJson)(tree, fileName, (json) => {
|
|
454
322
|
const ignoreSet = new Set([
|
|
455
323
|
...(json.ignorePatterns ?? []),
|