@so1ve/eslint-plugin 0.56.1 → 0.58.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/dist/index.cjs +20 -799
- package/dist/index.d.ts +1 -18
- package/dist/index.mjs +21 -787
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -1,354 +1,10 @@
|
|
|
1
|
-
import { ESLintUtils
|
|
2
|
-
import { ref, computed } from '@vue/reactivity';
|
|
3
|
-
import * as util from '@typescript-eslint/utils/dist/ast-utils';
|
|
1
|
+
import { ESLintUtils } from '@typescript-eslint/utils';
|
|
4
2
|
|
|
5
3
|
const createEslintRule = ESLintUtils.RuleCreator((ruleName) => ruleName);
|
|
6
4
|
|
|
7
|
-
const RULE_NAME$
|
|
8
|
-
const arrayBracketSpacing = createEslintRule({
|
|
9
|
-
name: RULE_NAME$8,
|
|
10
|
-
meta: {
|
|
11
|
-
type: "layout",
|
|
12
|
-
docs: {
|
|
13
|
-
description: "Array bracket spacing",
|
|
14
|
-
recommended: "error"
|
|
15
|
-
},
|
|
16
|
-
fixable: "whitespace",
|
|
17
|
-
schema: [],
|
|
18
|
-
messages: {
|
|
19
|
-
arrayBracketSpacing: "Array bracket spacing mismatch"
|
|
20
|
-
}
|
|
21
|
-
},
|
|
22
|
-
defaultOptions: [],
|
|
23
|
-
create: (context) => {
|
|
24
|
-
const sourceCode = context.getSourceCode();
|
|
25
|
-
const text = sourceCode.getText();
|
|
26
|
-
const checkNode = (node) => {
|
|
27
|
-
const elements = node.type === AST_NODE_TYPES.TSTupleType ? node.elementTypes : node.elements;
|
|
28
|
-
const firstElement = elements[0];
|
|
29
|
-
const lastElement = elements[elements.length - 1];
|
|
30
|
-
if (!firstElement) {
|
|
31
|
-
return;
|
|
32
|
-
}
|
|
33
|
-
const leftToken = sourceCode.getTokenBefore(firstElement);
|
|
34
|
-
const rightToken = ref(sourceCode.getTokenAfter(lastElement));
|
|
35
|
-
if (rightToken.value.value === ",") {
|
|
36
|
-
rightToken.value = sourceCode.getTokenAfter(rightToken.value);
|
|
37
|
-
}
|
|
38
|
-
const textBetweenFirstAndToken = computed(() => text.slice(leftToken.range[1], firstElement.range[0]));
|
|
39
|
-
const isNewline = computed(() => textBetweenFirstAndToken.value.includes("\n"));
|
|
40
|
-
const textBetweenLastAndToken = computed(() => text.slice(lastElement.range[1], rightToken.value.range[0]));
|
|
41
|
-
const hasNewlineAfter = computed(() => textBetweenLastAndToken.value.includes("\n"));
|
|
42
|
-
if (sourceCode.isSpaceBetween(leftToken, firstElement) && !isNewline.value) {
|
|
43
|
-
context.report({
|
|
44
|
-
node,
|
|
45
|
-
messageId: "arrayBracketSpacing",
|
|
46
|
-
*fix(fixer) {
|
|
47
|
-
yield fixer.removeRange([leftToken.range[1], firstElement.range[0]]);
|
|
48
|
-
}
|
|
49
|
-
});
|
|
50
|
-
}
|
|
51
|
-
if (sourceCode.isSpaceBetween(lastElement, rightToken.value)) {
|
|
52
|
-
if (!isNewline.value) {
|
|
53
|
-
context.report({
|
|
54
|
-
node,
|
|
55
|
-
messageId: "arrayBracketSpacing",
|
|
56
|
-
*fix(fixer) {
|
|
57
|
-
yield fixer.removeRange([lastElement.range[1], rightToken.value.range[0]]);
|
|
58
|
-
}
|
|
59
|
-
});
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
if (isNewline.value && !hasNewlineAfter.value) {
|
|
63
|
-
context.report({
|
|
64
|
-
node,
|
|
65
|
-
messageId: "arrayBracketSpacing",
|
|
66
|
-
*fix(fixer) {
|
|
67
|
-
yield fixer.replaceTextRange([lastElement.range[1], rightToken.value.range[0]], "\n");
|
|
68
|
-
}
|
|
69
|
-
});
|
|
70
|
-
}
|
|
71
|
-
};
|
|
72
|
-
return {
|
|
73
|
-
TSTupleType: checkNode,
|
|
74
|
-
ArrayExpression: checkNode
|
|
75
|
-
};
|
|
76
|
-
}
|
|
77
|
-
});
|
|
78
|
-
|
|
79
|
-
const RULE_NAME$7 = "generic-spacing";
|
|
80
|
-
const genericSpacing = createEslintRule({
|
|
81
|
-
name: RULE_NAME$7,
|
|
82
|
-
meta: {
|
|
83
|
-
type: "layout",
|
|
84
|
-
docs: {
|
|
85
|
-
description: "Spaces around generic type parameters",
|
|
86
|
-
recommended: "error"
|
|
87
|
-
},
|
|
88
|
-
fixable: "whitespace",
|
|
89
|
-
schema: [],
|
|
90
|
-
messages: {
|
|
91
|
-
genericSpacingMismatch: "Generic spaces mismatch"
|
|
92
|
-
}
|
|
93
|
-
},
|
|
94
|
-
defaultOptions: [],
|
|
95
|
-
create: (context) => {
|
|
96
|
-
const sourceCode = context.getSourceCode();
|
|
97
|
-
const text = sourceCode.getText();
|
|
98
|
-
return {
|
|
99
|
-
TSTypeParameterDeclaration: (node) => {
|
|
100
|
-
const params = node.params;
|
|
101
|
-
for (const param of params) {
|
|
102
|
-
const leftToken = sourceCode.getTokenBefore(param);
|
|
103
|
-
const rightToken = sourceCode.getTokenAfter(param);
|
|
104
|
-
const hasSpacingBeforeParam = sourceCode.isSpaceBetween(leftToken, param);
|
|
105
|
-
const hasSpacingAfterParam = sourceCode.isSpaceBetween(param, rightToken);
|
|
106
|
-
if (hasSpacingBeforeParam && param.loc.start.line === node.loc.start.line && leftToken.value === "<") {
|
|
107
|
-
context.report({
|
|
108
|
-
node,
|
|
109
|
-
loc: {
|
|
110
|
-
start: {
|
|
111
|
-
line: leftToken.loc.end.line,
|
|
112
|
-
column: leftToken.loc.end.column
|
|
113
|
-
},
|
|
114
|
-
end: {
|
|
115
|
-
line: param.loc.start.line,
|
|
116
|
-
column: param.loc.start.column - 1
|
|
117
|
-
}
|
|
118
|
-
},
|
|
119
|
-
messageId: "genericSpacingMismatch",
|
|
120
|
-
*fix(fixer) {
|
|
121
|
-
yield fixer.removeRange([leftToken.range[1], param.range[0]]);
|
|
122
|
-
}
|
|
123
|
-
});
|
|
124
|
-
}
|
|
125
|
-
if (hasSpacingAfterParam && param.loc.end.line === node.loc.end.line) {
|
|
126
|
-
context.report({
|
|
127
|
-
loc: {
|
|
128
|
-
start: {
|
|
129
|
-
line: param.loc.end.line,
|
|
130
|
-
column: param.loc.end.column
|
|
131
|
-
},
|
|
132
|
-
end: {
|
|
133
|
-
line: rightToken.loc.start.line,
|
|
134
|
-
column: rightToken.loc.start.column
|
|
135
|
-
}
|
|
136
|
-
},
|
|
137
|
-
node,
|
|
138
|
-
messageId: "genericSpacingMismatch",
|
|
139
|
-
*fix(fixer) {
|
|
140
|
-
yield fixer.removeRange([param.range[1], rightToken.range[0]]);
|
|
141
|
-
}
|
|
142
|
-
});
|
|
143
|
-
}
|
|
144
|
-
if (!hasSpacingBeforeParam && util.isCommaToken(leftToken)) {
|
|
145
|
-
context.report({
|
|
146
|
-
node,
|
|
147
|
-
loc: {
|
|
148
|
-
start: {
|
|
149
|
-
line: leftToken.loc.end.line,
|
|
150
|
-
column: leftToken.loc.end.column
|
|
151
|
-
},
|
|
152
|
-
end: {
|
|
153
|
-
line: param.loc.start.line,
|
|
154
|
-
column: param.loc.start.column - 1
|
|
155
|
-
}
|
|
156
|
-
},
|
|
157
|
-
messageId: "genericSpacingMismatch",
|
|
158
|
-
*fix(fixer) {
|
|
159
|
-
yield fixer.replaceTextRange([leftToken.range[1], param.range[0]], " ");
|
|
160
|
-
}
|
|
161
|
-
});
|
|
162
|
-
}
|
|
163
|
-
}
|
|
164
|
-
if (!["TSCallSignatureDeclaration", "ArrowFunctionExpression"].includes(node.parent.type)) {
|
|
165
|
-
const leftToken = sourceCode.getTokenBefore(node);
|
|
166
|
-
const hasSpacingBeforeNode = sourceCode.isSpaceBetween(leftToken, node);
|
|
167
|
-
const lastParam = params[params.length - 1];
|
|
168
|
-
const endBracket = sourceCode.getTokenAfter(lastParam);
|
|
169
|
-
const rightToken = sourceCode.getTokenAfter(endBracket, util.isOpeningParenToken);
|
|
170
|
-
if (!rightToken) {
|
|
171
|
-
return;
|
|
172
|
-
}
|
|
173
|
-
const hasSpacingAfterParam = sourceCode.isSpaceBetween(endBracket, rightToken);
|
|
174
|
-
if (hasSpacingBeforeNode && node.parent.type !== AST_NODE_TYPES.TSFunctionType) {
|
|
175
|
-
context.report({
|
|
176
|
-
node,
|
|
177
|
-
loc: {
|
|
178
|
-
start: {
|
|
179
|
-
line: leftToken.loc.end.line,
|
|
180
|
-
column: leftToken.loc.end.column
|
|
181
|
-
},
|
|
182
|
-
end: {
|
|
183
|
-
line: node.loc.start.line,
|
|
184
|
-
column: node.loc.start.column
|
|
185
|
-
}
|
|
186
|
-
},
|
|
187
|
-
messageId: "genericSpacingMismatch",
|
|
188
|
-
*fix(fixer) {
|
|
189
|
-
yield fixer.removeRange([leftToken.range[1], node.range[0]]);
|
|
190
|
-
}
|
|
191
|
-
});
|
|
192
|
-
}
|
|
193
|
-
if (hasSpacingAfterParam && [AST_NODE_TYPES.TSFunctionType, AST_NODE_TYPES.FunctionDeclaration, AST_NODE_TYPES.FunctionExpression].includes(node.parent.type)) {
|
|
194
|
-
context.report({
|
|
195
|
-
node,
|
|
196
|
-
loc: {
|
|
197
|
-
start: {
|
|
198
|
-
line: endBracket.loc.end.line,
|
|
199
|
-
column: endBracket.loc.end.column
|
|
200
|
-
},
|
|
201
|
-
end: {
|
|
202
|
-
line: rightToken.loc.start.line,
|
|
203
|
-
column: rightToken.loc.start.column
|
|
204
|
-
}
|
|
205
|
-
},
|
|
206
|
-
messageId: "genericSpacingMismatch",
|
|
207
|
-
*fix(fixer) {
|
|
208
|
-
yield fixer.removeRange([endBracket.range[1], rightToken.range[0]]);
|
|
209
|
-
}
|
|
210
|
-
});
|
|
211
|
-
}
|
|
212
|
-
}
|
|
213
|
-
},
|
|
214
|
-
// add space around = in type Foo<T = true>
|
|
215
|
-
TSTypeParameter: (node) => {
|
|
216
|
-
if (!node.default) {
|
|
217
|
-
return;
|
|
218
|
-
}
|
|
219
|
-
const endNode = node.constraint ?? node.name;
|
|
220
|
-
const from = endNode.range[1];
|
|
221
|
-
const to = node.default.range[0];
|
|
222
|
-
const spaceAndEqual = sourceCode.text.slice(from, to);
|
|
223
|
-
if (spaceAndEqual !== " = ") {
|
|
224
|
-
const preSpace = spaceAndEqual.match(/^(\s*)/)?.[0];
|
|
225
|
-
const postSpace = spaceAndEqual.match(/(\s*)$/)?.[0];
|
|
226
|
-
if (preSpace.length !== 1) {
|
|
227
|
-
context.report({
|
|
228
|
-
*fix(fixer) {
|
|
229
|
-
yield fixer.replaceTextRange([from, from + preSpace.length], " ");
|
|
230
|
-
},
|
|
231
|
-
loc: {
|
|
232
|
-
start: {
|
|
233
|
-
line: node.loc.start.line,
|
|
234
|
-
column: node.loc.start.column + 1
|
|
235
|
-
},
|
|
236
|
-
end: {
|
|
237
|
-
line: node.loc.end.line,
|
|
238
|
-
column: node.loc.end.column - 2 - postSpace.length
|
|
239
|
-
}
|
|
240
|
-
},
|
|
241
|
-
node,
|
|
242
|
-
messageId: "genericSpacingMismatch"
|
|
243
|
-
});
|
|
244
|
-
}
|
|
245
|
-
if (postSpace.length !== 1) {
|
|
246
|
-
context.report({
|
|
247
|
-
*fix(fixer) {
|
|
248
|
-
yield fixer.replaceTextRange([to - postSpace.length, to], " ");
|
|
249
|
-
},
|
|
250
|
-
loc: {
|
|
251
|
-
start: {
|
|
252
|
-
line: node.loc.start.line,
|
|
253
|
-
column: node.loc.start.column + 2 + preSpace.length
|
|
254
|
-
},
|
|
255
|
-
end: {
|
|
256
|
-
line: node.loc.end.line,
|
|
257
|
-
column: node.loc.end.column - 1
|
|
258
|
-
}
|
|
259
|
-
},
|
|
260
|
-
messageId: "genericSpacingMismatch"
|
|
261
|
-
});
|
|
262
|
-
}
|
|
263
|
-
}
|
|
264
|
-
},
|
|
265
|
-
// type T = Generic< any >
|
|
266
|
-
TSTypeParameterInstantiation: (node) => {
|
|
267
|
-
const params = node.params;
|
|
268
|
-
for (const param of params) {
|
|
269
|
-
const leftToken = sourceCode.getTokenBefore(param);
|
|
270
|
-
const rightToken = sourceCode.getTokenAfter(param);
|
|
271
|
-
const hasSpacingBeforeParam = leftToken.value === "<" ? sourceCode.isSpaceBetween(leftToken, param) : false;
|
|
272
|
-
const hasSpacingAfterParam = rightToken.value === ">" ? sourceCode.isSpaceBetween(param, rightToken) : false;
|
|
273
|
-
if (hasSpacingBeforeParam && leftToken.loc.end.line === param.loc.start.line) {
|
|
274
|
-
context.report({
|
|
275
|
-
node,
|
|
276
|
-
loc: {
|
|
277
|
-
start: {
|
|
278
|
-
line: leftToken.loc.end.line,
|
|
279
|
-
column: leftToken.loc.end.column
|
|
280
|
-
},
|
|
281
|
-
end: {
|
|
282
|
-
line: param.loc.start.line,
|
|
283
|
-
column: param.loc.start.column
|
|
284
|
-
}
|
|
285
|
-
},
|
|
286
|
-
messageId: "genericSpacingMismatch",
|
|
287
|
-
*fix(fixer) {
|
|
288
|
-
yield fixer.removeRange([leftToken.range[1], param.range[0]]);
|
|
289
|
-
}
|
|
290
|
-
});
|
|
291
|
-
}
|
|
292
|
-
if (hasSpacingAfterParam && param.loc.end.line === rightToken.loc.start.line) {
|
|
293
|
-
context.report({
|
|
294
|
-
node,
|
|
295
|
-
loc: {
|
|
296
|
-
start: {
|
|
297
|
-
line: param.loc.end.line,
|
|
298
|
-
column: param.loc.end.column
|
|
299
|
-
},
|
|
300
|
-
end: {
|
|
301
|
-
line: rightToken.loc.start.line,
|
|
302
|
-
column: rightToken.loc.start.column
|
|
303
|
-
}
|
|
304
|
-
},
|
|
305
|
-
messageId: "genericSpacingMismatch",
|
|
306
|
-
*fix(fixer) {
|
|
307
|
-
yield fixer.removeRange([param.range[1], rightToken.range[0]]);
|
|
308
|
-
}
|
|
309
|
-
});
|
|
310
|
-
}
|
|
311
|
-
}
|
|
312
|
-
},
|
|
313
|
-
// Add spaces before extends
|
|
314
|
-
// interface a {}
|
|
315
|
-
// interface A<B extends 1>extends a {}
|
|
316
|
-
// Fix to: interface A<B extends 1> extends a {}
|
|
317
|
-
TSInterfaceDeclaration: (node) => {
|
|
318
|
-
if (!node.extends || !node.typeParameters) {
|
|
319
|
-
return;
|
|
320
|
-
}
|
|
321
|
-
const { typeParameters } = node;
|
|
322
|
-
const extendsKeywordStart = typeParameters.range[1];
|
|
323
|
-
const extendsKeywordEnd = node.extends[0].range[0];
|
|
324
|
-
const extendsText = text.slice(extendsKeywordStart, extendsKeywordEnd);
|
|
325
|
-
if (!/^\s+/.test(extendsText)) {
|
|
326
|
-
context.report({
|
|
327
|
-
loc: {
|
|
328
|
-
start: {
|
|
329
|
-
line: typeParameters.loc.end.line,
|
|
330
|
-
column: typeParameters.loc.end.column
|
|
331
|
-
},
|
|
332
|
-
end: {
|
|
333
|
-
line: typeParameters.loc.end.line,
|
|
334
|
-
column: typeParameters.loc.end.column + 7
|
|
335
|
-
}
|
|
336
|
-
},
|
|
337
|
-
node,
|
|
338
|
-
messageId: "genericSpacingMismatch",
|
|
339
|
-
*fix(fixer) {
|
|
340
|
-
yield fixer.replaceTextRange([extendsKeywordStart, extendsKeywordEnd - 8], " ");
|
|
341
|
-
}
|
|
342
|
-
});
|
|
343
|
-
}
|
|
344
|
-
}
|
|
345
|
-
};
|
|
346
|
-
}
|
|
347
|
-
});
|
|
348
|
-
|
|
349
|
-
const RULE_NAME$6 = "import-dedupe";
|
|
5
|
+
const RULE_NAME$2 = "import-dedupe";
|
|
350
6
|
const importDedupe = createEslintRule({
|
|
351
|
-
name: RULE_NAME$
|
|
7
|
+
name: RULE_NAME$2,
|
|
352
8
|
meta: {
|
|
353
9
|
type: "problem",
|
|
354
10
|
docs: {
|
|
@@ -396,9 +52,9 @@ const importDedupe = createEslintRule({
|
|
|
396
52
|
}
|
|
397
53
|
});
|
|
398
54
|
|
|
399
|
-
const RULE_NAME$
|
|
55
|
+
const RULE_NAME$1 = "no-inline-type-import";
|
|
400
56
|
const noInlineTypeImport = createEslintRule({
|
|
401
|
-
name: RULE_NAME$
|
|
57
|
+
name: RULE_NAME$1,
|
|
402
58
|
meta: {
|
|
403
59
|
type: "layout",
|
|
404
60
|
docs: {
|
|
@@ -448,450 +104,34 @@ import { ${valueSpecifiersText} } from "${node.source.value}";`
|
|
|
448
104
|
}
|
|
449
105
|
});
|
|
450
106
|
|
|
451
|
-
const RULE_NAME
|
|
452
|
-
const
|
|
453
|
-
name: RULE_NAME$4,
|
|
454
|
-
meta: {
|
|
455
|
-
type: "layout",
|
|
456
|
-
docs: {
|
|
457
|
-
description: "Space before paren",
|
|
458
|
-
recommended: "error"
|
|
459
|
-
},
|
|
460
|
-
fixable: "whitespace",
|
|
461
|
-
schema: [],
|
|
462
|
-
messages: {
|
|
463
|
-
noSpaceBeforeParen: "Expected no space before paren"
|
|
464
|
-
}
|
|
465
|
-
},
|
|
466
|
-
defaultOptions: [],
|
|
467
|
-
create: (context) => {
|
|
468
|
-
const sourceCode = context.getSourceCode();
|
|
469
|
-
const text = sourceCode.getText();
|
|
470
|
-
return {
|
|
471
|
-
ImportExpression(node) {
|
|
472
|
-
const sourceRange = node.source.range;
|
|
473
|
-
const parenStart = sourceRange[0] - 1;
|
|
474
|
-
const importEnd = node.range[0] + 6;
|
|
475
|
-
const textBetweenImportAndParenRange = [importEnd, parenStart];
|
|
476
|
-
const textBetweenImportAndParen = text.slice(...textBetweenImportAndParenRange);
|
|
477
|
-
if (textBetweenImportAndParen.length > 0) {
|
|
478
|
-
context.report({
|
|
479
|
-
node,
|
|
480
|
-
messageId: "noSpaceBeforeParen",
|
|
481
|
-
*fix(fixer) {
|
|
482
|
-
yield fixer.removeRange(textBetweenImportAndParenRange);
|
|
483
|
-
}
|
|
484
|
-
});
|
|
485
|
-
}
|
|
486
|
-
},
|
|
487
|
-
CallExpression(node) {
|
|
488
|
-
let caller = "property" in node.callee ? node.callee.property : node.callee;
|
|
489
|
-
if (caller.type === AST_NODE_TYPES.TSInstantiationExpression && "property" in caller.expression) {
|
|
490
|
-
caller = caller.expression.property;
|
|
491
|
-
}
|
|
492
|
-
const callerEnd = ref(caller.range[1]);
|
|
493
|
-
const textAfterCaller = computed(() => text.slice(callerEnd.value));
|
|
494
|
-
const parenStart = ref(callerEnd.value + textAfterCaller.value.indexOf("("));
|
|
495
|
-
const textBetweenFunctionNameAndParenRange = computed(
|
|
496
|
-
() => [callerEnd.value, parenStart.value]
|
|
497
|
-
);
|
|
498
|
-
const textBetweenFunctionNameAndParen = computed(
|
|
499
|
-
() => text.slice(...textBetweenFunctionNameAndParenRange.value)
|
|
500
|
-
);
|
|
501
|
-
const hasGenerics = computed(() => /^\s*</.test(textBetweenFunctionNameAndParen.value));
|
|
502
|
-
const hasIndex = computed(() => textBetweenFunctionNameAndParen.value.startsWith("]"));
|
|
503
|
-
if (hasIndex.value) {
|
|
504
|
-
callerEnd.value += 1;
|
|
505
|
-
}
|
|
506
|
-
if (node.optional) {
|
|
507
|
-
parenStart.value = callerEnd.value + textAfterCaller.value.indexOf("(");
|
|
508
|
-
}
|
|
509
|
-
const spaces = /(\s*)$/.exec(textBetweenFunctionNameAndParen.value)[1];
|
|
510
|
-
if (!hasGenerics.value) {
|
|
511
|
-
if (spaces.length > 0 && textBetweenFunctionNameAndParen.value !== "?.") {
|
|
512
|
-
const textBeforeSpaces = textBetweenFunctionNameAndParen.value.slice(
|
|
513
|
-
0,
|
|
514
|
-
textBetweenFunctionNameAndParen.value.length - spaces.length
|
|
515
|
-
);
|
|
516
|
-
context.report({
|
|
517
|
-
node,
|
|
518
|
-
messageId: "noSpaceBeforeParen",
|
|
519
|
-
*fix(fixer) {
|
|
520
|
-
yield fixer.replaceTextRange(
|
|
521
|
-
textBetweenFunctionNameAndParenRange.value,
|
|
522
|
-
textBeforeSpaces + (node.optional ? "?." : "")
|
|
523
|
-
);
|
|
524
|
-
}
|
|
525
|
-
});
|
|
526
|
-
}
|
|
527
|
-
} else {
|
|
528
|
-
const preSpaces = /^(\s*)/.exec(textBetweenFunctionNameAndParen.value)[1];
|
|
529
|
-
const postSpaces = /(\s*)$/.exec(textBetweenFunctionNameAndParen.value)[1];
|
|
530
|
-
const spacesBeforeOptionalMark = /(\s*)\?\./.exec(textBetweenFunctionNameAndParen.value)?.[1] ?? "";
|
|
531
|
-
if (preSpaces.length > 0) {
|
|
532
|
-
context.report({
|
|
533
|
-
node,
|
|
534
|
-
messageId: "noSpaceBeforeParen",
|
|
535
|
-
*fix(fixer) {
|
|
536
|
-
yield fixer.removeRange([callerEnd.value, callerEnd.value + preSpaces.length]);
|
|
537
|
-
}
|
|
538
|
-
});
|
|
539
|
-
}
|
|
540
|
-
if (postSpaces.length > 0) {
|
|
541
|
-
context.report({
|
|
542
|
-
node,
|
|
543
|
-
messageId: "noSpaceBeforeParen",
|
|
544
|
-
*fix(fixer) {
|
|
545
|
-
yield fixer.removeRange([parenStart.value - postSpaces.length, parenStart.value]);
|
|
546
|
-
}
|
|
547
|
-
});
|
|
548
|
-
}
|
|
549
|
-
if (spacesBeforeOptionalMark.length > 0 && !textBetweenFunctionNameAndParen.value.endsWith(" ")) {
|
|
550
|
-
context.report({
|
|
551
|
-
node,
|
|
552
|
-
messageId: "noSpaceBeforeParen",
|
|
553
|
-
*fix(fixer) {
|
|
554
|
-
yield fixer.removeRange([parenStart.value - spacesBeforeOptionalMark.length - 2, parenStart.value - 2]);
|
|
555
|
-
}
|
|
556
|
-
});
|
|
557
|
-
}
|
|
558
|
-
}
|
|
559
|
-
},
|
|
560
|
-
NewExpression(node) {
|
|
561
|
-
const calleeEnd = node.callee.range[1];
|
|
562
|
-
const textAfterCallee = text.slice(calleeEnd);
|
|
563
|
-
const parenStart = calleeEnd + textAfterCallee.indexOf("(");
|
|
564
|
-
const textBetweenCalleeAndParenRange = [calleeEnd, parenStart];
|
|
565
|
-
const textBetweenCalleeAndParen = text.slice(...textBetweenCalleeAndParenRange);
|
|
566
|
-
const hasGenerics = /^\s*</.test(textBetweenCalleeAndParen);
|
|
567
|
-
if (!hasGenerics && textBetweenCalleeAndParen.length > 0) {
|
|
568
|
-
context.report({
|
|
569
|
-
node,
|
|
570
|
-
messageId: "noSpaceBeforeParen",
|
|
571
|
-
*fix(fixer) {
|
|
572
|
-
yield fixer.removeRange(textBetweenCalleeAndParenRange);
|
|
573
|
-
}
|
|
574
|
-
});
|
|
575
|
-
} else if (hasGenerics) {
|
|
576
|
-
const preSpaces = /^(\s*)/.exec(textBetweenCalleeAndParen)[1];
|
|
577
|
-
const postSpaces = /(\s*)$/.exec(textBetweenCalleeAndParen)[1];
|
|
578
|
-
if (preSpaces.length > 0) {
|
|
579
|
-
context.report({
|
|
580
|
-
node,
|
|
581
|
-
messageId: "noSpaceBeforeParen",
|
|
582
|
-
*fix(fixer) {
|
|
583
|
-
yield fixer.removeRange([calleeEnd, calleeEnd + preSpaces.length]);
|
|
584
|
-
}
|
|
585
|
-
});
|
|
586
|
-
}
|
|
587
|
-
if (postSpaces.length > 0) {
|
|
588
|
-
context.report({
|
|
589
|
-
node,
|
|
590
|
-
messageId: "noSpaceBeforeParen",
|
|
591
|
-
*fix(fixer) {
|
|
592
|
-
yield fixer.removeRange([parenStart - postSpaces.length, parenStart]);
|
|
593
|
-
}
|
|
594
|
-
});
|
|
595
|
-
}
|
|
596
|
-
}
|
|
597
|
-
}
|
|
598
|
-
};
|
|
599
|
-
}
|
|
600
|
-
});
|
|
601
|
-
|
|
602
|
-
const RULE_NAME$3 = "semi-spacing";
|
|
603
|
-
const semiSpacing = createEslintRule({
|
|
604
|
-
name: RULE_NAME$3,
|
|
605
|
-
meta: {
|
|
606
|
-
type: "layout",
|
|
607
|
-
docs: {
|
|
608
|
-
description: "Semicolon spacing in types",
|
|
609
|
-
recommended: "error"
|
|
610
|
-
},
|
|
611
|
-
fixable: "whitespace",
|
|
612
|
-
schema: [],
|
|
613
|
-
messages: {
|
|
614
|
-
noSpaceBeforeSemi: "Expected no space before semicolon"
|
|
615
|
-
}
|
|
616
|
-
},
|
|
617
|
-
defaultOptions: [],
|
|
618
|
-
create: (context) => {
|
|
619
|
-
const sourceCode = context.getSourceCode();
|
|
620
|
-
return {
|
|
621
|
-
TSTypeAliasDeclaration(node) {
|
|
622
|
-
const leftToken = node.typeAnnotation;
|
|
623
|
-
const rightToken = sourceCode.getTokenAfter(node.typeAnnotation);
|
|
624
|
-
if (!rightToken || rightToken.type !== AST_TOKEN_TYPES.Punctuator || rightToken.value !== ";") {
|
|
625
|
-
return;
|
|
626
|
-
}
|
|
627
|
-
const hasSpacing = sourceCode.isSpaceBetween(leftToken, rightToken);
|
|
628
|
-
if (hasSpacing) {
|
|
629
|
-
context.report({
|
|
630
|
-
loc: {
|
|
631
|
-
start: {
|
|
632
|
-
line: leftToken.loc.end.line,
|
|
633
|
-
column: leftToken.loc.end.column
|
|
634
|
-
},
|
|
635
|
-
end: {
|
|
636
|
-
line: rightToken.loc.start.line,
|
|
637
|
-
column: rightToken.loc.start.column
|
|
638
|
-
}
|
|
639
|
-
},
|
|
640
|
-
node,
|
|
641
|
-
messageId: "noSpaceBeforeSemi",
|
|
642
|
-
*fix(fixer) {
|
|
643
|
-
yield fixer.removeRange([leftToken.range[1], rightToken.range[0]]);
|
|
644
|
-
}
|
|
645
|
-
});
|
|
646
|
-
}
|
|
647
|
-
}
|
|
648
|
-
};
|
|
649
|
-
}
|
|
650
|
-
});
|
|
651
|
-
|
|
652
|
-
const RULE_NAME$2 = "space-before-function-paren";
|
|
653
|
-
const spaceBeforeFunctionParen = createEslintRule({
|
|
654
|
-
name: RULE_NAME$2,
|
|
655
|
-
meta: {
|
|
656
|
-
type: "layout",
|
|
657
|
-
docs: {
|
|
658
|
-
description: "Enforce consistent spacing before function parenthesis",
|
|
659
|
-
recommended: false,
|
|
660
|
-
extendsBaseRule: true
|
|
661
|
-
},
|
|
662
|
-
fixable: "whitespace",
|
|
663
|
-
schema: [
|
|
664
|
-
{
|
|
665
|
-
oneOf: [
|
|
666
|
-
{
|
|
667
|
-
enum: ["always", "never"]
|
|
668
|
-
},
|
|
669
|
-
{
|
|
670
|
-
type: "object",
|
|
671
|
-
properties: {
|
|
672
|
-
anonymous: {
|
|
673
|
-
enum: ["always", "never", "ignore"]
|
|
674
|
-
},
|
|
675
|
-
named: {
|
|
676
|
-
enum: ["always", "never", "ignore"]
|
|
677
|
-
},
|
|
678
|
-
asyncArrow: {
|
|
679
|
-
enum: ["always", "never", "ignore"]
|
|
680
|
-
}
|
|
681
|
-
},
|
|
682
|
-
additionalProperties: false
|
|
683
|
-
}
|
|
684
|
-
]
|
|
685
|
-
}
|
|
686
|
-
],
|
|
687
|
-
messages: {
|
|
688
|
-
unexpected: "Unexpected space before function parentheses.",
|
|
689
|
-
missing: "Missing space before function parentheses."
|
|
690
|
-
}
|
|
691
|
-
},
|
|
692
|
-
defaultOptions: ["always"],
|
|
693
|
-
create(context, [firstOption]) {
|
|
694
|
-
const sourceCode = context.getSourceCode();
|
|
695
|
-
const baseConfig = typeof firstOption === "string" ? firstOption : "always";
|
|
696
|
-
const overrideConfig = typeof firstOption === "object" ? firstOption : {};
|
|
697
|
-
function isNamedFunction(node) {
|
|
698
|
-
if (node.id != null) {
|
|
699
|
-
return true;
|
|
700
|
-
}
|
|
701
|
-
const parent = node.parent;
|
|
702
|
-
return parent.type === AST_NODE_TYPES.MethodDefinition || parent.type === AST_NODE_TYPES.TSAbstractMethodDefinition || parent.type === AST_NODE_TYPES.Property && (parent.kind === "get" || parent.kind === "set" || parent.method);
|
|
703
|
-
}
|
|
704
|
-
function getConfigForFunction(node) {
|
|
705
|
-
if (node.type === AST_NODE_TYPES.ArrowFunctionExpression) {
|
|
706
|
-
if (node.async && util.isOpeningParenToken(sourceCode.getFirstToken(node, { skip: 1 }))) {
|
|
707
|
-
return overrideConfig.asyncArrow ?? baseConfig;
|
|
708
|
-
}
|
|
709
|
-
} else if (isNamedFunction(node)) {
|
|
710
|
-
return overrideConfig.named ?? baseConfig;
|
|
711
|
-
} else if (!node.generator) {
|
|
712
|
-
return overrideConfig.anonymous ?? baseConfig;
|
|
713
|
-
}
|
|
714
|
-
return "ignore";
|
|
715
|
-
}
|
|
716
|
-
function checkFunction(node) {
|
|
717
|
-
const functionConfig = getConfigForFunction(node);
|
|
718
|
-
if (functionConfig === "ignore") {
|
|
719
|
-
return;
|
|
720
|
-
}
|
|
721
|
-
let leftToken, rightToken;
|
|
722
|
-
if (node.typeParameters) {
|
|
723
|
-
leftToken = sourceCode.getLastToken(node.typeParameters);
|
|
724
|
-
rightToken = sourceCode.getTokenAfter(leftToken);
|
|
725
|
-
} else {
|
|
726
|
-
rightToken = sourceCode.getFirstToken(node, util.isOpeningParenToken);
|
|
727
|
-
leftToken = sourceCode.getTokenBefore(rightToken);
|
|
728
|
-
}
|
|
729
|
-
const hasSpacing = sourceCode.isSpaceBetween(leftToken, rightToken);
|
|
730
|
-
if (hasSpacing && functionConfig === "never") {
|
|
731
|
-
context.report({
|
|
732
|
-
node,
|
|
733
|
-
loc: {
|
|
734
|
-
start: leftToken.loc.end,
|
|
735
|
-
end: rightToken.loc.start
|
|
736
|
-
},
|
|
737
|
-
messageId: "unexpected",
|
|
738
|
-
fix: (fixer) => fixer.removeRange([leftToken.range[1], rightToken.range[0]])
|
|
739
|
-
});
|
|
740
|
-
} else if (!hasSpacing && functionConfig === "always" && !node.typeParameters) {
|
|
741
|
-
context.report({
|
|
742
|
-
node,
|
|
743
|
-
loc: rightToken.loc,
|
|
744
|
-
messageId: "missing",
|
|
745
|
-
fix: (fixer) => fixer.insertTextAfter(leftToken, " ")
|
|
746
|
-
});
|
|
747
|
-
}
|
|
748
|
-
}
|
|
749
|
-
return {
|
|
750
|
-
ArrowFunctionExpression: checkFunction,
|
|
751
|
-
FunctionDeclaration: checkFunction,
|
|
752
|
-
FunctionExpression: checkFunction,
|
|
753
|
-
TSEmptyBodyFunctionExpression: checkFunction,
|
|
754
|
-
TSDeclareFunction: checkFunction
|
|
755
|
-
};
|
|
756
|
-
}
|
|
757
|
-
});
|
|
758
|
-
|
|
759
|
-
const operatorOrAnyBracketOrKeywordRE = /^(\||&|\*|\+|\-|\/|%|<|>|<=|>=|==|!=|===|!==|\[|\(|\{|as|extends|implements|keyof|new|readonly|typeof|unique|unknown)/;
|
|
760
|
-
const RULE_NAME$1 = "space-between-generic-and-paren";
|
|
761
|
-
const spaceBetweenGenericAndParen = createEslintRule({
|
|
762
|
-
name: RULE_NAME$1,
|
|
763
|
-
meta: {
|
|
764
|
-
type: "layout",
|
|
765
|
-
docs: {
|
|
766
|
-
description: "Spaces between generic type parameters and paren",
|
|
767
|
-
recommended: "error"
|
|
768
|
-
},
|
|
769
|
-
fixable: "whitespace",
|
|
770
|
-
schema: [],
|
|
771
|
-
messages: {
|
|
772
|
-
noSpaceBetweenGenericAndParen: "Expected no space between generic type parameters and paren"
|
|
773
|
-
}
|
|
774
|
-
},
|
|
775
|
-
defaultOptions: [],
|
|
776
|
-
create: (context) => {
|
|
777
|
-
const sourceCode = context.getSourceCode();
|
|
778
|
-
const text = sourceCode.text;
|
|
779
|
-
return {
|
|
780
|
-
TSTypeParameter: (node) => {
|
|
781
|
-
const spaceStartRange = node.range[1] + 1;
|
|
782
|
-
const post = text.slice(spaceStartRange);
|
|
783
|
-
const postSpace = post.match(/^(\s*)/)?.[0];
|
|
784
|
-
const postEqual = post.slice(postSpace.length).match(/^(=)/)?.[0];
|
|
785
|
-
const postComma = text.slice(node.range[1]).match(/^(,)/)?.[0];
|
|
786
|
-
const postQuestionMark = text.slice(spaceStartRange + postSpace.length).match(/^(\?)/)?.[0];
|
|
787
|
-
const postOperatorOrAnyBracketOrKeyword = text.slice(spaceStartRange + postSpace.length).match(operatorOrAnyBracketOrKeywordRE)?.[0];
|
|
788
|
-
if (postSpace?.length && !postEqual && !postComma && !postQuestionMark && !postOperatorOrAnyBracketOrKeyword && node.parent.type !== AST_NODE_TYPES.TSInferType) {
|
|
789
|
-
context.report({
|
|
790
|
-
loc: {
|
|
791
|
-
start: {
|
|
792
|
-
line: node.loc.end.line,
|
|
793
|
-
column: node.loc.end.column + 1
|
|
794
|
-
},
|
|
795
|
-
end: {
|
|
796
|
-
line: node.loc.end.line,
|
|
797
|
-
column: node.loc.end.column + 1 + postSpace.length
|
|
798
|
-
}
|
|
799
|
-
},
|
|
800
|
-
node,
|
|
801
|
-
messageId: "noSpaceBetweenGenericAndParen",
|
|
802
|
-
*fix(fixer) {
|
|
803
|
-
yield fixer.replaceTextRange([spaceStartRange, spaceStartRange + postSpace.length], "");
|
|
804
|
-
}
|
|
805
|
-
});
|
|
806
|
-
}
|
|
807
|
-
if (node.parent?.parent.type === AST_NODE_TYPES.FunctionDeclaration) {
|
|
808
|
-
const spaceEndRange = node.range[0] - 1;
|
|
809
|
-
const pre = sourceCode.text.slice(0, spaceEndRange);
|
|
810
|
-
const preSpace = pre.match(/(\s+)$/)?.[0];
|
|
811
|
-
if (preSpace?.length) {
|
|
812
|
-
context.report({
|
|
813
|
-
loc: {
|
|
814
|
-
start: {
|
|
815
|
-
line: node.loc.start.line,
|
|
816
|
-
column: node.loc.start.column - preSpace.length
|
|
817
|
-
},
|
|
818
|
-
end: {
|
|
819
|
-
line: node.loc.start.line,
|
|
820
|
-
column: node.loc.start.column - 1
|
|
821
|
-
}
|
|
822
|
-
},
|
|
823
|
-
node,
|
|
824
|
-
messageId: "noSpaceBetweenGenericAndParen",
|
|
825
|
-
*fix(fixer) {
|
|
826
|
-
yield fixer.replaceTextRange([spaceEndRange - preSpace.length, spaceEndRange], "");
|
|
827
|
-
}
|
|
828
|
-
});
|
|
829
|
-
}
|
|
830
|
-
}
|
|
831
|
-
}
|
|
832
|
-
};
|
|
833
|
-
}
|
|
834
|
-
});
|
|
835
|
-
|
|
836
|
-
const RULE_NAME = "space-in-empty-block";
|
|
837
|
-
const spaceInEmptyBlock = createEslintRule({
|
|
107
|
+
const RULE_NAME = "no-useless-template-string";
|
|
108
|
+
const noUselessTemplateString = createEslintRule({
|
|
838
109
|
name: RULE_NAME,
|
|
839
110
|
meta: {
|
|
840
|
-
type: "
|
|
111
|
+
type: "problem",
|
|
841
112
|
docs: {
|
|
842
|
-
description: "
|
|
113
|
+
description: "No useless template string",
|
|
843
114
|
recommended: "error"
|
|
844
115
|
},
|
|
845
|
-
fixable: "
|
|
116
|
+
fixable: "code",
|
|
846
117
|
schema: [],
|
|
847
118
|
messages: {
|
|
848
|
-
|
|
119
|
+
noUselessTemplateString: "No useless template string"
|
|
849
120
|
}
|
|
850
121
|
},
|
|
851
122
|
defaultOptions: [],
|
|
852
123
|
create: (context) => {
|
|
853
|
-
const sourceCode = context.getSourceCode();
|
|
854
124
|
return {
|
|
855
|
-
|
|
856
|
-
|
|
857
|
-
|
|
858
|
-
}
|
|
859
|
-
const spaceStartRange = node.range[1] - 2;
|
|
860
|
-
const post = sourceCode.text.slice(spaceStartRange);
|
|
861
|
-
const postSpace = post.match(/^(\s*)/)?.[0];
|
|
862
|
-
if (postSpace?.length) {
|
|
125
|
+
TemplateLiteral(node) {
|
|
126
|
+
const hasNewline = node.quasis.some((n) => n.value.raw.includes("\n"));
|
|
127
|
+
if (node.expressions.length === 0 && !hasNewline) {
|
|
863
128
|
context.report({
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
|
|
867
|
-
|
|
868
|
-
|
|
869
|
-
}
|
|
870
|
-
},
|
|
871
|
-
messageId: "noSpaceInEmptyBlock",
|
|
872
|
-
*fix(fixer) {
|
|
873
|
-
yield fixer.replaceTextRange([node.range[0] + 1, spaceStartRange + postSpace.length], "");
|
|
874
|
-
}
|
|
875
|
-
});
|
|
876
|
-
}
|
|
877
|
-
const spaceEndRange = node.range[0] + 1;
|
|
878
|
-
const pre = sourceCode.text.slice(0, spaceEndRange);
|
|
879
|
-
const preSpace = pre.match(/(\s+)$/)?.[0];
|
|
880
|
-
if (preSpace?.length) {
|
|
881
|
-
context.report({
|
|
882
|
-
loc: {
|
|
883
|
-
start: {
|
|
884
|
-
line: node.loc.start.line,
|
|
885
|
-
column: node.loc.start.column - preSpace.length
|
|
886
|
-
},
|
|
887
|
-
end: {
|
|
888
|
-
line: node.loc.start.line,
|
|
889
|
-
column: node.loc.start.column
|
|
890
|
-
}
|
|
891
|
-
},
|
|
892
|
-
messageId: "noSpaceInEmptyBlock",
|
|
893
|
-
*fix(fixer) {
|
|
894
|
-
yield fixer.replaceTextRange([spaceEndRange - preSpace.length, spaceEndRange], "");
|
|
129
|
+
node,
|
|
130
|
+
messageId: "noUselessTemplateString",
|
|
131
|
+
fix(fixer) {
|
|
132
|
+
const s = node.range[0];
|
|
133
|
+
const e = node.range[1];
|
|
134
|
+
return fixer.replaceTextRange([s, e], `"${node.quasis[0].value.raw}"`);
|
|
895
135
|
}
|
|
896
136
|
});
|
|
897
137
|
}
|
|
@@ -903,14 +143,8 @@ const spaceInEmptyBlock = createEslintRule({
|
|
|
903
143
|
const index = {
|
|
904
144
|
rules: {
|
|
905
145
|
"import-dedupe": importDedupe,
|
|
906
|
-
"generic-spacing": genericSpacing,
|
|
907
|
-
"space-between-generic-and-paren": spaceBetweenGenericAndParen,
|
|
908
|
-
"space-in-empty-block": spaceInEmptyBlock,
|
|
909
|
-
"semi-spacing": semiSpacing,
|
|
910
146
|
"no-inline-type-import": noInlineTypeImport,
|
|
911
|
-
"no-
|
|
912
|
-
"space-before-function-paren": spaceBeforeFunctionParen,
|
|
913
|
-
"array-bracket-spacing": arrayBracketSpacing
|
|
147
|
+
"no-useless-template-string": noUselessTemplateString
|
|
914
148
|
}
|
|
915
149
|
};
|
|
916
150
|
|