eslint-plugin-unicorn 22.0.0 → 23.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/index.js +4 -0
- package/package.json +20 -9
- package/readme.md +6 -0
- package/rules/better-regex.js +8 -4
- package/rules/catch-error-name.js +6 -5
- package/rules/consistent-function-scoping.js +13 -13
- package/rules/custom-error-definition.js +4 -3
- package/rules/error-message.js +11 -3
- package/rules/escape-case.js +8 -3
- package/rules/expiring-todo-comments.js +24 -23
- package/rules/explicit-length-check.js +20 -10
- package/rules/filename-case.js +6 -4
- package/rules/import-index.js +8 -2
- package/rules/import-style.js +6 -5
- package/rules/no-abusive-eslint-disable.js +10 -2
- package/rules/no-array-instanceof.js +7 -3
- package/rules/no-console-spaces.js +19 -17
- package/rules/no-fn-reference-in-iterator.js +7 -6
- package/rules/no-for-loop.js +10 -6
- package/rules/no-hex-escape.js +7 -1
- package/rules/no-keyword-prefix.js +4 -3
- package/rules/no-nested-ternary.js +24 -27
- package/rules/no-new-buffer.js +9 -2
- package/rules/no-null.js +6 -5
- package/rules/no-object-as-default-parameter.js +4 -3
- package/rules/no-process-exit.js +8 -3
- package/rules/no-reduce.js +5 -4
- package/rules/no-unreadable-array-destructuring.js +8 -3
- package/rules/no-unsafe-regex.js +8 -4
- package/rules/no-unused-properties.js +8 -2
- package/rules/no-useless-undefined.js +4 -3
- package/rules/no-zero-fractions.js +8 -3
- package/rules/number-literal-case.js +14 -12
- package/rules/numeric-separators-style.js +153 -0
- package/rules/prefer-add-event-listener.js +12 -5
- package/rules/prefer-array-find.js +11 -11
- package/rules/prefer-dataset.js +8 -2
- package/rules/prefer-event-key.js +9 -2
- package/rules/prefer-flat-map.js +12 -11
- package/rules/prefer-includes.js +7 -3
- package/rules/prefer-math-trunc.js +92 -0
- package/rules/prefer-negative-index.js +9 -2
- package/rules/prefer-node-append.js +7 -3
- package/rules/prefer-node-remove.js +8 -7
- package/rules/prefer-number-properties.js +12 -6
- package/rules/prefer-optional-catch-binding.js +5 -4
- package/rules/prefer-query-selector.js +12 -2
- package/rules/prefer-reflect-apply.js +10 -4
- package/rules/prefer-replace-all.js +8 -4
- package/rules/prefer-set-has.js +11 -9
- package/rules/prefer-spread.js +8 -2
- package/rules/prefer-starts-ends-with.js +5 -4
- package/rules/prefer-string-slice.js +11 -3
- package/rules/prefer-ternary.js +269 -0
- package/rules/prefer-text-content.js +7 -3
- package/rules/prefer-type-error.js +8 -2
- package/rules/prevent-abbreviations.js +15 -0
- package/rules/string-content.js +7 -6
- package/rules/throw-new-error.js +5 -3
- package/rules/utils/cartesian-product-samples.js +2 -2
- package/rules/utils/method-selector.js +1 -1
package/index.js
CHANGED
|
@@ -49,6 +49,8 @@ module.exports = {
|
|
|
49
49
|
'unicorn/no-useless-undefined': 'error',
|
|
50
50
|
'unicorn/no-zero-fractions': 'error',
|
|
51
51
|
'unicorn/number-literal-case': 'error',
|
|
52
|
+
// TODO: Enable this by default when it's shipping in a Node.js LTS version.
|
|
53
|
+
'unicorn/numeric-separators-style': 'off',
|
|
52
54
|
'unicorn/prefer-add-event-listener': 'error',
|
|
53
55
|
'unicorn/prefer-array-find': 'error',
|
|
54
56
|
'unicorn/prefer-dataset': 'error',
|
|
@@ -56,6 +58,7 @@ module.exports = {
|
|
|
56
58
|
// TODO: Enable this by default when targeting Node.js 12.
|
|
57
59
|
'unicorn/prefer-flat-map': 'off',
|
|
58
60
|
'unicorn/prefer-includes': 'error',
|
|
61
|
+
'unicorn/prefer-math-trunc': 'error',
|
|
59
62
|
'unicorn/prefer-modern-dom-apis': 'error',
|
|
60
63
|
'unicorn/prefer-negative-index': 'error',
|
|
61
64
|
'unicorn/prefer-node-append': 'error',
|
|
@@ -70,6 +73,7 @@ module.exports = {
|
|
|
70
73
|
'unicorn/prefer-spread': 'error',
|
|
71
74
|
'unicorn/prefer-starts-ends-with': 'error',
|
|
72
75
|
'unicorn/prefer-string-slice': 'error',
|
|
76
|
+
'unicorn/prefer-ternary': 'error',
|
|
73
77
|
'unicorn/prefer-text-content': 'error',
|
|
74
78
|
'unicorn/prefer-trim-start-end': 'error',
|
|
75
79
|
'unicorn/prefer-type-error': 'error',
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "eslint-plugin-unicorn",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "23.0.0",
|
|
4
4
|
"description": "Various awesome ESLint rules",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"repository": "sindresorhus/eslint-plugin-unicorn",
|
|
@@ -51,25 +51,25 @@
|
|
|
51
51
|
"@ava/babel": "^1.0.1",
|
|
52
52
|
"@babel/code-frame": "7.10.4",
|
|
53
53
|
"@lubien/fixture-beta-package": "^1.0.0-beta.1",
|
|
54
|
-
"@typescript-eslint/parser": "^4.1
|
|
55
|
-
"ava": "^3.
|
|
54
|
+
"@typescript-eslint/parser": "^4.4.1",
|
|
55
|
+
"ava": "^3.13.0",
|
|
56
56
|
"babel-eslint": "^10.1.0",
|
|
57
57
|
"chalk": "^4.1.0",
|
|
58
|
-
"eslint": "^7.
|
|
58
|
+
"eslint": "^7.11.0",
|
|
59
59
|
"eslint-ava-rule-tester": "^4.0.0",
|
|
60
60
|
"eslint-plugin-eslint-plugin": "^2.3.0",
|
|
61
61
|
"execa": "^4.0.3",
|
|
62
62
|
"listr": "^0.14.3",
|
|
63
|
-
"mem": "
|
|
63
|
+
"mem": "8.0.0",
|
|
64
64
|
"nyc": "^15.1.0",
|
|
65
65
|
"outdent": "^0.7.1",
|
|
66
66
|
"pify": "^5.0.0",
|
|
67
|
-
"typescript": "^4.0.
|
|
68
|
-
"vue-eslint-parser": "^7.1.
|
|
67
|
+
"typescript": "^4.0.3",
|
|
68
|
+
"vue-eslint-parser": "^7.1.1",
|
|
69
69
|
"xo": "^0.33.1"
|
|
70
70
|
},
|
|
71
71
|
"peerDependencies": {
|
|
72
|
-
"eslint": ">=7.
|
|
72
|
+
"eslint": ">=7.11.0"
|
|
73
73
|
},
|
|
74
74
|
"ava": {
|
|
75
75
|
"babel": true,
|
|
@@ -93,6 +93,9 @@
|
|
|
93
93
|
"extends": [
|
|
94
94
|
"plugin:eslint-plugin/all"
|
|
95
95
|
],
|
|
96
|
+
"ignores": [
|
|
97
|
+
"test/integration/{fixtures,unicorn}/**"
|
|
98
|
+
],
|
|
96
99
|
"overrides": [
|
|
97
100
|
{
|
|
98
101
|
"files": "rules/utils/*.js",
|
|
@@ -110,7 +113,15 @@
|
|
|
110
113
|
],
|
|
111
114
|
"rules": {
|
|
112
115
|
"strict": "error",
|
|
113
|
-
"unicorn/no-null": "error"
|
|
116
|
+
"unicorn/no-null": "error",
|
|
117
|
+
"unicorn/prevent-abbreviations": [
|
|
118
|
+
"error",
|
|
119
|
+
{
|
|
120
|
+
"replacements": {
|
|
121
|
+
"fn": false
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
]
|
|
114
125
|
}
|
|
115
126
|
}
|
|
116
127
|
}
|
package/readme.md
CHANGED
|
@@ -65,12 +65,14 @@ Configure it in `package.json`.
|
|
|
65
65
|
"unicorn/no-useless-undefined": "error",
|
|
66
66
|
"unicorn/no-zero-fractions": "error",
|
|
67
67
|
"unicorn/number-literal-case": "error",
|
|
68
|
+
"unicorn/numeric-separators-style": "off",
|
|
68
69
|
"unicorn/prefer-add-event-listener": "error",
|
|
69
70
|
"unicorn/prefer-array-find": "error",
|
|
70
71
|
"unicorn/prefer-dataset": "error",
|
|
71
72
|
"unicorn/prefer-event-key": "error",
|
|
72
73
|
"unicorn/prefer-flat-map": "error",
|
|
73
74
|
"unicorn/prefer-includes": "error",
|
|
75
|
+
"unicorn/prefer-math-trunc": "error",
|
|
74
76
|
"unicorn/prefer-modern-dom-apis": "error",
|
|
75
77
|
"unicorn/prefer-negative-index": "error",
|
|
76
78
|
"unicorn/prefer-node-append": "error",
|
|
@@ -84,6 +86,7 @@ Configure it in `package.json`.
|
|
|
84
86
|
"unicorn/prefer-spread": "error",
|
|
85
87
|
"unicorn/prefer-starts-ends-with": "error",
|
|
86
88
|
"unicorn/prefer-string-slice": "error",
|
|
89
|
+
"unicorn/prefer-ternary": "off",
|
|
87
90
|
"unicorn/prefer-text-content": "error",
|
|
88
91
|
"unicorn/prefer-trim-start-end": "error",
|
|
89
92
|
"unicorn/prefer-type-error": "error",
|
|
@@ -128,12 +131,14 @@ Configure it in `package.json`.
|
|
|
128
131
|
- [no-useless-undefined](docs/rules/no-useless-undefined.md) - Disallow useless `undefined`. *(fixable)*
|
|
129
132
|
- [no-zero-fractions](docs/rules/no-zero-fractions.md) - Disallow number literals with zero fractions or dangling dots. *(fixable)*
|
|
130
133
|
- [number-literal-case](docs/rules/number-literal-case.md) - Enforce proper case for numeric literals. *(fixable)*
|
|
134
|
+
- [numeric-separators-style](docs/rules/numeric-separators-style.md) - Enforce the style of numeric separators by correctly grouping digits. *(fixable)*
|
|
131
135
|
- [prefer-add-event-listener](docs/rules/prefer-add-event-listener.md) - Prefer `.addEventListener()` and `.removeEventListener()` over `on`-functions. *(partly fixable)*
|
|
132
136
|
- [prefer-array-find](docs/rules/prefer-array-find.md) - Prefer `.find(…)` over the first element from `.filter(…)`. *(partly fixable)*
|
|
133
137
|
- [prefer-dataset](docs/rules/prefer-dataset.md) - Prefer using `.dataset` on DOM elements over `.setAttribute(…)`. *(fixable)*
|
|
134
138
|
- [prefer-event-key](docs/rules/prefer-event-key.md) - Prefer `KeyboardEvent#key` over `KeyboardEvent#keyCode`. *(partly fixable)*
|
|
135
139
|
- [prefer-flat-map](docs/rules/prefer-flat-map.md) - Prefer `.flatMap(…)` over `.map(…).flat()`. *(fixable)*
|
|
136
140
|
- [prefer-includes](docs/rules/prefer-includes.md) - Prefer `.includes()` over `.indexOf()` when checking for existence or non-existence. *(fixable)*
|
|
141
|
+
- [prefer-math-trunc](docs/rules/prefer-math-trunc.md) - Enforce the use of `Math.trunc` instead of bitwise operators. *(partly fixable)*
|
|
137
142
|
- [prefer-modern-dom-apis](docs/rules/prefer-modern-dom-apis.md) - Prefer `.before()` over `.insertBefore()`, `.replaceWith()` over `.replaceChild()`, prefer one of `.before()`, `.after()`, `.append()` or `.prepend()` over `insertAdjacentText()` and `insertAdjacentElement()`. *(fixable)*
|
|
138
143
|
- [prefer-negative-index](docs/rules/prefer-negative-index.md) - Prefer negative index over `.length - index` for `{String,Array,TypedArray}#slice()` and `Array#splice()`. *(fixable)*
|
|
139
144
|
- [prefer-node-append](docs/rules/prefer-node-append.md) - Prefer `Node#append()` over `Node#appendChild()`. *(fixable)*
|
|
@@ -147,6 +152,7 @@ Configure it in `package.json`.
|
|
|
147
152
|
- [prefer-spread](docs/rules/prefer-spread.md) - Prefer the spread operator over `Array.from()`. *(fixable)*
|
|
148
153
|
- [prefer-starts-ends-with](docs/rules/prefer-starts-ends-with.md) - Prefer `String#startsWith()` & `String#endsWith()` over more complex alternatives. *(partly fixable)*
|
|
149
154
|
- [prefer-string-slice](docs/rules/prefer-string-slice.md) - Prefer `String#slice()` over `String#substr()` and `String#substring()`. *(partly fixable)*
|
|
155
|
+
- [prefer-ternary](docs/rules/prefer-ternary.md) - Prefer ternary expressions over simple `if-else` statements. *(fixable)*
|
|
150
156
|
- [prefer-text-content](docs/rules/prefer-text-content.md) - Prefer `.textContent` over `.innerText`. *(fixable)*
|
|
151
157
|
- [prefer-trim-start-end](docs/rules/prefer-trim-start-end.md) - Prefer `String#trimStart()` / `String#trimEnd()` over `String#trimLeft()` / `String#trimRight()`. *(fixable)*
|
|
152
158
|
- [prefer-type-error](docs/rules/prefer-type-error.md) - Enforce throwing `TypeError` in type checking conditions. *(fixable)*
|
package/rules/better-regex.js
CHANGED
|
@@ -4,7 +4,10 @@ const {optimize} = require('regexp-tree');
|
|
|
4
4
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
5
5
|
const quoteString = require('./utils/quote-string');
|
|
6
6
|
|
|
7
|
-
const
|
|
7
|
+
const MESSAGE_ID = 'better-regex';
|
|
8
|
+
const messages = {
|
|
9
|
+
[MESSAGE_ID]: '{{original}} can be optimized to {{optimized}}.'
|
|
10
|
+
};
|
|
8
11
|
|
|
9
12
|
const create = context => {
|
|
10
13
|
const {sortCharacterClasses} = context.options[0] || {};
|
|
@@ -37,7 +40,7 @@ const create = context => {
|
|
|
37
40
|
|
|
38
41
|
context.report({
|
|
39
42
|
node,
|
|
40
|
-
|
|
43
|
+
messageId: MESSAGE_ID,
|
|
41
44
|
data: {
|
|
42
45
|
original,
|
|
43
46
|
optimized
|
|
@@ -64,7 +67,7 @@ const create = context => {
|
|
|
64
67
|
if (oldPattern !== newPattern) {
|
|
65
68
|
context.report({
|
|
66
69
|
node,
|
|
67
|
-
|
|
70
|
+
messageId: MESSAGE_ID,
|
|
68
71
|
data: {
|
|
69
72
|
original: oldPattern,
|
|
70
73
|
optimized: newPattern
|
|
@@ -99,6 +102,7 @@ module.exports = {
|
|
|
99
102
|
url: getDocumentationUrl(__filename)
|
|
100
103
|
},
|
|
101
104
|
fixable: 'code',
|
|
102
|
-
schema
|
|
105
|
+
schema,
|
|
106
|
+
messages
|
|
103
107
|
}
|
|
104
108
|
};
|
|
@@ -5,7 +5,10 @@ const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
|
5
5
|
const renameVariable = require('./utils/rename-variable');
|
|
6
6
|
const methodSelector = require('./utils/method-selector');
|
|
7
7
|
|
|
8
|
-
const
|
|
8
|
+
const MESSAGE_ID = 'catch-error-name';
|
|
9
|
+
const messages = {
|
|
10
|
+
[MESSAGE_ID]: 'The catch parameter `{{originalName}}` should be named `{{fixedName}}`.'
|
|
11
|
+
};
|
|
9
12
|
|
|
10
13
|
const promiseMethodSelector = (method, argumentsLength, argumentIndex) => [
|
|
11
14
|
methodSelector({
|
|
@@ -78,7 +81,7 @@ const create = context => {
|
|
|
78
81
|
|
|
79
82
|
context.report({
|
|
80
83
|
node,
|
|
81
|
-
messageId:
|
|
84
|
+
messageId: MESSAGE_ID,
|
|
82
85
|
data: {
|
|
83
86
|
originalName,
|
|
84
87
|
fixedName
|
|
@@ -124,8 +127,6 @@ module.exports = {
|
|
|
124
127
|
},
|
|
125
128
|
fixable: 'code',
|
|
126
129
|
schema,
|
|
127
|
-
messages
|
|
128
|
-
[ERROR_MESSAGE_ID]: 'The catch parameter `{{originalName}}` should be named `{{fixedName}}`.'
|
|
129
|
-
}
|
|
130
|
+
messages
|
|
130
131
|
}
|
|
131
132
|
};
|
|
@@ -4,6 +4,9 @@ const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
|
4
4
|
const getReferences = require('./utils/get-references');
|
|
5
5
|
|
|
6
6
|
const MESSAGE_ID = 'consistent-function-scoping';
|
|
7
|
+
const messages = {
|
|
8
|
+
[MESSAGE_ID]: 'Move {{functionNameWithKind}} to the outer scope.'
|
|
9
|
+
};
|
|
7
10
|
|
|
8
11
|
const isSameScope = (scope1, scope2) =>
|
|
9
12
|
scope1 && scope2 && (scope1 === scope2 || scope1.block === scope2.block);
|
|
@@ -153,17 +156,21 @@ const create = context => {
|
|
|
153
156
|
const {scopeManager} = sourceCode;
|
|
154
157
|
|
|
155
158
|
const functions = [];
|
|
156
|
-
let hasJsx = false;
|
|
157
159
|
|
|
158
160
|
return {
|
|
159
|
-
'
|
|
161
|
+
':function': () => {
|
|
162
|
+
functions.push(false);
|
|
163
|
+
},
|
|
160
164
|
JSXElement: () => {
|
|
161
165
|
// Turn off this rule if we see a JSX element because scope
|
|
162
166
|
// references does not include JSXElement nodes.
|
|
163
|
-
|
|
167
|
+
if (functions.length > 0) {
|
|
168
|
+
functions[functions.length - 1] = true;
|
|
169
|
+
}
|
|
164
170
|
},
|
|
165
|
-
':
|
|
166
|
-
|
|
171
|
+
':function:exit': node => {
|
|
172
|
+
const currentFunctionHasJsx = functions.pop();
|
|
173
|
+
if (!currentFunctionHasJsx && !checkNode(node, scopeManager)) {
|
|
167
174
|
context.report({
|
|
168
175
|
node,
|
|
169
176
|
loc: getFunctionHeadLocation(node, sourceCode),
|
|
@@ -173,11 +180,6 @@ const create = context => {
|
|
|
173
180
|
}
|
|
174
181
|
});
|
|
175
182
|
}
|
|
176
|
-
|
|
177
|
-
functions.pop();
|
|
178
|
-
if (functions.length === 0) {
|
|
179
|
-
hasJsx = false;
|
|
180
|
-
}
|
|
181
183
|
}
|
|
182
184
|
};
|
|
183
185
|
};
|
|
@@ -189,8 +191,6 @@ module.exports = {
|
|
|
189
191
|
docs: {
|
|
190
192
|
url: getDocumentationUrl(__filename)
|
|
191
193
|
},
|
|
192
|
-
messages
|
|
193
|
-
[MESSAGE_ID]: 'Move {{functionNameWithKind}} to the outer scope.'
|
|
194
|
-
}
|
|
194
|
+
messages
|
|
195
195
|
}
|
|
196
196
|
};
|
|
@@ -3,6 +3,9 @@ const {upperFirst} = require('lodash');
|
|
|
3
3
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
4
4
|
|
|
5
5
|
const MESSAGE_ID_INVALID_EXPORT = 'invalidExport';
|
|
6
|
+
const messages = {
|
|
7
|
+
[MESSAGE_ID_INVALID_EXPORT]: 'Exported error name should match error class'
|
|
8
|
+
};
|
|
6
9
|
|
|
7
10
|
const nameRegexp = /^(?:[A-Z][\da-z]*)*Error$/;
|
|
8
11
|
|
|
@@ -212,8 +215,6 @@ module.exports = {
|
|
|
212
215
|
url: getDocumentationUrl(__filename)
|
|
213
216
|
},
|
|
214
217
|
fixable: 'code',
|
|
215
|
-
messages
|
|
216
|
-
[MESSAGE_ID_INVALID_EXPORT]: 'Exported error name should match error class'
|
|
217
|
-
}
|
|
218
|
+
messages
|
|
218
219
|
}
|
|
219
220
|
};
|
package/rules/error-message.js
CHANGED
|
@@ -1,6 +1,13 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
|
|
4
|
+
const MESSAGE_ID_MISSING_MESSAGE = 'constructorMissingMessage';
|
|
5
|
+
const MESSAGE_ID_EMPTY_MESSAGE = 'emptyMessage';
|
|
6
|
+
const messages = {
|
|
7
|
+
[MESSAGE_ID_MISSING_MESSAGE]: 'Pass a message to the error constructor.',
|
|
8
|
+
[MESSAGE_ID_EMPTY_MESSAGE]: 'Error message should not be an empty string.'
|
|
9
|
+
};
|
|
10
|
+
|
|
4
11
|
const errorConstructors = new Set([
|
|
5
12
|
'Error',
|
|
6
13
|
'EvalError',
|
|
@@ -55,14 +62,14 @@ const reportError = (expressionNode, context) => {
|
|
|
55
62
|
if (expressionNode.arguments.length === 0) {
|
|
56
63
|
context.report({
|
|
57
64
|
node: expressionNode.parent,
|
|
58
|
-
|
|
65
|
+
messageId: MESSAGE_ID_MISSING_MESSAGE
|
|
59
66
|
});
|
|
60
67
|
}
|
|
61
68
|
|
|
62
69
|
if (isEmptyMessageString(expressionNode)) {
|
|
63
70
|
context.report({
|
|
64
71
|
node: expressionNode.parent,
|
|
65
|
-
|
|
72
|
+
messageId: MESSAGE_ID_EMPTY_MESSAGE
|
|
66
73
|
});
|
|
67
74
|
}
|
|
68
75
|
}
|
|
@@ -99,6 +106,7 @@ module.exports = {
|
|
|
99
106
|
type: 'problem',
|
|
100
107
|
docs: {
|
|
101
108
|
url: getDocumentationUrl(__filename)
|
|
102
|
-
}
|
|
109
|
+
},
|
|
110
|
+
messages
|
|
103
111
|
}
|
|
104
112
|
};
|
package/rules/escape-case.js
CHANGED
|
@@ -2,9 +2,13 @@
|
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
const replaceTemplateElement = require('./utils/replace-template-element');
|
|
4
4
|
|
|
5
|
+
const MESSAGE_ID = 'escape-case';
|
|
6
|
+
const messages = {
|
|
7
|
+
[MESSAGE_ID]: 'Use uppercase characters for the value of the escape sequence.'
|
|
8
|
+
};
|
|
9
|
+
|
|
5
10
|
const escapeWithLowercase = /(?<=(?:^|[^\\])(?:\\\\)*\\)(?<data>x[\dA-Fa-f]{2}|u[\dA-Fa-f]{4}|u{[\dA-Fa-f]+})/g;
|
|
6
11
|
const escapePatternWithLowercase = /(?<=(?:^|[^\\])(?:\\\\)*\\)(?<data>x[\dA-Fa-f]{2}|u[\dA-Fa-f]{4}|u{[\dA-Fa-f]+}|c[a-z])/g;
|
|
7
|
-
const message = 'Use uppercase characters for the value of the escape sequence.';
|
|
8
12
|
|
|
9
13
|
const create = context => {
|
|
10
14
|
const check = ({node, original, regex = escapeWithLowercase, fix}) => {
|
|
@@ -13,7 +17,7 @@ const create = context => {
|
|
|
13
17
|
if (fixed !== original) {
|
|
14
18
|
context.report({
|
|
15
19
|
node,
|
|
16
|
-
|
|
20
|
+
messageId: MESSAGE_ID,
|
|
17
21
|
fix: fixer => fix ? fix(fixer, fixed) : fixer.replaceText(node, fixed)
|
|
18
22
|
});
|
|
19
23
|
}
|
|
@@ -54,6 +58,7 @@ module.exports = {
|
|
|
54
58
|
docs: {
|
|
55
59
|
url: getDocumentationUrl(__filename)
|
|
56
60
|
},
|
|
57
|
-
fixable: 'code'
|
|
61
|
+
fixable: 'code',
|
|
62
|
+
messages
|
|
58
63
|
}
|
|
59
64
|
};
|
|
@@ -18,6 +18,29 @@ const MESSAGE_ID_VERSION_MATCHES = 'unicorn/versionMatches';
|
|
|
18
18
|
const MESSAGE_ID_ENGINE_MATCHES = 'unicorn/engineMatches';
|
|
19
19
|
const MESSAGE_ID_REMOVE_WHITESPACE = 'unicorn/removeWhitespaces';
|
|
20
20
|
const MESSAGE_ID_MISSING_AT_SYMBOL = 'unicorn/missingAtSymbol';
|
|
21
|
+
const messages = {
|
|
22
|
+
[MESSAGE_ID_AVOID_MULTIPLE_DATES]:
|
|
23
|
+
'Avoid using multiple expiration dates in TODO: {{expirationDates}}. {{message}}',
|
|
24
|
+
[MESSAGE_ID_EXPIRED_TODO]:
|
|
25
|
+
'There is a TODO that is past due date: {{expirationDate}}. {{message}}',
|
|
26
|
+
[MESSAGE_ID_REACHED_PACKAGE_VERSION]:
|
|
27
|
+
'There is a TODO that is past due package version: {{comparison}}. {{message}}',
|
|
28
|
+
[MESSAGE_ID_AVOID_MULTIPLE_PACKAGE_VERSIONS]:
|
|
29
|
+
'Avoid using multiple package versions in TODO: {{versions}}. {{message}}',
|
|
30
|
+
[MESSAGE_ID_HAVE_PACKAGE]:
|
|
31
|
+
'There is a TODO that is deprecated since you installed: {{package}}. {{message}}',
|
|
32
|
+
[MESSAGE_ID_DONT_HAVE_PACKAGE]:
|
|
33
|
+
'There is a TODO that is deprecated since you uninstalled: {{package}}. {{message}}',
|
|
34
|
+
[MESSAGE_ID_VERSION_MATCHES]:
|
|
35
|
+
'There is a TODO match for package version: {{comparison}}. {{message}}',
|
|
36
|
+
[MESSAGE_ID_ENGINE_MATCHES]:
|
|
37
|
+
'There is a TODO match for Node.js version: {{comparison}}. {{message}}',
|
|
38
|
+
[MESSAGE_ID_REMOVE_WHITESPACE]:
|
|
39
|
+
'Avoid using whitespace on TODO argument. On \'{{original}}\' use \'{{fix}}\'. {{message}}',
|
|
40
|
+
[MESSAGE_ID_MISSING_AT_SYMBOL]:
|
|
41
|
+
'Missing \'@\' on TODO argument. On \'{{original}}\' use \'{{fix}}\'. {{message}}',
|
|
42
|
+
...baseRule.meta.messages
|
|
43
|
+
};
|
|
21
44
|
|
|
22
45
|
const packageResult = readPkgUp.sync();
|
|
23
46
|
const hasPackage = Boolean(packageResult);
|
|
@@ -509,29 +532,7 @@ module.exports = {
|
|
|
509
532
|
docs: {
|
|
510
533
|
url: getDocumentationUrl(__filename)
|
|
511
534
|
},
|
|
512
|
-
messages
|
|
513
|
-
[MESSAGE_ID_AVOID_MULTIPLE_DATES]:
|
|
514
|
-
'Avoid using multiple expiration dates in TODO: {{expirationDates}}. {{message}}',
|
|
515
|
-
[MESSAGE_ID_EXPIRED_TODO]:
|
|
516
|
-
'There is a TODO that is past due date: {{expirationDate}}. {{message}}',
|
|
517
|
-
[MESSAGE_ID_REACHED_PACKAGE_VERSION]:
|
|
518
|
-
'There is a TODO that is past due package version: {{comparison}}. {{message}}',
|
|
519
|
-
[MESSAGE_ID_AVOID_MULTIPLE_PACKAGE_VERSIONS]:
|
|
520
|
-
'Avoid using multiple package versions in TODO: {{versions}}. {{message}}',
|
|
521
|
-
[MESSAGE_ID_HAVE_PACKAGE]:
|
|
522
|
-
'There is a TODO that is deprecated since you installed: {{package}}. {{message}}',
|
|
523
|
-
[MESSAGE_ID_DONT_HAVE_PACKAGE]:
|
|
524
|
-
'There is a TODO that is deprecated since you uninstalled: {{package}}. {{message}}',
|
|
525
|
-
[MESSAGE_ID_VERSION_MATCHES]:
|
|
526
|
-
'There is a TODO match for package version: {{comparison}}. {{message}}',
|
|
527
|
-
[MESSAGE_ID_ENGINE_MATCHES]:
|
|
528
|
-
'There is a TODO match for Node.js version: {{comparison}}. {{message}}',
|
|
529
|
-
[MESSAGE_ID_REMOVE_WHITESPACE]:
|
|
530
|
-
'Avoid using whitespace on TODO argument. On \'{{original}}\' use \'{{fix}}\'. {{message}}',
|
|
531
|
-
[MESSAGE_ID_MISSING_AT_SYMBOL]:
|
|
532
|
-
'Missing \'@\' on TODO argument. On \'{{original}}\' use \'{{fix}}\'. {{message}}',
|
|
533
|
-
...baseRule.meta.messages
|
|
534
|
-
},
|
|
535
|
+
messages,
|
|
535
536
|
schema
|
|
536
537
|
}
|
|
537
538
|
};
|
|
@@ -1,16 +1,24 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
|
|
4
|
+
const messages = {
|
|
5
|
+
compareToValue: '`length` property should be compared to a value.',
|
|
6
|
+
zeroEqual: 'Zero `.length` should be compared with `=== 0`.',
|
|
7
|
+
nonZeroEqual: 'Non-zero `.length` should be compared with `!== 0`.',
|
|
8
|
+
nonZeroGreater: 'Non-zero `.length` should be compared with `> 0`.',
|
|
9
|
+
nonZeroGreaterEqual: 'Non-zero `.length` should be compared with `>= 1`.'
|
|
10
|
+
};
|
|
11
|
+
|
|
4
12
|
const operatorTypes = {
|
|
5
13
|
gt: ['>'],
|
|
6
14
|
gte: ['>='],
|
|
7
15
|
ne: ['!==', '!=']
|
|
8
16
|
};
|
|
9
17
|
|
|
10
|
-
function reportError(context, node,
|
|
18
|
+
function reportError(context, node, messageId, fixDetails) {
|
|
11
19
|
context.report({
|
|
12
20
|
node,
|
|
13
|
-
|
|
21
|
+
messageId,
|
|
14
22
|
fix: fixDetails && (fixer => {
|
|
15
23
|
return fixer.replaceText(
|
|
16
24
|
node,
|
|
@@ -25,7 +33,7 @@ function checkZeroType(context, node) {
|
|
|
25
33
|
reportError(
|
|
26
34
|
context,
|
|
27
35
|
node,
|
|
28
|
-
'
|
|
36
|
+
'zeroEqual',
|
|
29
37
|
{
|
|
30
38
|
node: node.left,
|
|
31
39
|
operator: '===',
|
|
@@ -35,7 +43,7 @@ function checkZeroType(context, node) {
|
|
|
35
43
|
}
|
|
36
44
|
}
|
|
37
45
|
|
|
38
|
-
function checkNonZeroType(context, node, type) {
|
|
46
|
+
function checkNonZeroType(context, node, type = 'greater-than') {
|
|
39
47
|
const {value} = node.right;
|
|
40
48
|
const {operator} = node;
|
|
41
49
|
|
|
@@ -48,7 +56,7 @@ function checkNonZeroType(context, node, type) {
|
|
|
48
56
|
reportError(
|
|
49
57
|
context,
|
|
50
58
|
node,
|
|
51
|
-
'
|
|
59
|
+
'nonZeroGreater',
|
|
52
60
|
{
|
|
53
61
|
node: node.left,
|
|
54
62
|
operator: '>',
|
|
@@ -66,7 +74,7 @@ function checkNonZeroType(context, node, type) {
|
|
|
66
74
|
reportError(
|
|
67
75
|
context,
|
|
68
76
|
node,
|
|
69
|
-
'
|
|
77
|
+
'nonZeroGreaterEqual',
|
|
70
78
|
{
|
|
71
79
|
node: node.left,
|
|
72
80
|
operator: '>=',
|
|
@@ -84,7 +92,7 @@ function checkNonZeroType(context, node, type) {
|
|
|
84
92
|
reportError(
|
|
85
93
|
context,
|
|
86
94
|
node,
|
|
87
|
-
'
|
|
95
|
+
'nonZeroEqual',
|
|
88
96
|
{
|
|
89
97
|
node: node.left,
|
|
90
98
|
operator: '!==',
|
|
@@ -134,7 +142,7 @@ function checkExpression(context, node) {
|
|
|
134
142
|
node.property.name === 'length' &&
|
|
135
143
|
!node.computed
|
|
136
144
|
) {
|
|
137
|
-
reportError(context, node, '
|
|
145
|
+
reportError(context, node, 'compareToValue');
|
|
138
146
|
}
|
|
139
147
|
}
|
|
140
148
|
|
|
@@ -154,7 +162,8 @@ const schema = [
|
|
|
154
162
|
type: 'object',
|
|
155
163
|
properties: {
|
|
156
164
|
'non-zero': {
|
|
157
|
-
enum: ['not-equal', 'greater-than', 'greater-than-or-equal']
|
|
165
|
+
enum: ['not-equal', 'greater-than', 'greater-than-or-equal'],
|
|
166
|
+
default: 'greater-than'
|
|
158
167
|
}
|
|
159
168
|
}
|
|
160
169
|
}
|
|
@@ -168,6 +177,7 @@ module.exports = {
|
|
|
168
177
|
url: getDocumentationUrl(__filename)
|
|
169
178
|
},
|
|
170
179
|
fixable: 'code',
|
|
171
|
-
schema
|
|
180
|
+
schema,
|
|
181
|
+
messages
|
|
172
182
|
}
|
|
173
183
|
};
|
package/rules/filename-case.js
CHANGED
|
@@ -4,6 +4,11 @@ const {camelCase, kebabCase, snakeCase, upperFirst} = require('lodash');
|
|
|
4
4
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
5
5
|
const cartesianProductSamples = require('./utils/cartesian-product-samples');
|
|
6
6
|
|
|
7
|
+
const messages = {
|
|
8
|
+
renameToCase: 'Filename is not in {{chosenCases}}. Rename it to {{renamedFilenames}}.',
|
|
9
|
+
renameToCases: 'Filename is not in {{chosenCases}}. Rename it to {{renamedFilenames}}.'
|
|
10
|
+
};
|
|
11
|
+
|
|
7
12
|
const pascalCase = string => upperFirst(camelCase(string));
|
|
8
13
|
const numberRegex = /\d+/;
|
|
9
14
|
const PLACEHOLDER = '\uFFFF\uFFFF\uFFFF';
|
|
@@ -246,9 +251,6 @@ module.exports = {
|
|
|
246
251
|
url: getDocumentationUrl(__filename)
|
|
247
252
|
},
|
|
248
253
|
schema,
|
|
249
|
-
messages
|
|
250
|
-
renameToCase: 'Filename is not in {{chosenCases}}. Rename it to {{renamedFilenames}}.',
|
|
251
|
-
renameToCases: 'Filename is not in {{chosenCases}}. Rename it to {{renamedFilenames}}.'
|
|
252
|
-
}
|
|
254
|
+
messages
|
|
253
255
|
}
|
|
254
256
|
};
|
package/rules/import-index.js
CHANGED
|
@@ -1,6 +1,11 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
|
|
4
|
+
const MESSAGE_ID = 'import-index';
|
|
5
|
+
const messages = {
|
|
6
|
+
[MESSAGE_ID]: 'Do not reference the index file directly..'
|
|
7
|
+
};
|
|
8
|
+
|
|
4
9
|
const regexp = /^(?<package>@.*?\/.*?|[./]+?.*?)\/(?:\.|(?:index(?:\.js)?))?$/;
|
|
5
10
|
const isImportingIndex = value => regexp.test(value);
|
|
6
11
|
const normalize = value => value.replace(regexp, '$<package>');
|
|
@@ -9,7 +14,7 @@ const importIndex = (context, node, argument) => {
|
|
|
9
14
|
if (argument && isImportingIndex(argument.value)) {
|
|
10
15
|
context.report({
|
|
11
16
|
node,
|
|
12
|
-
|
|
17
|
+
messageId: MESSAGE_ID,
|
|
13
18
|
fix: fixer => fixer.replaceText(argument, `'${normalize(argument.value)}'`)
|
|
14
19
|
});
|
|
15
20
|
}
|
|
@@ -50,6 +55,7 @@ module.exports = {
|
|
|
50
55
|
url: getDocumentationUrl(__filename)
|
|
51
56
|
},
|
|
52
57
|
schema,
|
|
53
|
-
fixable: 'code'
|
|
58
|
+
fixable: 'code',
|
|
59
|
+
messages
|
|
54
60
|
}
|
|
55
61
|
};
|
package/rules/import-style.js
CHANGED
|
@@ -3,6 +3,11 @@ const {defaultsDeep} = require('lodash');
|
|
|
3
3
|
const {getStringIfConstant} = require('eslint-utils');
|
|
4
4
|
const eslintTemplateVisitor = require('eslint-template-visitor');
|
|
5
5
|
|
|
6
|
+
const MESSAGE_ID = 'importStyle';
|
|
7
|
+
const messages = {
|
|
8
|
+
[MESSAGE_ID]: 'Use {{allowedStyles}} import for module `{{moduleName}}`.'
|
|
9
|
+
};
|
|
10
|
+
|
|
6
11
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
7
12
|
|
|
8
13
|
const getActualImportDeclarationStyles = importDeclaration => {
|
|
@@ -111,8 +116,6 @@ const joinOr = words => {
|
|
|
111
116
|
.join(' ');
|
|
112
117
|
};
|
|
113
118
|
|
|
114
|
-
const MESSAGE_ID = 'importStyle';
|
|
115
|
-
|
|
116
119
|
// Keep this alphabetically sorted for easier maintenance
|
|
117
120
|
const defaultStyles = {
|
|
118
121
|
chalk: {
|
|
@@ -364,9 +367,7 @@ module.exports = {
|
|
|
364
367
|
docs: {
|
|
365
368
|
url: getDocumentationUrl(__filename)
|
|
366
369
|
},
|
|
367
|
-
messages
|
|
368
|
-
[MESSAGE_ID]: 'Use {{allowedStyles}} import for module `{{moduleName}}`.'
|
|
369
|
-
},
|
|
370
|
+
messages,
|
|
370
371
|
schema
|
|
371
372
|
}
|
|
372
373
|
};
|
|
@@ -1,6 +1,11 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
|
|
4
|
+
const MESSAGE_ID = 'no-abusive-eslint-disable';
|
|
5
|
+
const messages = {
|
|
6
|
+
[MESSAGE_ID]: 'Specify the rules you want to disable.'
|
|
7
|
+
};
|
|
8
|
+
|
|
4
9
|
const disableRegex = /^eslint-disable(?:-next-line|-line)?(?<ruleId>$|(?:\s+(?:@(?:[\w-]+\/){1,2})?[\w-]+)?)/;
|
|
5
10
|
|
|
6
11
|
const create = context => ({
|
|
@@ -14,6 +19,8 @@ const create = context => ({
|
|
|
14
19
|
!result.groups.ruleId // But it did not specify any rules
|
|
15
20
|
) {
|
|
16
21
|
context.report({
|
|
22
|
+
// Can't set it at the given location as the warning
|
|
23
|
+
// will be ignored due to the disable comment
|
|
17
24
|
loc: {
|
|
18
25
|
start: {
|
|
19
26
|
...comment.loc.start,
|
|
@@ -21,7 +28,7 @@ const create = context => ({
|
|
|
21
28
|
},
|
|
22
29
|
end: comment.loc.end
|
|
23
30
|
},
|
|
24
|
-
|
|
31
|
+
messageId: MESSAGE_ID
|
|
25
32
|
});
|
|
26
33
|
}
|
|
27
34
|
}
|
|
@@ -34,6 +41,7 @@ module.exports = {
|
|
|
34
41
|
type: 'suggestion',
|
|
35
42
|
docs: {
|
|
36
43
|
url: getDocumentationUrl(__filename)
|
|
37
|
-
}
|
|
44
|
+
},
|
|
45
|
+
messages
|
|
38
46
|
}
|
|
39
47
|
};
|
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
const getDocumentationUrl = require('./utils/get-documentation-url');
|
|
3
3
|
|
|
4
|
-
const
|
|
4
|
+
const MESSAGE_ID = 'no-array-instanceof';
|
|
5
|
+
const messages = {
|
|
6
|
+
[MESSAGE_ID]: 'Use `Array.isArray()` instead of `instanceof Array`.'
|
|
7
|
+
};
|
|
5
8
|
const selector = [
|
|
6
9
|
'BinaryExpression',
|
|
7
10
|
'[operator="instanceof"]',
|
|
@@ -15,7 +18,7 @@ const create = context => {
|
|
|
15
18
|
return {
|
|
16
19
|
[selector]: node => context.report({
|
|
17
20
|
node,
|
|
18
|
-
|
|
21
|
+
messageId: MESSAGE_ID,
|
|
19
22
|
fix: fixer => fixer.replaceText(
|
|
20
23
|
node,
|
|
21
24
|
`Array.isArray(${sourceCode.getText(node.left)})`
|
|
@@ -31,6 +34,7 @@ module.exports = {
|
|
|
31
34
|
docs: {
|
|
32
35
|
url: getDocumentationUrl(__filename)
|
|
33
36
|
},
|
|
34
|
-
fixable: 'code'
|
|
37
|
+
fixable: 'code',
|
|
38
|
+
messages
|
|
35
39
|
}
|
|
36
40
|
};
|