@angular-eslint/schematics 15.2.2-alpha.9 → 16.0.0-alpha.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/add-eslint-to-project/index.js +13 -19
- package/dist/application/index.js +12 -23
- package/dist/application/schema.json +6 -0
- package/dist/collection.json +2 -1
- package/dist/convert-tslint-to-eslint/index.js +8 -516
- package/dist/library/index.js +12 -23
- package/dist/migrations/update-16-0-0/update-16-0-0.js +62 -0
- package/dist/migrations.json +5 -0
- package/dist/utils.js +106 -54
- package/dist/workspace/index.js +0 -1
- package/package.json +9 -8
- package/dist/convert-tslint-to-eslint/convert-to-eslint-config.js +0 -119
- package/dist/convert-tslint-to-eslint/schema.json +0 -39
- package/dist/convert-tslint-to-eslint/utils.js +0 -118
package/dist/library/index.js
CHANGED
|
@@ -11,28 +11,17 @@ var __rest = (this && this.__rest) || function (s, e) {
|
|
|
11
11
|
return t;
|
|
12
12
|
};
|
|
13
13
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
14
|
-
const
|
|
14
|
+
const devkit_1 = require("@nx/devkit");
|
|
15
|
+
const ngcli_adapter_1 = require("@nx/devkit/ngcli-adapter");
|
|
15
16
|
const utils_1 = require("../utils");
|
|
16
|
-
|
|
17
|
+
exports.default = (0, devkit_1.convertNxGenerator)(async (tree, options) => {
|
|
17
18
|
var _a;
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
}
|
|
27
|
-
function default_1(options) {
|
|
28
|
-
return (host, context) => {
|
|
29
|
-
// Remove angular-eslint specific options before passing to the Angular schematic
|
|
30
|
-
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
31
|
-
const { setParserOptionsProject } = options, angularOptions = __rest(options, ["setParserOptionsProject"]);
|
|
32
|
-
return (0, schematics_1.chain)([
|
|
33
|
-
(0, schematics_1.externalSchematic)('@schematics/angular', 'library', angularOptions),
|
|
34
|
-
eslintRelatedChanges(options),
|
|
35
|
-
])(host, context);
|
|
36
|
-
};
|
|
37
|
-
}
|
|
38
|
-
exports.default = default_1;
|
|
19
|
+
// Remove angular-eslint specific options before passing to the Angular schematic
|
|
20
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
21
|
+
const { setParserOptionsProject } = options, angularOptions = __rest(options, ["setParserOptionsProject"]);
|
|
22
|
+
const libraryGenerator = (0, ngcli_adapter_1.wrapAngularDevkitSchematic)('@schematics/angular', 'library');
|
|
23
|
+
await libraryGenerator(tree, angularOptions);
|
|
24
|
+
// Update the lint builder and config in angular.json
|
|
25
|
+
(0, utils_1.addESLintTargetToProject__NX)(tree, options.name, 'lint');
|
|
26
|
+
(0, utils_1.createESLintConfigForProject__NX)(tree, options.name, (_a = options.setParserOptionsProject) !== null && _a !== void 0 ? _a : false);
|
|
27
|
+
});
|
|
@@ -0,0 +1,62 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const schematics_1 = require("@angular-devkit/schematics");
|
|
4
|
+
const utils_1 = require("../../utils");
|
|
5
|
+
const dependencies_1 = require("../utils/dependencies");
|
|
6
|
+
const updatedTypeScriptESLintVersion = '5.59.2';
|
|
7
|
+
const updatedESLintVersion = '8.39.0';
|
|
8
|
+
function migration() {
|
|
9
|
+
return (0, schematics_1.chain)([
|
|
10
|
+
(0, dependencies_1.updateDependencies)([
|
|
11
|
+
{
|
|
12
|
+
packageName: '@typescript-eslint/eslint-plugin',
|
|
13
|
+
version: `^${updatedTypeScriptESLintVersion}`,
|
|
14
|
+
},
|
|
15
|
+
{
|
|
16
|
+
packageName: '@typescript-eslint/utils',
|
|
17
|
+
version: `^${updatedTypeScriptESLintVersion}`,
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
packageName: '@typescript-eslint/parser',
|
|
21
|
+
version: `^${updatedTypeScriptESLintVersion}`,
|
|
22
|
+
},
|
|
23
|
+
{
|
|
24
|
+
packageName: 'eslint',
|
|
25
|
+
version: `^${updatedESLintVersion}`,
|
|
26
|
+
},
|
|
27
|
+
]),
|
|
28
|
+
updateA11yRules,
|
|
29
|
+
]);
|
|
30
|
+
}
|
|
31
|
+
exports.default = migration;
|
|
32
|
+
// Remove the accessibility- prefix from all relevant template rules
|
|
33
|
+
function updateA11yRules() {
|
|
34
|
+
function modifyRules(parent) {
|
|
35
|
+
if (!parent.rules) {
|
|
36
|
+
return;
|
|
37
|
+
}
|
|
38
|
+
for (const rule of Object.keys(parent.rules)) {
|
|
39
|
+
if (rule.startsWith('@angular-eslint/template/accessibility-')) {
|
|
40
|
+
const ruleConfig = parent.rules[rule];
|
|
41
|
+
parent.rules[rule.replace('accessibility-', '')] = ruleConfig;
|
|
42
|
+
delete parent.rules[rule];
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
return (0, schematics_1.chain)([
|
|
47
|
+
(0, utils_1.visitNotIgnoredFiles)((filePath) => {
|
|
48
|
+
if (!filePath.endsWith('.eslintrc.json')) {
|
|
49
|
+
return;
|
|
50
|
+
}
|
|
51
|
+
return (0, utils_1.updateJsonInTree)(filePath.toString(), (json) => {
|
|
52
|
+
if (json.overrides) {
|
|
53
|
+
for (const override of json.overrides) {
|
|
54
|
+
modifyRules(override);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
modifyRules(json);
|
|
58
|
+
return json;
|
|
59
|
+
});
|
|
60
|
+
}),
|
|
61
|
+
]);
|
|
62
|
+
}
|
package/dist/migrations.json
CHANGED
|
@@ -35,6 +35,11 @@
|
|
|
35
35
|
"version": "15.0.0-alpha.1",
|
|
36
36
|
"description": "Updates @angular-eslint to v15",
|
|
37
37
|
"factory": "./migrations/update-15-0-0/update-15-0-0"
|
|
38
|
+
},
|
|
39
|
+
"update-16-0-0": {
|
|
40
|
+
"version": "16.0.0-alpha.0",
|
|
41
|
+
"description": "Updates @angular-eslint to v16",
|
|
42
|
+
"factory": "./migrations/update-16-0-0/update-16-0-0"
|
|
38
43
|
}
|
|
39
44
|
}
|
|
40
45
|
}
|
package/dist/utils.js
CHANGED
|
@@ -3,11 +3,13 @@ var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
|
3
3
|
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
4
|
};
|
|
5
5
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
-
exports.updateSchematicDefaults = exports.updateSchematicCollections = exports.
|
|
6
|
+
exports.updateSchematicDefaults = exports.updateSchematicCollections = exports.determineTargetProjectName = exports.determineTargetProjectName__NX = exports.sortObjectByKeys = exports.createESLintConfigForProject = exports.createESLintConfigForProject__NX = exports.createRootESLintConfig = exports.visitNotIgnoredFiles = exports.addESLintTargetToProject = exports.addESLintTargetToProject__NX = exports.getTargetsConfigFromProject = exports.updateJsonInTree = exports.readJsonInTree = void 0;
|
|
7
7
|
const core_1 = require("@angular-devkit/core");
|
|
8
8
|
const schematics_1 = require("@angular-devkit/schematics");
|
|
9
|
+
const devkit_1 = require("@nx/devkit");
|
|
9
10
|
const ignore_1 = __importDefault(require("ignore"));
|
|
10
11
|
const strip_json_comments_1 = __importDefault(require("strip-json-comments"));
|
|
12
|
+
const DEFAULT_PREFIX = 'app';
|
|
11
13
|
/**
|
|
12
14
|
* This method is specifically for reading JSON files in a Tree
|
|
13
15
|
* @param host The host tree
|
|
@@ -51,7 +53,6 @@ function getWorkspacePath(host) {
|
|
|
51
53
|
const possibleFiles = ['/workspace.json', '/angular.json', '/.angular.json'];
|
|
52
54
|
return possibleFiles.filter((path) => host.exists(path))[0];
|
|
53
55
|
}
|
|
54
|
-
exports.getWorkspacePath = getWorkspacePath;
|
|
55
56
|
function getTargetsConfigFromProject(projectConfig) {
|
|
56
57
|
if (!projectConfig) {
|
|
57
58
|
return null;
|
|
@@ -66,42 +67,6 @@ function getTargetsConfigFromProject(projectConfig) {
|
|
|
66
67
|
return null;
|
|
67
68
|
}
|
|
68
69
|
exports.getTargetsConfigFromProject = getTargetsConfigFromProject;
|
|
69
|
-
function isTSLintUsedInWorkspace(tree) {
|
|
70
|
-
const workspaceJson = readJsonInTree(tree, getWorkspacePath(tree));
|
|
71
|
-
if (!workspaceJson) {
|
|
72
|
-
return false;
|
|
73
|
-
}
|
|
74
|
-
for (const [, projectConfig] of Object.entries(workspaceJson.projects)) {
|
|
75
|
-
const targetsConfig = getTargetsConfigFromProject(projectConfig);
|
|
76
|
-
if (!targetsConfig) {
|
|
77
|
-
continue;
|
|
78
|
-
}
|
|
79
|
-
for (const [, targetConfig] of Object.entries(targetsConfig)) {
|
|
80
|
-
if (!targetConfig) {
|
|
81
|
-
continue;
|
|
82
|
-
}
|
|
83
|
-
if (targetConfig.builder === '@angular-devkit/build-angular:tslint') {
|
|
84
|
-
// Workspace is still using TSLint, exit early
|
|
85
|
-
return true;
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
}
|
|
89
|
-
// If we got this far the user has no remaining TSLint usage
|
|
90
|
-
return false;
|
|
91
|
-
}
|
|
92
|
-
exports.isTSLintUsedInWorkspace = isTSLintUsedInWorkspace;
|
|
93
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
94
|
-
function getProjectConfig(host, name) {
|
|
95
|
-
const workspaceJson = readJsonInTree(host, getWorkspacePath(host));
|
|
96
|
-
const projectConfig = workspaceJson.projects[name];
|
|
97
|
-
if (!projectConfig) {
|
|
98
|
-
throw new Error(`Cannot find project '${name}'`);
|
|
99
|
-
}
|
|
100
|
-
else {
|
|
101
|
-
return projectConfig;
|
|
102
|
-
}
|
|
103
|
-
}
|
|
104
|
-
exports.getProjectConfig = getProjectConfig;
|
|
105
70
|
function offsetFromRoot(fullPathToSourceDir) {
|
|
106
71
|
const parts = (0, core_1.normalize)(fullPathToSourceDir).split('/');
|
|
107
72
|
let offset = '';
|
|
@@ -110,7 +75,6 @@ function offsetFromRoot(fullPathToSourceDir) {
|
|
|
110
75
|
}
|
|
111
76
|
return offset;
|
|
112
77
|
}
|
|
113
|
-
exports.offsetFromRoot = offsetFromRoot;
|
|
114
78
|
function serializeJson(json) {
|
|
115
79
|
return `${JSON.stringify(json, null, 2)}\n`;
|
|
116
80
|
}
|
|
@@ -122,7 +86,39 @@ function updateWorkspaceInTree(callback) {
|
|
|
122
86
|
return host;
|
|
123
87
|
};
|
|
124
88
|
}
|
|
125
|
-
|
|
89
|
+
function readProjectConfiguration(tree, projectName) {
|
|
90
|
+
const angularJSON = (0, devkit_1.readJson)(tree, 'angular.json');
|
|
91
|
+
return angularJSON.projects[projectName];
|
|
92
|
+
}
|
|
93
|
+
function updateProjectConfiguration(tree, projectName, projectConfig) {
|
|
94
|
+
const angularJSON = (0, devkit_1.readJson)(tree, 'angular.json');
|
|
95
|
+
angularJSON.projects[projectName] = projectConfig;
|
|
96
|
+
(0, devkit_1.writeJson)(tree, 'angular.json', angularJSON);
|
|
97
|
+
}
|
|
98
|
+
function addESLintTargetToProject__NX(tree, projectName, targetName) {
|
|
99
|
+
const existingProjectConfig = readProjectConfiguration(tree, projectName);
|
|
100
|
+
let lintFilePatternsRoot = '';
|
|
101
|
+
// Default Angular CLI project at the root of the workspace
|
|
102
|
+
if (existingProjectConfig.root === '') {
|
|
103
|
+
lintFilePatternsRoot = existingProjectConfig.sourceRoot || 'src';
|
|
104
|
+
}
|
|
105
|
+
else {
|
|
106
|
+
lintFilePatternsRoot = existingProjectConfig.root;
|
|
107
|
+
}
|
|
108
|
+
const eslintTargetConfig = {
|
|
109
|
+
builder: '@angular-eslint/builder:lint',
|
|
110
|
+
options: {
|
|
111
|
+
lintFilePatterns: [
|
|
112
|
+
`${lintFilePatternsRoot}/**/*.ts`,
|
|
113
|
+
`${lintFilePatternsRoot}/**/*.html`,
|
|
114
|
+
],
|
|
115
|
+
},
|
|
116
|
+
};
|
|
117
|
+
existingProjectConfig.architect = existingProjectConfig.architect || {};
|
|
118
|
+
existingProjectConfig.architect[targetName] = eslintTargetConfig;
|
|
119
|
+
updateProjectConfiguration(tree, projectName, existingProjectConfig);
|
|
120
|
+
}
|
|
121
|
+
exports.addESLintTargetToProject__NX = addESLintTargetToProject__NX;
|
|
126
122
|
function addESLintTargetToProject(projectName, targetName) {
|
|
127
123
|
return updateWorkspaceInTree((workspaceJson) => {
|
|
128
124
|
const existingProjectConfig = workspaceJson.projects[projectName];
|
|
@@ -195,7 +191,6 @@ function setESLintProjectBasedOnProjectType(projectRoot, projectType, hasE2e) {
|
|
|
195
191
|
}
|
|
196
192
|
return project;
|
|
197
193
|
}
|
|
198
|
-
exports.setESLintProjectBasedOnProjectType = setESLintProjectBasedOnProjectType;
|
|
199
194
|
// eslint-disable-next-line @typescript-eslint/explicit-module-boundary-types
|
|
200
195
|
function createRootESLintConfig(prefix) {
|
|
201
196
|
let codeRules;
|
|
@@ -230,7 +225,10 @@ function createRootESLintConfig(prefix) {
|
|
|
230
225
|
},
|
|
231
226
|
{
|
|
232
227
|
files: ['*.html'],
|
|
233
|
-
extends: [
|
|
228
|
+
extends: [
|
|
229
|
+
'plugin:@angular-eslint/template/recommended',
|
|
230
|
+
'plugin:@angular-eslint/template/accessibility',
|
|
231
|
+
],
|
|
234
232
|
rules: {},
|
|
235
233
|
},
|
|
236
234
|
],
|
|
@@ -265,6 +263,53 @@ function createProjectESLintConfig(projectRoot, projectType, prefix, setParserOp
|
|
|
265
263
|
],
|
|
266
264
|
};
|
|
267
265
|
}
|
|
266
|
+
function createProjectESLintConfig__NX(projectRoot, projectType, prefix, setParserOptionsProject, hasE2e) {
|
|
267
|
+
return {
|
|
268
|
+
extends: `${(0, devkit_1.offsetFromRoot)(projectRoot)}.eslintrc.json`,
|
|
269
|
+
ignorePatterns: ['!**/*'],
|
|
270
|
+
overrides: [
|
|
271
|
+
Object.assign(Object.assign({ files: ['*.ts'] }, (setParserOptionsProject
|
|
272
|
+
? {
|
|
273
|
+
parserOptions: {
|
|
274
|
+
project: setESLintProjectBasedOnProjectType(projectRoot, projectType, hasE2e),
|
|
275
|
+
},
|
|
276
|
+
}
|
|
277
|
+
: null)), { rules: {
|
|
278
|
+
'@angular-eslint/directive-selector': [
|
|
279
|
+
'error',
|
|
280
|
+
{ type: 'attribute', prefix, style: 'camelCase' },
|
|
281
|
+
],
|
|
282
|
+
'@angular-eslint/component-selector': [
|
|
283
|
+
'error',
|
|
284
|
+
{ type: 'element', prefix, style: 'kebab-case' },
|
|
285
|
+
],
|
|
286
|
+
} }),
|
|
287
|
+
{
|
|
288
|
+
files: ['*.html'],
|
|
289
|
+
rules: {},
|
|
290
|
+
},
|
|
291
|
+
],
|
|
292
|
+
};
|
|
293
|
+
}
|
|
294
|
+
function createESLintConfigForProject__NX(tree, projectName, setParserOptionsProject) {
|
|
295
|
+
const existingProjectConfig = readProjectConfiguration(tree, projectName);
|
|
296
|
+
const targets = existingProjectConfig.architect || existingProjectConfig.targets;
|
|
297
|
+
const { root: projectRoot, projectType, prefix } = existingProjectConfig;
|
|
298
|
+
const hasE2e = !!(targets === null || targets === void 0 ? void 0 : targets.e2e);
|
|
299
|
+
/**
|
|
300
|
+
* If the root is an empty string it must be the initial project created at the
|
|
301
|
+
* root by the Angular CLI's workspace schematic
|
|
302
|
+
*/
|
|
303
|
+
if (projectRoot === '') {
|
|
304
|
+
return createRootESLintConfigFile__NX(tree, prefix || DEFAULT_PREFIX);
|
|
305
|
+
}
|
|
306
|
+
// If, for whatever reason, the root .eslintrc.json doesn't exist yet, create it
|
|
307
|
+
if (!tree.exists('.eslintrc.json')) {
|
|
308
|
+
createRootESLintConfigFile__NX(tree, prefix || DEFAULT_PREFIX);
|
|
309
|
+
}
|
|
310
|
+
(0, devkit_1.writeJson)(tree, (0, core_1.join)((0, core_1.normalize)(projectRoot), '.eslintrc.json'), createProjectESLintConfig__NX(projectRoot, projectType || 'library', prefix || DEFAULT_PREFIX, setParserOptionsProject, hasE2e));
|
|
311
|
+
}
|
|
312
|
+
exports.createESLintConfigForProject__NX = createESLintConfigForProject__NX;
|
|
268
313
|
function createESLintConfigForProject(projectName, setParserOptionsProject) {
|
|
269
314
|
return (tree) => {
|
|
270
315
|
const angularJSON = readJsonInTree(tree, 'angular.json');
|
|
@@ -287,17 +332,6 @@ function createESLintConfigForProject(projectName, setParserOptionsProject) {
|
|
|
287
332
|
};
|
|
288
333
|
}
|
|
289
334
|
exports.createESLintConfigForProject = createESLintConfigForProject;
|
|
290
|
-
function removeTSLintJSONForProject(projectName) {
|
|
291
|
-
return (tree) => {
|
|
292
|
-
const angularJSON = readJsonInTree(tree, 'angular.json');
|
|
293
|
-
const { root: projectRoot } = angularJSON.projects[projectName];
|
|
294
|
-
const tslintJsonPath = (0, core_1.join)((0, core_1.normalize)(projectRoot || '/'), 'tslint.json');
|
|
295
|
-
if (tree.exists(tslintJsonPath)) {
|
|
296
|
-
tree.delete(tslintJsonPath);
|
|
297
|
-
}
|
|
298
|
-
};
|
|
299
|
-
}
|
|
300
|
-
exports.removeTSLintJSONForProject = removeTSLintJSONForProject;
|
|
301
335
|
function createRootESLintConfigFile(projectName) {
|
|
302
336
|
return (tree) => {
|
|
303
337
|
var _a;
|
|
@@ -310,6 +344,9 @@ function createRootESLintConfigFile(projectName) {
|
|
|
310
344
|
return updateJsonInTree('.eslintrc.json', () => createRootESLintConfig(lintPrefix));
|
|
311
345
|
};
|
|
312
346
|
}
|
|
347
|
+
function createRootESLintConfigFile__NX(tree, prefix) {
|
|
348
|
+
return (0, devkit_1.writeJson)(tree, '.eslintrc.json', createRootESLintConfig(prefix));
|
|
349
|
+
}
|
|
313
350
|
function sortObjectByKeys(obj) {
|
|
314
351
|
return Object.keys(obj)
|
|
315
352
|
.sort()
|
|
@@ -318,6 +355,22 @@ function sortObjectByKeys(obj) {
|
|
|
318
355
|
}, {});
|
|
319
356
|
}
|
|
320
357
|
exports.sortObjectByKeys = sortObjectByKeys;
|
|
358
|
+
/**
|
|
359
|
+
* To make certain schematic usage conversion more ergonomic, if the user does not specify a project
|
|
360
|
+
* and only has a single project in their angular.json we will just go ahead and use that one.
|
|
361
|
+
*/
|
|
362
|
+
function determineTargetProjectName__NX(tree, maybeProject) {
|
|
363
|
+
if (maybeProject) {
|
|
364
|
+
return maybeProject;
|
|
365
|
+
}
|
|
366
|
+
const workspaceJson = (0, devkit_1.readJson)(tree, 'angular.json');
|
|
367
|
+
const projects = Object.keys(workspaceJson.projects);
|
|
368
|
+
if (projects.length === 1) {
|
|
369
|
+
return projects[0];
|
|
370
|
+
}
|
|
371
|
+
return null;
|
|
372
|
+
}
|
|
373
|
+
exports.determineTargetProjectName__NX = determineTargetProjectName__NX;
|
|
321
374
|
/**
|
|
322
375
|
* To make certain schematic usage conversion more ergonomic, if the user does not specify a project
|
|
323
376
|
* and only has a single project in their angular.json we will just go ahead and use that one.
|
|
@@ -344,7 +397,6 @@ angularJSON, projectName) {
|
|
|
344
397
|
var _a;
|
|
345
398
|
return !!((_a = getTargetsConfigFromProject(angularJSON.projects[projectName])) === null || _a === void 0 ? void 0 : _a.e2e);
|
|
346
399
|
}
|
|
347
|
-
exports.determineTargetProjectHasE2E = determineTargetProjectHasE2E;
|
|
348
400
|
/**
|
|
349
401
|
* See `schematicCollections` docs here:
|
|
350
402
|
* https://github.com/angular/angular-cli/blob/8431b3f0769b5f95b9e13807a09293d820c4b017/docs/specifications/schematic-collections-config.md
|
package/dist/workspace/index.js
CHANGED
|
@@ -13,7 +13,6 @@ This worked for simple scenarios but it was not possible to support all the opti
|
|
|
13
13
|
Instead, simply:
|
|
14
14
|
- Run \`ng new\` (without \`--collection\`) and create your Angular CLI workspace with whatever options you prefer.
|
|
15
15
|
- Change directory to your new workspace and run \`ng add @angular-eslint/schematics\` to add all relevant ESLint packages.
|
|
16
|
-
- Run \`ng g @angular-eslint/schematics:convert-tslint-to-eslint --remove-tslint-if-no-more-tslint-targets --ignore-existing-tslint-config\` to automatically convert your new project from TSLint to ESLint.
|
|
17
16
|
`.trim());
|
|
18
17
|
};
|
|
19
18
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@angular-eslint/schematics",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "16.0.0-alpha.1",
|
|
4
4
|
"description": "Angular Schematics for angular-eslint",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"main": "dist/index.js",
|
|
@@ -33,20 +33,21 @@
|
|
|
33
33
|
"save": "devDependencies"
|
|
34
34
|
},
|
|
35
35
|
"dependencies": {
|
|
36
|
-
"@angular-eslint/eslint-plugin": "
|
|
37
|
-
"@angular-eslint/eslint-plugin-template": "
|
|
36
|
+
"@angular-eslint/eslint-plugin": "16.0.0-alpha.1",
|
|
37
|
+
"@angular-eslint/eslint-plugin-template": "16.0.0-alpha.1",
|
|
38
|
+
"@nx/devkit": "16.0.2",
|
|
38
39
|
"ignore": "5.2.4",
|
|
40
|
+
"nx": "16.0.2",
|
|
39
41
|
"strip-json-comments": "3.1.1",
|
|
40
42
|
"tmp": "0.2.1"
|
|
41
43
|
},
|
|
42
44
|
"devDependencies": {
|
|
43
45
|
"@types/tmp": "0.2.3",
|
|
44
|
-
"@typescript-eslint/utils": "5.
|
|
45
|
-
"eslint": "8.
|
|
46
|
-
"tslint-to-eslint-config": "2.4.0"
|
|
46
|
+
"@typescript-eslint/utils": "5.59.2",
|
|
47
|
+
"eslint": "8.39.0"
|
|
47
48
|
},
|
|
48
49
|
"peerDependencies": {
|
|
49
|
-
"@angular/cli": ">=
|
|
50
|
+
"@angular/cli": ">= 16.0.0 < 17.0.0 || ^16.0.0-rc.1"
|
|
50
51
|
},
|
|
51
|
-
"gitHead": "
|
|
52
|
+
"gitHead": "ffcbae10749bc12760a9d442d4293179c6c19042"
|
|
52
53
|
}
|
|
@@ -1,119 +0,0 @@
|
|
|
1
|
-
"use strict";
|
|
2
|
-
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.convertTSLintDisableCommentsForProject = exports.createConvertToESLintConfig = void 0;
|
|
4
|
-
const core_1 = require("@angular-devkit/core");
|
|
5
|
-
const child_process_1 = require("child_process");
|
|
6
|
-
const tmp_1 = require("tmp");
|
|
7
|
-
const utils_1 = require("../utils");
|
|
8
|
-
const tslintToEslintConfigVersion =
|
|
9
|
-
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
10
|
-
require('../../package.json').devDependencies['tslint-to-eslint-config'];
|
|
11
|
-
let tslintToEslintConfigLibrary;
|
|
12
|
-
function getTslintToEslintConfigLibrary(context) {
|
|
13
|
-
if (tslintToEslintConfigLibrary) {
|
|
14
|
-
return tslintToEslintConfigLibrary;
|
|
15
|
-
}
|
|
16
|
-
try {
|
|
17
|
-
// This is usually not available at runtime but makes it easier to work with in our tests
|
|
18
|
-
return require('tslint-to-eslint-config');
|
|
19
|
-
// eslint-disable-next-line no-empty
|
|
20
|
-
}
|
|
21
|
-
catch (e) { }
|
|
22
|
-
context.logger.info('\nINFO: We are now installing the "tslint-to-eslint-config" package into a tmp directory to aid with the conversion');
|
|
23
|
-
context.logger.info('\nThis may take a minute or two...\n');
|
|
24
|
-
/**
|
|
25
|
-
* In order to avoid all users of angular-eslint needing to have tslint-to-eslint-config (and therefore tslint)
|
|
26
|
-
* in their node_modules, we dynamically install and uninstall the library as part of the conversion
|
|
27
|
-
* process.
|
|
28
|
-
*/
|
|
29
|
-
const tempDir = (0, tmp_1.dirSync)().name;
|
|
30
|
-
(0, child_process_1.execSync)(`npm i -D tslint-to-eslint-config@${tslintToEslintConfigVersion}`, {
|
|
31
|
-
cwd: tempDir,
|
|
32
|
-
stdio: 'ignore',
|
|
33
|
-
});
|
|
34
|
-
tslintToEslintConfigLibrary = require(require.resolve('tslint-to-eslint-config', {
|
|
35
|
-
paths: [tempDir],
|
|
36
|
-
}));
|
|
37
|
-
return tslintToEslintConfigLibrary;
|
|
38
|
-
}
|
|
39
|
-
function createConvertToESLintConfig(context) {
|
|
40
|
-
return async function convertToESLintConfig(pathToTslintJson, tslintJson) {
|
|
41
|
-
const { findReportedConfiguration, createESLintConfiguration, joinConfigConversionResults, } = getTslintToEslintConfigLibrary(context);
|
|
42
|
-
const reportedConfiguration = await findReportedConfiguration('npx tslint --print-config', pathToTslintJson);
|
|
43
|
-
if (reportedConfiguration instanceof Error) {
|
|
44
|
-
if (reportedConfiguration.message.includes('unknown option `--print-config')) {
|
|
45
|
-
throw new Error('\nError: TSLint v5.18 required in order to run this schematic. Please update your version and try again.\n');
|
|
46
|
-
}
|
|
47
|
-
/**
|
|
48
|
-
* Make a print-config issue easier to understand for the end user.
|
|
49
|
-
* This error could occur if, for example, the user does not have a TSLint plugin installed correctly that they
|
|
50
|
-
* reference in their config.
|
|
51
|
-
*/
|
|
52
|
-
const printConfigFailureMessageStart = 'Command failed: npx tslint --print-config "tslint.json"';
|
|
53
|
-
if (reportedConfiguration.message.startsWith(printConfigFailureMessageStart)) {
|
|
54
|
-
throw new Error(`\nThere was a critical error when trying to inspect your tslint.json: \n${reportedConfiguration.message.replace(printConfigFailureMessageStart, '')}`);
|
|
55
|
-
}
|
|
56
|
-
throw new Error(`Unexpected error: ${reportedConfiguration.message}`);
|
|
57
|
-
}
|
|
58
|
-
const originalConfigurations = {
|
|
59
|
-
tslint: {
|
|
60
|
-
full: reportedConfiguration,
|
|
61
|
-
raw: tslintJson,
|
|
62
|
-
},
|
|
63
|
-
};
|
|
64
|
-
const summarizedConfiguration = await createESLintConfiguration(originalConfigurations);
|
|
65
|
-
const expectedESLintPlugins = [
|
|
66
|
-
// These are added to support the ng-cli-compat configs
|
|
67
|
-
'eslint-plugin-jsdoc',
|
|
68
|
-
'eslint-plugin-prefer-arrow',
|
|
69
|
-
'eslint-plugin-import',
|
|
70
|
-
// These are already covered by our recommended config, and are installed by the `ng add` schematic
|
|
71
|
-
'@angular-eslint/eslint-plugin',
|
|
72
|
-
'@angular-eslint/eslint-plugin-template',
|
|
73
|
-
];
|
|
74
|
-
const convertedESLintConfig = joinConfigConversionResults(summarizedConfiguration, originalConfigurations);
|
|
75
|
-
return {
|
|
76
|
-
convertedESLintConfig,
|
|
77
|
-
unconvertedTSLintRules: summarizedConfiguration.missing,
|
|
78
|
-
ensureESLintPlugins: Array.from(summarizedConfiguration.plugins).filter((pluginName) => !expectedESLintPlugins.includes(pluginName)),
|
|
79
|
-
};
|
|
80
|
-
};
|
|
81
|
-
}
|
|
82
|
-
exports.createConvertToESLintConfig = createConvertToESLintConfig;
|
|
83
|
-
function likelyContainsTSLintComment(fileContent) {
|
|
84
|
-
return fileContent.includes('tslint:');
|
|
85
|
-
}
|
|
86
|
-
function convertTSLintDisableCommentsForProject(projectName) {
|
|
87
|
-
return (tree, context) => {
|
|
88
|
-
/**
|
|
89
|
-
* We need to avoid a direct dependency on tslint-to-eslint-config
|
|
90
|
-
* and ensure we are only resolving the dependency from the user's
|
|
91
|
-
* node_modules on demand (it will be installed as part of the
|
|
92
|
-
* conversion schematic).
|
|
93
|
-
*/
|
|
94
|
-
const { convertFileComments } = getTslintToEslintConfigLibrary(context);
|
|
95
|
-
const workspaceJson = (0, utils_1.readJsonInTree)(tree, 'angular.json');
|
|
96
|
-
const existingProjectConfig = workspaceJson.projects[projectName];
|
|
97
|
-
let pathRoot = '';
|
|
98
|
-
// Default Angular CLI project at the root of the workspace
|
|
99
|
-
if (existingProjectConfig.root === '') {
|
|
100
|
-
pathRoot = existingProjectConfig.sourceRoot || 'src';
|
|
101
|
-
}
|
|
102
|
-
else {
|
|
103
|
-
pathRoot = existingProjectConfig.root;
|
|
104
|
-
}
|
|
105
|
-
return (0, utils_1.visitNotIgnoredFiles)((filePath, host) => {
|
|
106
|
-
if (!filePath.endsWith('.ts')) {
|
|
107
|
-
return;
|
|
108
|
-
}
|
|
109
|
-
const fileContent = host.read(filePath).toString('utf-8');
|
|
110
|
-
// Avoid updating files if we don't have to
|
|
111
|
-
if (!likelyContainsTSLintComment(fileContent)) {
|
|
112
|
-
return;
|
|
113
|
-
}
|
|
114
|
-
const updatedFileContent = convertFileComments({ fileContent, filePath });
|
|
115
|
-
host.overwrite(filePath, updatedFileContent);
|
|
116
|
-
}, (0, core_1.normalize)(pathRoot));
|
|
117
|
-
};
|
|
118
|
-
}
|
|
119
|
-
exports.convertTSLintDisableCommentsForProject = convertTSLintDisableCommentsForProject;
|
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"$schema": "http://json-schema.org/schema",
|
|
3
|
-
"$id": "convert-tslint-to-eslint",
|
|
4
|
-
"title": "Convert an Angular CLI project from TSLint to ESLint",
|
|
5
|
-
"examples": [
|
|
6
|
-
{
|
|
7
|
-
"command": "g convert-tslint-to-eslint myapp",
|
|
8
|
-
"description": "Convert the Angular CLI project `myapp` from TSLint to ESLint"
|
|
9
|
-
}
|
|
10
|
-
],
|
|
11
|
-
"type": "object",
|
|
12
|
-
"properties": {
|
|
13
|
-
"project": {
|
|
14
|
-
"description": "The name of the project to convert.",
|
|
15
|
-
"type": "string",
|
|
16
|
-
"$default": {
|
|
17
|
-
"$source": "argv",
|
|
18
|
-
"index": 0
|
|
19
|
-
}
|
|
20
|
-
},
|
|
21
|
-
"convertIndentationRules": {
|
|
22
|
-
"description": "Whether or not rules relating purely to indentation (code formatting) should be converted. It is strongly encouraged to switch to https://prettier.io instead.",
|
|
23
|
-
"type": "boolean",
|
|
24
|
-
"default": false
|
|
25
|
-
},
|
|
26
|
-
"removeTslintIfNoMoreTslintTargets": {
|
|
27
|
-
"type": "boolean",
|
|
28
|
-
"description": "If this conversion leaves no more TSLint usage in the workspace, it will remove TSLint and related dependencies and configuration",
|
|
29
|
-
"default": true,
|
|
30
|
-
"x-prompt": "Would you like to remove TSLint and its related config if there are no TSLint projects remaining after this conversion?"
|
|
31
|
-
},
|
|
32
|
-
"ignoreExistingTslintConfig": {
|
|
33
|
-
"type": "boolean",
|
|
34
|
-
"description": "If true we will not use existing TSLint config as a reference, we will just reset the project with the latest recommended ESLint config",
|
|
35
|
-
"default": false,
|
|
36
|
-
"x-prompt": "Would you like to ignore the existing TSLint config? Recommended if the TSLint config has not been altered much as it makes the new ESLint config cleaner."
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
}
|