eslint-plugin-lube 0.8.0 → 0.9.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/CHANGELOG.md +95 -0
- package/README.md +17 -4
- package/docs/closures-last.md +34 -0
- package/docs/indent.md +102 -0
- package/docs/no-ambiguous-start.md +23 -0
- package/docs/no-loose-types.md +25 -0
- package/docs/no-typedef.md +24 -0
- package/docs/pretty-jsdoc-lines.md +30 -0
- package/docs/pretty-parens.md +59 -0
- package/docs/require-returns.md +21 -0
- package/docs/svelte-naming-convention.md +5 -6
- package/package.json +2 -7
- package/src/index.js +78 -19
- package/src/rules/ascii-order.js +113 -127
- package/src/rules/closures-last.js +323 -0
- package/src/rules/indent.js +84 -0
- package/src/rules/no-ambiguous-start.js +42 -0
- package/src/rules/no-loose-types.js +127 -0
- package/src/rules/no-typedef.js +44 -0
- package/src/rules/prefer-param-tag.js +35 -35
- package/src/rules/prefer-type-tag.js +29 -29
- package/src/rules/pretty-imports.js +23 -23
- package/src/rules/pretty-jsdoc-casting.js +39 -39
- package/src/rules/pretty-jsdoc-lines.js +104 -0
- package/src/rules/pretty-parens.js +280 -0
- package/src/rules/pretty-sequence.js +79 -95
- package/src/rules/pretty-ternary.js +27 -31
- package/src/rules/require-returns.js +190 -0
- package/src/rules/svelte-naming-convention.js +457 -546
- package/src/utils/accept_cr_eol.js +36 -0
- package/src/utils/indent_model.js +1596 -0
- package/src/utils/jsdoc_tags.js +30 -0
- package/src/utils/order_compare.js +17 -0
- package/src/utils/rule_options.js +30 -0
- package/src/utils/skip_unchanged_fixes.js +3 -3
- package/src/utils/source_text.js +80 -255
- package/src/utils/split_declarations.js +35 -14
- package/src/utils/trim_fixes.js +108 -0
- package/types/index.d.ts.map +1 -1
package/src/index.js
CHANGED
|
@@ -1,21 +1,32 @@
|
|
|
1
1
|
import ascii_order from "./rules/ascii-order.js"
|
|
2
|
+
import closures_last from "./rules/closures-last.js"
|
|
3
|
+
import indent from "./rules/indent.js"
|
|
4
|
+
import no_ambiguous_start from "./rules/no-ambiguous-start.js"
|
|
5
|
+
import no_loose_types from "./rules/no-loose-types.js"
|
|
6
|
+
import no_typedef from "./rules/no-typedef.js"
|
|
2
7
|
import prefer_param_tag from "./rules/prefer-param-tag.js"
|
|
3
8
|
import prefer_type_tag from "./rules/prefer-type-tag.js"
|
|
4
9
|
import pretty_imports from "./rules/pretty-imports.js"
|
|
5
10
|
import pretty_jsdoc_casting from "./rules/pretty-jsdoc-casting.js"
|
|
11
|
+
import pretty_jsdoc_lines from "./rules/pretty-jsdoc-lines.js"
|
|
12
|
+
import pretty_parens from "./rules/pretty-parens.js"
|
|
6
13
|
import pretty_sequence from "./rules/pretty-sequence.js"
|
|
7
14
|
import pretty_ternary from "./rules/pretty-ternary.js"
|
|
15
|
+
import require_returns from "./rules/require-returns.js"
|
|
8
16
|
import svelte_naming_convention from "./rules/svelte-naming-convention.js"
|
|
17
|
+
import { accept_cr_eol } from "./utils/accept_cr_eol.js"
|
|
9
18
|
import { keep_body_comments } from "./utils/keep_body_comments.js"
|
|
10
19
|
import {
|
|
11
20
|
keep_comment_order,
|
|
12
21
|
keep_comments
|
|
13
22
|
} from "./utils/keep_comments.js"
|
|
14
23
|
import { keep_line_breaks } from "./utils/keep_line_breaks.js"
|
|
24
|
+
import { record_options } from "./utils/rule_options.js"
|
|
15
25
|
import { skip_hole_commas } from "./utils/skip_hole_commas.js"
|
|
16
26
|
import { skip_optional_patterns } from "./utils/skip_optional_patterns.js"
|
|
17
27
|
import { skip_unchanged_fixes } from "./utils/skip_unchanged_fixes.js"
|
|
18
28
|
import { split_declarations } from "./utils/split_declarations.js"
|
|
29
|
+
import { trim_fixes } from "./utils/trim_fixes.js"
|
|
19
30
|
import stylistic_plugin from "@stylistic/eslint-plugin"
|
|
20
31
|
import { builtinRules } from "eslint/use-at-your-own-risk"
|
|
21
32
|
import { readFileSync } from "node:fs"
|
|
@@ -31,6 +42,12 @@ const manifest = JSON.parse(
|
|
|
31
42
|
"utf8"
|
|
32
43
|
)
|
|
33
44
|
)
|
|
45
|
+
const whole_comment_rules = new Set(
|
|
46
|
+
[
|
|
47
|
+
"pretty-jsdoc-lines",
|
|
48
|
+
"require-returns"
|
|
49
|
+
]
|
|
50
|
+
)
|
|
34
51
|
const brace_rules = /** @type {const} */([
|
|
35
52
|
"object-curly-newline",
|
|
36
53
|
"object-curly-spacing"
|
|
@@ -66,11 +83,6 @@ const strict_rules = {
|
|
|
66
83
|
"@stylistic/function-call-argument-newline": [ "error", "consistent" ],
|
|
67
84
|
"@stylistic/function-call-spacing": [ "error", "never" ],
|
|
68
85
|
"@stylistic/generator-star-spacing": [ "error", "after" ],
|
|
69
|
-
"@stylistic/indent": [
|
|
70
|
-
"error",
|
|
71
|
-
"tab",
|
|
72
|
-
{ "SwitchCase": 0 }
|
|
73
|
-
],
|
|
74
86
|
"@stylistic/jsx-quotes": [ "error", "prefer-double" ],
|
|
75
87
|
"@stylistic/key-spacing": [
|
|
76
88
|
"error",
|
|
@@ -152,13 +164,28 @@ const strict_rules = {
|
|
|
152
164
|
checkTests: true
|
|
153
165
|
}
|
|
154
166
|
],
|
|
167
|
+
"lube/closures-last": "error",
|
|
155
168
|
"lube/curly": [ "error", "all" ],
|
|
169
|
+
"lube/indent": [
|
|
170
|
+
"error",
|
|
171
|
+
"tab",
|
|
172
|
+
{
|
|
173
|
+
"SwitchCase": 0,
|
|
174
|
+
"binaryOperator": 1
|
|
175
|
+
}
|
|
176
|
+
],
|
|
177
|
+
"lube/no-ambiguous-start": "error",
|
|
178
|
+
"lube/no-loose-types": "error",
|
|
179
|
+
"lube/no-typedef": "error",
|
|
156
180
|
"lube/prefer-param-tag": "error",
|
|
157
181
|
"lube/prefer-type-tag": "error",
|
|
158
182
|
"lube/pretty-imports": "error",
|
|
159
183
|
"lube/pretty-jsdoc-casting": "error",
|
|
184
|
+
"lube/pretty-jsdoc-lines": "error",
|
|
185
|
+
"lube/pretty-parens": "error",
|
|
160
186
|
"lube/pretty-sequence": "error",
|
|
161
187
|
"lube/pretty-ternary": "error",
|
|
188
|
+
"lube/require-returns": "error",
|
|
162
189
|
"lube/svelte-naming-convention": "error",
|
|
163
190
|
"no-case-declarations": "off",
|
|
164
191
|
"no-console": "warn",
|
|
@@ -212,8 +239,15 @@ const recommended_rules = {
|
|
|
212
239
|
checkTests: false
|
|
213
240
|
}
|
|
214
241
|
],
|
|
242
|
+
"lube/indent": [
|
|
243
|
+
"error",
|
|
244
|
+
"tab",
|
|
245
|
+
{ "SwitchCase": 0 }
|
|
246
|
+
],
|
|
215
247
|
"lube/pretty-imports": [ "error", { maxLength: 80 } ],
|
|
216
248
|
"lube/pretty-jsdoc-casting": "error",
|
|
249
|
+
"lube/pretty-jsdoc-lines": "error",
|
|
250
|
+
"lube/pretty-parens": "error",
|
|
217
251
|
"lube/pretty-sequence": [ "error", { maxLength: 80 } ],
|
|
218
252
|
"lube/pretty-ternary": "error"
|
|
219
253
|
}
|
|
@@ -243,19 +277,39 @@ const plugin = {
|
|
|
243
277
|
name: "eslint-plugin-lube",
|
|
244
278
|
version: manifest.version
|
|
245
279
|
},
|
|
246
|
-
rules:
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
280
|
+
rules: Object.fromEntries(
|
|
281
|
+
Object.entries(
|
|
282
|
+
/** @type {Record<string, import("eslint").Rule.RuleModule>} */({
|
|
283
|
+
"ascii-order": ascii_order,
|
|
284
|
+
"closures-last": closures_last,
|
|
285
|
+
"curly": keep_body_comments(
|
|
286
|
+
/** @type {import("eslint").Rule.RuleModule} */(builtinRules.get("curly"))/**/
|
|
287
|
+
),
|
|
288
|
+
"indent": indent,
|
|
289
|
+
"no-ambiguous-start": no_ambiguous_start,
|
|
290
|
+
"no-loose-types": no_loose_types,
|
|
291
|
+
"no-typedef": no_typedef,
|
|
292
|
+
"prefer-param-tag": prefer_param_tag,
|
|
293
|
+
"prefer-type-tag": prefer_type_tag,
|
|
294
|
+
"pretty-imports": pretty_imports,
|
|
295
|
+
"pretty-jsdoc-casting": pretty_jsdoc_casting,
|
|
296
|
+
"pretty-jsdoc-lines": pretty_jsdoc_lines,
|
|
297
|
+
"pretty-parens": pretty_parens,
|
|
298
|
+
"pretty-sequence": pretty_sequence,
|
|
299
|
+
"pretty-ternary": pretty_ternary,
|
|
300
|
+
"require-returns": require_returns,
|
|
301
|
+
"svelte-naming-convention": svelte_naming_convention
|
|
302
|
+
})/**/
|
|
303
|
+
).map(
|
|
304
|
+
([ name, rule ]) => [
|
|
305
|
+
name,
|
|
306
|
+
record_options(
|
|
307
|
+
name,
|
|
308
|
+
rule.meta?.fixable && !whole_comment_rules.has(name) ? trim_fixes(rule) : rule
|
|
309
|
+
)
|
|
310
|
+
]
|
|
311
|
+
)
|
|
312
|
+
)
|
|
259
313
|
}
|
|
260
314
|
/** @type {Record<string, import("eslint").Rule.RuleModule>} */
|
|
261
315
|
const stylistic_rules = {
|
|
@@ -263,6 +317,9 @@ const stylistic_rules = {
|
|
|
263
317
|
"comma-style": skip_hole_commas(
|
|
264
318
|
/** @type {import("eslint").Rule.RuleModule} */(stylistic.rules?.["comma-style"])/**/
|
|
265
319
|
),
|
|
320
|
+
"eol-last": accept_cr_eol(
|
|
321
|
+
/** @type {import("eslint").Rule.RuleModule} */(stylistic.rules?.["eol-last"])/**/
|
|
322
|
+
),
|
|
266
323
|
"max-statements-per-line": split_declarations(
|
|
267
324
|
/** @type {import("eslint").Rule.RuleModule} */(stylistic.rules?.["max-statements-per-line"])/**/
|
|
268
325
|
),
|
|
@@ -298,7 +355,9 @@ const plugins = {
|
|
|
298
355
|
Object.entries(stylistic_rules).map(
|
|
299
356
|
([ name, rule ]) => [
|
|
300
357
|
name,
|
|
301
|
-
|
|
358
|
+
trim_fixes(
|
|
359
|
+
skip_unchanged_fixes(keep_line_breaks(rule))
|
|
360
|
+
)
|
|
302
361
|
]
|
|
303
362
|
)
|
|
304
363
|
)
|
package/src/rules/ascii-order.js
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { compare } from "../utils/order_compare.js"
|
|
1
2
|
import { create_source_text } from "../utils/source_text.js"
|
|
2
3
|
const not_static = Symbol("not static")
|
|
3
4
|
const portable_flags_regex = /^[gimsuy]*$/
|
|
@@ -59,22 +60,6 @@ const safe_constructors = new Set(
|
|
|
59
60
|
const closers = new Set([ ")", "]", "}" ])
|
|
60
61
|
const member_separators = new Set([ ",", ";" ])
|
|
61
62
|
const shebang_types = new Set([ "Hashbang", "Shebang" ])
|
|
62
|
-
/**
|
|
63
|
-
* @param {import("../../private.js").OrderEntry} a
|
|
64
|
-
* @param {import("../../private.js").OrderEntry} b
|
|
65
|
-
* @returns {number}
|
|
66
|
-
*/
|
|
67
|
-
function compare(a, b) {
|
|
68
|
-
const rank = (a.rank ?? 1) - (b.rank ?? 1)
|
|
69
|
-
if (rank) {
|
|
70
|
-
return rank
|
|
71
|
-
}
|
|
72
|
-
return a.name < b.name
|
|
73
|
-
? -1
|
|
74
|
-
: a.name > b.name
|
|
75
|
-
? 1
|
|
76
|
-
: 0
|
|
77
|
-
}
|
|
78
63
|
/**
|
|
79
64
|
* @param {import("../../private.js").Comment[]} comments
|
|
80
65
|
* @param {number} line
|
|
@@ -93,11 +78,13 @@ function count_same_line(comments, line) {
|
|
|
93
78
|
}
|
|
94
79
|
/**
|
|
95
80
|
* @param {import("eslint").Rule.RuleContext} context
|
|
81
|
+
* @returns {{ verify: (entries: import("../../private.js").OrderEntry[], message_id: string, layout: import("../../private.js").OrderLayout, get_level?: ((node: import("../../private.js").OrderNode) => number) | undefined) => void; }}
|
|
96
82
|
*/
|
|
97
83
|
function create_reorder(context) {
|
|
98
84
|
const source_code = context.sourceCode
|
|
99
85
|
const source = create_source_text(source_code)
|
|
100
86
|
const text = source.text
|
|
87
|
+
return { verify }
|
|
101
88
|
/**
|
|
102
89
|
* @param {import("../../private.js").OrderEntry} entry
|
|
103
90
|
* @param {import("../../private.js").OrderLayout} layout
|
|
@@ -216,11 +203,11 @@ function create_reorder(context) {
|
|
|
216
203
|
const has_tail = item.tail_start < item.after
|
|
217
204
|
if (
|
|
218
205
|
item.leading && !slot.break_before
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
206
|
+
|| i == 0 && slot.head && !slot.break_before
|
|
207
|
+
|| slot.header && item != slot
|
|
208
|
+
|| slot.tail_start < slot.after && !slot.break_after && (i < last_index || !slot.closes)
|
|
209
|
+
|| has_tail && !slot.break_after && (i < last_index || item.tail_line)
|
|
210
|
+
|| layout == "statement" && i < last_index && !item.terminated && !slot.break_after
|
|
224
211
|
) {
|
|
225
212
|
return null
|
|
226
213
|
}
|
|
@@ -302,7 +289,6 @@ function create_reorder(context) {
|
|
|
302
289
|
}
|
|
303
290
|
)
|
|
304
291
|
}
|
|
305
|
-
return { verify }
|
|
306
292
|
}
|
|
307
293
|
/**
|
|
308
294
|
* @param {import("../../private.js").OrderItem[]} items
|
|
@@ -409,6 +395,107 @@ export default {
|
|
|
409
395
|
const default_exports = new Set()
|
|
410
396
|
/** @type {Parameters<typeof verify>[]} */
|
|
411
397
|
const pending = []
|
|
398
|
+
/** @type {import("../../private.js").OrderRuleListener} */
|
|
399
|
+
const listener = {
|
|
400
|
+
BlockStatement: verify_statements,
|
|
401
|
+
ExportNamedDeclaration: node => {
|
|
402
|
+
if (check_names) {
|
|
403
|
+
verify_nodes(
|
|
404
|
+
node.specifiers,
|
|
405
|
+
get_specifier_name,
|
|
406
|
+
"names",
|
|
407
|
+
"sequence"
|
|
408
|
+
)
|
|
409
|
+
}
|
|
410
|
+
},
|
|
411
|
+
ImportDeclaration: node => {
|
|
412
|
+
if (check_names) {
|
|
413
|
+
verify_nodes(
|
|
414
|
+
node.specifiers,
|
|
415
|
+
get_specifier_name,
|
|
416
|
+
"names",
|
|
417
|
+
"sequence"
|
|
418
|
+
)
|
|
419
|
+
}
|
|
420
|
+
},
|
|
421
|
+
ObjectExpression: node => {
|
|
422
|
+
if (!check_keys) {
|
|
423
|
+
return
|
|
424
|
+
}
|
|
425
|
+
const condition = is_package_condition(node)
|
|
426
|
+
verify_nodes(
|
|
427
|
+
node.properties,
|
|
428
|
+
get_key_name,
|
|
429
|
+
condition ? "conditions" : "keys",
|
|
430
|
+
"sequence",
|
|
431
|
+
classify,
|
|
432
|
+
condition ? get_condition_rank : undefined
|
|
433
|
+
)
|
|
434
|
+
},
|
|
435
|
+
ObjectPattern: node => {
|
|
436
|
+
if (check_keys) {
|
|
437
|
+
/** @type {Map<import("../../private.js").OrderNode, string[]>} */
|
|
438
|
+
const targets = new Map()
|
|
439
|
+
/** @type {Set<string>} */
|
|
440
|
+
const seen = new Set()
|
|
441
|
+
/** @type {Set<string>} */
|
|
442
|
+
const repeated = new Set()
|
|
443
|
+
for (const property of node.properties) {
|
|
444
|
+
const names = collect_targets(property, [])
|
|
445
|
+
for (const name of new Set(names)) {
|
|
446
|
+
if (seen.has(name)) {
|
|
447
|
+
repeated.add(name)
|
|
448
|
+
}
|
|
449
|
+
seen.add(name)
|
|
450
|
+
}
|
|
451
|
+
targets.set(property, names)
|
|
452
|
+
}
|
|
453
|
+
verify_nodes(
|
|
454
|
+
node.properties,
|
|
455
|
+
get_key_name,
|
|
456
|
+
"keys",
|
|
457
|
+
"sequence",
|
|
458
|
+
property => targets.get(property)?.some(name => repeated.has(name))
|
|
459
|
+
? 2
|
|
460
|
+
: classify_pattern(property)
|
|
461
|
+
)
|
|
462
|
+
}
|
|
463
|
+
},
|
|
464
|
+
Program: node => {
|
|
465
|
+
collect_default_exports(node)
|
|
466
|
+
verify_statements(node)
|
|
467
|
+
},
|
|
468
|
+
"Program:exit": () => {
|
|
469
|
+
for (let i = pending.length - 1; i >= 0; i--) {
|
|
470
|
+
verify(
|
|
471
|
+
.../** @type {Parameters<typeof verify>} */(pending[i])/**/
|
|
472
|
+
)
|
|
473
|
+
}
|
|
474
|
+
},
|
|
475
|
+
StaticBlock: verify_statements,
|
|
476
|
+
TSInterfaceBody: node => {
|
|
477
|
+
if (check_keys) {
|
|
478
|
+
verify_nodes(
|
|
479
|
+
node.body,
|
|
480
|
+
get_key_name,
|
|
481
|
+
"keys",
|
|
482
|
+
"member"
|
|
483
|
+
)
|
|
484
|
+
}
|
|
485
|
+
},
|
|
486
|
+
TSModuleBlock: verify_statements,
|
|
487
|
+
TSTypeLiteral: node => {
|
|
488
|
+
if (check_keys) {
|
|
489
|
+
verify_nodes(
|
|
490
|
+
node.members,
|
|
491
|
+
get_key_name,
|
|
492
|
+
"keys",
|
|
493
|
+
"member"
|
|
494
|
+
)
|
|
495
|
+
}
|
|
496
|
+
}
|
|
497
|
+
}
|
|
498
|
+
return /** @type {import("eslint").Rule.RuleListener} */(/** @type {unknown} */(listener))/**/
|
|
412
499
|
/**
|
|
413
500
|
* @param {import("../../private.js").OrderNode} node
|
|
414
501
|
* @returns {number}
|
|
@@ -534,8 +621,8 @@ export default {
|
|
|
534
621
|
const args = node.arguments.map(static_value)
|
|
535
622
|
if (
|
|
536
623
|
args.includes(not_static)
|
|
537
|
-
|
|
538
|
-
|
|
624
|
+
|| (callee.name.includes("Array") || callee.name == "DataView") && args.some(is_large)
|
|
625
|
+
|| callee.name == "RegExp" && !is_portable_regexp(args)
|
|
539
626
|
) {
|
|
540
627
|
return not_static
|
|
541
628
|
}
|
|
@@ -694,8 +781,8 @@ export default {
|
|
|
694
781
|
const parent = /** @type {import("eslint").Rule.Node} */(declaration)/**/.parent
|
|
695
782
|
if (
|
|
696
783
|
parent?.type == "SwitchCase"
|
|
697
|
-
|
|
698
|
-
|
|
784
|
+
|| parent?.parent?.type == "SwitchCase"
|
|
785
|
+
|| /** @type {[number, number]} */(node.range)/**/[0] < /** @type {[number, number]} */(declaration.range)/**/[1]
|
|
699
786
|
) {
|
|
700
787
|
return false
|
|
701
788
|
}
|
|
@@ -892,107 +979,6 @@ export default {
|
|
|
892
979
|
}
|
|
893
980
|
}
|
|
894
981
|
}
|
|
895
|
-
/** @type {import("../../private.js").OrderRuleListener} */
|
|
896
|
-
const listener = {
|
|
897
|
-
BlockStatement: verify_statements,
|
|
898
|
-
ExportNamedDeclaration: node => {
|
|
899
|
-
if (check_names) {
|
|
900
|
-
verify_nodes(
|
|
901
|
-
node.specifiers,
|
|
902
|
-
get_specifier_name,
|
|
903
|
-
"names",
|
|
904
|
-
"sequence"
|
|
905
|
-
)
|
|
906
|
-
}
|
|
907
|
-
},
|
|
908
|
-
ImportDeclaration: node => {
|
|
909
|
-
if (check_names) {
|
|
910
|
-
verify_nodes(
|
|
911
|
-
node.specifiers,
|
|
912
|
-
get_specifier_name,
|
|
913
|
-
"names",
|
|
914
|
-
"sequence"
|
|
915
|
-
)
|
|
916
|
-
}
|
|
917
|
-
},
|
|
918
|
-
ObjectExpression: node => {
|
|
919
|
-
if (!check_keys) {
|
|
920
|
-
return
|
|
921
|
-
}
|
|
922
|
-
const condition = is_package_condition(node)
|
|
923
|
-
verify_nodes(
|
|
924
|
-
node.properties,
|
|
925
|
-
get_key_name,
|
|
926
|
-
condition ? "conditions" : "keys",
|
|
927
|
-
"sequence",
|
|
928
|
-
classify,
|
|
929
|
-
condition ? get_condition_rank : undefined
|
|
930
|
-
)
|
|
931
|
-
},
|
|
932
|
-
ObjectPattern: node => {
|
|
933
|
-
if (check_keys) {
|
|
934
|
-
/** @type {Map<import("../../private.js").OrderNode, string[]>} */
|
|
935
|
-
const targets = new Map()
|
|
936
|
-
/** @type {Set<string>} */
|
|
937
|
-
const seen = new Set()
|
|
938
|
-
/** @type {Set<string>} */
|
|
939
|
-
const repeated = new Set()
|
|
940
|
-
for (const property of node.properties) {
|
|
941
|
-
const names = collect_targets(property, [])
|
|
942
|
-
for (const name of new Set(names)) {
|
|
943
|
-
if (seen.has(name)) {
|
|
944
|
-
repeated.add(name)
|
|
945
|
-
}
|
|
946
|
-
seen.add(name)
|
|
947
|
-
}
|
|
948
|
-
targets.set(property, names)
|
|
949
|
-
}
|
|
950
|
-
verify_nodes(
|
|
951
|
-
node.properties,
|
|
952
|
-
get_key_name,
|
|
953
|
-
"keys",
|
|
954
|
-
"sequence",
|
|
955
|
-
property => targets.get(property)?.some(name => repeated.has(name))
|
|
956
|
-
? 2
|
|
957
|
-
: classify_pattern(property)
|
|
958
|
-
)
|
|
959
|
-
}
|
|
960
|
-
},
|
|
961
|
-
Program: node => {
|
|
962
|
-
collect_default_exports(node)
|
|
963
|
-
verify_statements(node)
|
|
964
|
-
},
|
|
965
|
-
"Program:exit": () => {
|
|
966
|
-
for (let i = pending.length - 1; i >= 0; i--) {
|
|
967
|
-
verify(
|
|
968
|
-
.../** @type {Parameters<typeof verify>} */(pending[i])/**/
|
|
969
|
-
)
|
|
970
|
-
}
|
|
971
|
-
},
|
|
972
|
-
StaticBlock: verify_statements,
|
|
973
|
-
TSInterfaceBody: node => {
|
|
974
|
-
if (check_keys) {
|
|
975
|
-
verify_nodes(
|
|
976
|
-
node.body,
|
|
977
|
-
get_key_name,
|
|
978
|
-
"keys",
|
|
979
|
-
"member"
|
|
980
|
-
)
|
|
981
|
-
}
|
|
982
|
-
},
|
|
983
|
-
TSModuleBlock: verify_statements,
|
|
984
|
-
TSTypeLiteral: node => {
|
|
985
|
-
if (check_keys) {
|
|
986
|
-
verify_nodes(
|
|
987
|
-
node.members,
|
|
988
|
-
get_key_name,
|
|
989
|
-
"keys",
|
|
990
|
-
"member"
|
|
991
|
-
)
|
|
992
|
-
}
|
|
993
|
-
}
|
|
994
|
-
}
|
|
995
|
-
return /** @type {import("eslint").Rule.RuleListener} */(/** @type {unknown} */(listener))/**/
|
|
996
982
|
},
|
|
997
983
|
meta: {
|
|
998
984
|
docs: {
|