@timmo001/oxlint-rules 0.3.0 → 0.3.2
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/README.md +2 -1
- package/THIRD_PARTY_NOTICES.md +9 -0
- package/dist/cli.js +978 -83
- package/dist/configs/recommended-effect.js +1207 -312
- package/dist/configs/recommended.js +772 -70
- package/dist/upstream/anti-slop.js +765 -63
- package/dist/upstream/effect.js +196 -3
- package/package.json +5 -5
- package/vendor/anti-slop/src/effect/index.ts +8 -0
- package/vendor/anti-slop/src/effect/rules/no-manual-effect-error-tag.ts +52 -0
- package/vendor/anti-slop/src/effect/rules/no-manual-tag-comparison.ts +45 -0
- package/vendor/anti-slop/src/effect/rules/no-manual-tagged-construction.ts +37 -0
- package/vendor/anti-slop/src/effect/rules/prefer-effect-match.ts +54 -0
- package/vendor/anti-slop/src/effect/shared/tagged-values.ts +97 -0
- package/vendor/anti-slop/src/index.ts +6 -0
- package/vendor/anti-slop/src/rules/no-array-filter-map.ts +28 -0
- package/vendor/anti-slop/src/rules/no-known-value-widening.ts +2 -14
- package/vendor/anti-slop/src/rules/no-module-mocking.ts +3 -14
- package/vendor/anti-slop/src/rules/no-reduce-accumulator-copy.ts +109 -0
- package/vendor/anti-slop/src/rules/require-readable-spacing.ts +47 -0
- package/vendor/anti-slop/src/shared/array-method.ts +94 -0
- package/vendor/anti-slop/src/shared/reflect-method.ts +2 -13
- package/vendor/anti-slop/src/shared/scope.ts +15 -0
- package/vendor/anti-slop/src/vendor/eslint-stylistic/LICENSE +22 -0
- package/vendor/anti-slop/src/vendor/eslint-stylistic/UPSTREAM.md +28 -0
- package/vendor/anti-slop/src/vendor/eslint-stylistic/padding-line-ast.ts +51 -0
- package/vendor/anti-slop/src/vendor/eslint-stylistic/padding-line-between-statements.ts +906 -0
- package/vendor/anti-slop/src/vendor/eslint-stylistic/padding-line-options.d.ts +87 -0
|
@@ -1,8 +1,208 @@
|
|
|
1
|
+
// node_modules/oxlint/dist/index.js
|
|
2
|
+
function defineConfig(config) {
|
|
3
|
+
return config;
|
|
4
|
+
}
|
|
5
|
+
|
|
1
6
|
// vendor/anti-slop/src/index.ts
|
|
2
7
|
import { eslintCompatPlugin } from "@oxlint/plugins";
|
|
3
8
|
|
|
4
|
-
// vendor/anti-slop/src/rules/no-
|
|
9
|
+
// vendor/anti-slop/src/rules/no-array-filter-map.ts
|
|
5
10
|
import { defineRule } from "@oxlint/plugins";
|
|
11
|
+
|
|
12
|
+
// vendor/anti-slop/src/shared/array-method.ts
|
|
13
|
+
function unwrapArrayExpression(node) {
|
|
14
|
+
while (node.type === "ParenthesizedExpression" || node.type === "ChainExpression" || node.type === "TSAsExpression" || node.type === "TSTypeAssertion" || node.type === "TSNonNullExpression" || node.type === "TSSatisfiesExpression") {
|
|
15
|
+
node = node.expression;
|
|
16
|
+
}
|
|
17
|
+
return node;
|
|
18
|
+
}
|
|
19
|
+
function resolveArrayBinding(sourceCode, node) {
|
|
20
|
+
node = unwrapArrayExpression(node);
|
|
21
|
+
if (node.type !== "Identifier")
|
|
22
|
+
return null;
|
|
23
|
+
let scope = sourceCode.getScope(node);
|
|
24
|
+
while (scope !== null) {
|
|
25
|
+
const variable = scope.set.get(node.name);
|
|
26
|
+
if (variable !== undefined)
|
|
27
|
+
return variable;
|
|
28
|
+
scope = scope.upper;
|
|
29
|
+
}
|
|
30
|
+
return null;
|
|
31
|
+
}
|
|
32
|
+
function arrayMethodTarget(node) {
|
|
33
|
+
node = unwrapArrayExpression(node);
|
|
34
|
+
if (node.type !== "MemberExpression")
|
|
35
|
+
return null;
|
|
36
|
+
const property = node.property;
|
|
37
|
+
if (!node.computed && property.type === "Identifier") {
|
|
38
|
+
return { name: property.name, object: node.object };
|
|
39
|
+
}
|
|
40
|
+
if (node.computed && property.type === "Literal" && typeof property.value === "string") {
|
|
41
|
+
return { name: property.value, object: node.object };
|
|
42
|
+
}
|
|
43
|
+
return null;
|
|
44
|
+
}
|
|
45
|
+
function isArrayAnnotation(type) {
|
|
46
|
+
if (type.type === "TSArrayType" || type.type === "TSTupleType")
|
|
47
|
+
return true;
|
|
48
|
+
if (type.type === "TSParenthesizedType")
|
|
49
|
+
return isArrayAnnotation(type.typeAnnotation);
|
|
50
|
+
if (type.type === "TSTypeOperator" && type.operator === "readonly") {
|
|
51
|
+
return isArrayAnnotation(type.typeAnnotation);
|
|
52
|
+
}
|
|
53
|
+
return type.type === "TSTypeReference" && type.typeName.type === "Identifier" && (type.typeName.name === "Array" || type.typeName.name === "ReadonlyArray");
|
|
54
|
+
}
|
|
55
|
+
function isKnownArrayExpression(sourceCode, node, visited = new Set) {
|
|
56
|
+
node = unwrapArrayExpression(node);
|
|
57
|
+
if (node.type === "ArrayExpression")
|
|
58
|
+
return true;
|
|
59
|
+
if (node.type === "CallExpression") {
|
|
60
|
+
const method = arrayMethodTarget(node.callee);
|
|
61
|
+
return method !== null && ["map", "filter", "flatMap", "slice", "concat", "toSorted", "toReversed", "toSpliced"].includes(method.name) && isKnownArrayExpression(sourceCode, method.object, visited);
|
|
62
|
+
}
|
|
63
|
+
if (node.type !== "Identifier")
|
|
64
|
+
return false;
|
|
65
|
+
const variable = resolveArrayBinding(sourceCode, node);
|
|
66
|
+
if (variable === null || visited.has(variable))
|
|
67
|
+
return false;
|
|
68
|
+
visited.add(variable);
|
|
69
|
+
if (variable.references.some((reference) => reference.isWrite() && !reference.init))
|
|
70
|
+
return false;
|
|
71
|
+
for (const identifier of variable.identifiers) {
|
|
72
|
+
const annotation = identifier.typeAnnotation?.typeAnnotation;
|
|
73
|
+
if (annotation !== undefined)
|
|
74
|
+
return isArrayAnnotation(annotation);
|
|
75
|
+
}
|
|
76
|
+
for (const definition of variable.defs) {
|
|
77
|
+
if (definition.type === "Variable" && definition.node.type === "VariableDeclarator" && definition.node.id.type === "Identifier" && definition.node.init !== null && definition.node.parent.type === "VariableDeclaration" && definition.node.parent.kind === "const") {
|
|
78
|
+
return isKnownArrayExpression(sourceCode, definition.node.init, visited);
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
return false;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// vendor/anti-slop/src/rules/no-array-filter-map.ts
|
|
85
|
+
var noArrayFilterMapRule = defineRule({
|
|
86
|
+
meta: {
|
|
87
|
+
type: "suggestion",
|
|
88
|
+
docs: { description: "Disallow adjacent array filter/map passes in favor of lazy iterator helpers or a single transformation." },
|
|
89
|
+
messages: {
|
|
90
|
+
arrayFilterMap: "Avoid consecutive array `{{first}}` and `{{second}}` passes. Prefer `.values().{{first}}(...).{{second}}(...).toArray()` where iterator helpers are supported, or a single `flatMap`/mutating reducer. Preserve callback ordering, indexes, and filtering semantics."
|
|
91
|
+
}
|
|
92
|
+
},
|
|
93
|
+
createOnce(context) {
|
|
94
|
+
return {
|
|
95
|
+
CallExpression(node) {
|
|
96
|
+
const outer = arrayMethodTarget(node.callee);
|
|
97
|
+
if (outer === null || outer.name !== "map" && outer.name !== "filter")
|
|
98
|
+
return;
|
|
99
|
+
const innerCall = unwrapArrayExpression(outer.object);
|
|
100
|
+
if (innerCall.type !== "CallExpression")
|
|
101
|
+
return;
|
|
102
|
+
const inner = arrayMethodTarget(innerCall.callee);
|
|
103
|
+
if (inner === null || inner.name !== (outer.name === "map" ? "filter" : "map"))
|
|
104
|
+
return;
|
|
105
|
+
if (!isKnownArrayExpression(context.sourceCode, inner.object))
|
|
106
|
+
return;
|
|
107
|
+
context.report({ node, messageId: "arrayFilterMap", data: { first: inner.name, second: outer.name } });
|
|
108
|
+
}
|
|
109
|
+
};
|
|
110
|
+
}
|
|
111
|
+
});
|
|
112
|
+
|
|
113
|
+
// vendor/anti-slop/src/rules/no-reduce-accumulator-copy.ts
|
|
114
|
+
import { defineRule as defineRule2 } from "@oxlint/plugins";
|
|
115
|
+
function enclosingReducer(node) {
|
|
116
|
+
let parent = node.parent;
|
|
117
|
+
while (parent !== null) {
|
|
118
|
+
if (parent.type === "FunctionDeclaration")
|
|
119
|
+
return null;
|
|
120
|
+
if (parent.type === "ArrowFunctionExpression" || parent.type === "FunctionExpression") {
|
|
121
|
+
const callback = parent;
|
|
122
|
+
let owner = callback.parent;
|
|
123
|
+
while (owner !== null && unwrapArrayExpression(owner) === callback)
|
|
124
|
+
owner = owner.parent;
|
|
125
|
+
if (owner?.type !== "CallExpression")
|
|
126
|
+
return null;
|
|
127
|
+
const method = arrayMethodTarget(owner.callee);
|
|
128
|
+
const firstArgument = owner.arguments[0];
|
|
129
|
+
if (method === null || method.name !== "reduce" && method.name !== "reduceRight" || owner.arguments.length > 2 || firstArgument === undefined || unwrapArrayExpression(firstArgument) !== callback)
|
|
130
|
+
return null;
|
|
131
|
+
const firstParameter = callback.params[0];
|
|
132
|
+
const accumulator = firstParameter?.type === "AssignmentPattern" ? firstParameter.left : firstParameter;
|
|
133
|
+
if (accumulator?.type !== "Identifier")
|
|
134
|
+
return null;
|
|
135
|
+
return { callback, accumulator, initialValue: owner.arguments[1] };
|
|
136
|
+
}
|
|
137
|
+
parent = parent.parent;
|
|
138
|
+
}
|
|
139
|
+
return null;
|
|
140
|
+
}
|
|
141
|
+
function referencesAccumulator(sourceCode, node, accumulator, visited = new Set) {
|
|
142
|
+
const variable = resolveArrayBinding(sourceCode, node);
|
|
143
|
+
if (variable === null || visited.has(variable))
|
|
144
|
+
return false;
|
|
145
|
+
if (variable === accumulator)
|
|
146
|
+
return true;
|
|
147
|
+
visited.add(variable);
|
|
148
|
+
if (variable.references.some((reference) => reference.isWrite() && !reference.init))
|
|
149
|
+
return false;
|
|
150
|
+
for (const definition of variable.defs) {
|
|
151
|
+
if (definition.type === "Variable" && definition.node.type === "VariableDeclarator" && definition.node.id.type === "Identifier" && definition.node.init !== null && definition.node.parent.type === "VariableDeclaration" && definition.node.parent.kind === "const") {
|
|
152
|
+
return referencesAccumulator(sourceCode, definition.node.init, accumulator, visited);
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
return false;
|
|
156
|
+
}
|
|
157
|
+
function isGlobalCopyOwner(sourceCode, node, name) {
|
|
158
|
+
node = unwrapArrayExpression(node);
|
|
159
|
+
if (node.type !== "Identifier" || node.name !== name)
|
|
160
|
+
return false;
|
|
161
|
+
const variable = resolveArrayBinding(sourceCode, node);
|
|
162
|
+
return variable === null || variable.defs.length === 0;
|
|
163
|
+
}
|
|
164
|
+
var noReduceAccumulatorCopyRule = defineRule2({
|
|
165
|
+
meta: {
|
|
166
|
+
type: "problem",
|
|
167
|
+
docs: { description: "Disallow copying growing reducer accumulators with Object.assign, Array.from, or array copy methods." },
|
|
168
|
+
messages: {
|
|
169
|
+
accumulatorCopy: "Do not copy the reducer accumulator on every iteration; growing copies can cause quadratic work. Mutate a fresh, locally owned accumulator and return it, or use an iterator pipeline/flatMap."
|
|
170
|
+
}
|
|
171
|
+
},
|
|
172
|
+
createOnce(context) {
|
|
173
|
+
return {
|
|
174
|
+
CallExpression(node) {
|
|
175
|
+
const method = arrayMethodTarget(node.callee);
|
|
176
|
+
if (method === null)
|
|
177
|
+
return;
|
|
178
|
+
const reducer = enclosingReducer(node);
|
|
179
|
+
if (reducer === null)
|
|
180
|
+
return;
|
|
181
|
+
const accumulator = context.sourceCode.getDeclaredVariables(reducer.callback).find((variable) => variable.identifiers.some((identifier) => identifier.start === reducer.accumulator.start));
|
|
182
|
+
if (accumulator === undefined)
|
|
183
|
+
return;
|
|
184
|
+
const isAccumulator = (expression) => referencesAccumulator(context.sourceCode, expression, accumulator);
|
|
185
|
+
let copiesAccumulator = false;
|
|
186
|
+
if (method.name === "assign" && isGlobalCopyOwner(context.sourceCode, method.object, "Object")) {
|
|
187
|
+
const target = node.arguments[0];
|
|
188
|
+
copiesAccumulator = target !== undefined && unwrapArrayExpression(target).type === "ObjectExpression" && node.arguments.slice(1).some(isAccumulator);
|
|
189
|
+
} else if (method.name === "from" && isGlobalCopyOwner(context.sourceCode, method.object, "Array")) {
|
|
190
|
+
const source = node.arguments[0];
|
|
191
|
+
copiesAccumulator = source !== undefined && isAccumulator(source);
|
|
192
|
+
} else if (["concat", "slice", "toSpliced", "toSorted", "toReversed", "with"].includes(method.name)) {
|
|
193
|
+
const initialValue = reducer.initialValue;
|
|
194
|
+
const arrayAccumulator = initialValue !== undefined && isKnownArrayExpression(context.sourceCode, initialValue);
|
|
195
|
+
copiesAccumulator = arrayAccumulator && isAccumulator(method.object);
|
|
196
|
+
}
|
|
197
|
+
if (copiesAccumulator)
|
|
198
|
+
context.report({ node, messageId: "accumulatorCopy" });
|
|
199
|
+
}
|
|
200
|
+
};
|
|
201
|
+
}
|
|
202
|
+
});
|
|
203
|
+
|
|
204
|
+
// vendor/anti-slop/src/rules/no-chained-type-assertions.ts
|
|
205
|
+
import { defineRule as defineRule3 } from "@oxlint/plugins";
|
|
6
206
|
function isTypeAssertionExpression(node) {
|
|
7
207
|
return node.type === "TSAsExpression" || node.type === "TSTypeAssertion";
|
|
8
208
|
}
|
|
@@ -37,7 +237,7 @@ function isForbiddenAssertionChain(node) {
|
|
|
37
237
|
}
|
|
38
238
|
return assertionCount > 1 && hasNonConstAssertion;
|
|
39
239
|
}
|
|
40
|
-
var noChainedTypeAssertionsRule =
|
|
240
|
+
var noChainedTypeAssertionsRule = defineRule3({
|
|
41
241
|
meta: {
|
|
42
242
|
type: "problem",
|
|
43
243
|
docs: {
|
|
@@ -61,7 +261,7 @@ var noChainedTypeAssertionsRule = defineRule({
|
|
|
61
261
|
});
|
|
62
262
|
|
|
63
263
|
// vendor/anti-slop/src/rules/no-conditional-empty-object-spread.ts
|
|
64
|
-
import { defineRule as
|
|
264
|
+
import { defineRule as defineRule4 } from "@oxlint/plugins";
|
|
65
265
|
function unwrapParentheses(node) {
|
|
66
266
|
let current = node;
|
|
67
267
|
while (current.type === "ParenthesizedExpression") {
|
|
@@ -76,7 +276,7 @@ function isConditionalEmptyObjectSpread(node) {
|
|
|
76
276
|
const conditional = unwrapParentheses(node);
|
|
77
277
|
return conditional.type === "ConditionalExpression" && (isEmptyObjectExpression(conditional.consequent) || isEmptyObjectExpression(conditional.alternate));
|
|
78
278
|
}
|
|
79
|
-
var noConditionalEmptyObjectSpreadRule =
|
|
279
|
+
var noConditionalEmptyObjectSpreadRule = defineRule4({
|
|
80
280
|
meta: {
|
|
81
281
|
type: "suggestion",
|
|
82
282
|
docs: {
|
|
@@ -100,7 +300,7 @@ var noConditionalEmptyObjectSpreadRule = defineRule2({
|
|
|
100
300
|
});
|
|
101
301
|
|
|
102
302
|
// vendor/anti-slop/src/rules/no-known-value-widening.ts
|
|
103
|
-
import { defineRule as
|
|
303
|
+
import { defineRule as defineRule5 } from "@oxlint/plugins";
|
|
104
304
|
|
|
105
305
|
// vendor/anti-slop/src/shared/lexical-type-parameters.ts
|
|
106
306
|
function isNode(value) {
|
|
@@ -503,9 +703,9 @@ function classifyWideningTarget(type, environment) {
|
|
|
503
703
|
if (alias === null)
|
|
504
704
|
return null;
|
|
505
705
|
if ((alias.typeParameters?.params.length ?? 0) > 0) {
|
|
506
|
-
const
|
|
507
|
-
const
|
|
508
|
-
return
|
|
706
|
+
const substitutions = aliasSubstitution(alias, unwrapped, new Map);
|
|
707
|
+
const resolved = substitutions === null ? null : classifyAliasBroadTarget(alias.typeAnnotation, environment, substitutions, new Set([name]));
|
|
708
|
+
return resolved?.kind === "open dictionary" ? { kind: "generic container" } : null;
|
|
509
709
|
}
|
|
510
710
|
const substitutions = aliasSubstitution(alias, unwrapped, new Map);
|
|
511
711
|
if (substitutions === null)
|
|
@@ -629,14 +829,7 @@ function functionParameterBindingName(parameter, sourceCode) {
|
|
|
629
829
|
return annotationStart === undefined ? sourceText : sourceText.slice(0, annotationStart - parameter.start).trimEnd();
|
|
630
830
|
}
|
|
631
831
|
|
|
632
|
-
// vendor/anti-slop/src/
|
|
633
|
-
function unwrapExpression(expression) {
|
|
634
|
-
let current = expression;
|
|
635
|
-
while (current.type === "ParenthesizedExpression" || current.type === "TSAsExpression" || current.type === "TSSatisfiesExpression" || current.type === "TSTypeAssertion" || current.type === "TSNonNullExpression") {
|
|
636
|
-
current = current.expression;
|
|
637
|
-
}
|
|
638
|
-
return current;
|
|
639
|
-
}
|
|
832
|
+
// vendor/anti-slop/src/shared/scope.ts
|
|
640
833
|
function resolveVariable(sourceCode, identifier) {
|
|
641
834
|
let scope = sourceCode.getScope(identifier);
|
|
642
835
|
while (scope !== null) {
|
|
@@ -647,6 +840,15 @@ function resolveVariable(sourceCode, identifier) {
|
|
|
647
840
|
}
|
|
648
841
|
return null;
|
|
649
842
|
}
|
|
843
|
+
|
|
844
|
+
// vendor/anti-slop/src/rules/no-known-value-widening.ts
|
|
845
|
+
function unwrapExpression(expression) {
|
|
846
|
+
let current = expression;
|
|
847
|
+
while (current.type === "ParenthesizedExpression" || current.type === "TSAsExpression" || current.type === "TSSatisfiesExpression" || current.type === "TSTypeAssertion" || current.type === "TSNonNullExpression") {
|
|
848
|
+
current = current.expression;
|
|
849
|
+
}
|
|
850
|
+
return current;
|
|
851
|
+
}
|
|
650
852
|
function variableDeclarator(variable) {
|
|
651
853
|
if (variable.defs.length !== 1)
|
|
652
854
|
return null;
|
|
@@ -799,7 +1001,7 @@ function isDictionaryAccumulatorTarget(destination) {
|
|
|
799
1001
|
function hasParentAssertion(node) {
|
|
800
1002
|
return node.parent?.type === "TSAsExpression" || node.parent?.type === "TSTypeAssertion";
|
|
801
1003
|
}
|
|
802
|
-
var noKnownValueWideningRule =
|
|
1004
|
+
var noKnownValueWideningRule = defineRule5({
|
|
803
1005
|
meta: {
|
|
804
1006
|
type: "problem",
|
|
805
1007
|
docs: {
|
|
@@ -912,18 +1114,8 @@ var noKnownValueWideningRule = defineRule3({
|
|
|
912
1114
|
});
|
|
913
1115
|
|
|
914
1116
|
// vendor/anti-slop/src/rules/no-module-mocking.ts
|
|
915
|
-
import { defineRule as
|
|
1117
|
+
import { defineRule as defineRule6 } from "@oxlint/plugins";
|
|
916
1118
|
var moduleMockMethods = new Set(["doMock", "mock", "unstable_mockModule"]);
|
|
917
|
-
function resolveVariable2(sourceCode, identifier) {
|
|
918
|
-
let scope = sourceCode.getScope(identifier);
|
|
919
|
-
while (scope !== null) {
|
|
920
|
-
const variable = scope.set.get(identifier.name);
|
|
921
|
-
if (variable !== undefined)
|
|
922
|
-
return variable;
|
|
923
|
-
scope = scope.upper;
|
|
924
|
-
}
|
|
925
|
-
return null;
|
|
926
|
-
}
|
|
927
1119
|
function importedName(node) {
|
|
928
1120
|
if (node.type !== "ImportSpecifier")
|
|
929
1121
|
return null;
|
|
@@ -935,7 +1127,7 @@ function isTestFrameworkObject(sourceCode, expression) {
|
|
|
935
1127
|
if ((expression.name === "vi" || expression.name === "jest") && sourceCode.isGlobalReference(expression)) {
|
|
936
1128
|
return true;
|
|
937
1129
|
}
|
|
938
|
-
const variable =
|
|
1130
|
+
const variable = resolveVariable(sourceCode, expression);
|
|
939
1131
|
if (variable === null || variable.defs.length === 0) {
|
|
940
1132
|
return expression.name === "vi" || expression.name === "jest";
|
|
941
1133
|
}
|
|
@@ -957,7 +1149,7 @@ function moduleMockCall(sourceCode, callee) {
|
|
|
957
1149
|
const method = callee.computed ? property.type === "Literal" && (property.value === "doMock" || property.value === "mock" || property.value === "unstable_mockModule") ? property.value : null : property.type === "Identifier" ? property.name : null;
|
|
958
1150
|
return method !== null && moduleMockMethods.has(method);
|
|
959
1151
|
}
|
|
960
|
-
var noModuleMockingRule =
|
|
1152
|
+
var noModuleMockingRule = defineRule6({
|
|
961
1153
|
meta: {
|
|
962
1154
|
type: "problem",
|
|
963
1155
|
docs: {
|
|
@@ -981,8 +1173,8 @@ var noModuleMockingRule = defineRule4({
|
|
|
981
1173
|
});
|
|
982
1174
|
|
|
983
1175
|
// vendor/anti-slop/src/rules/no-object-parameters.ts
|
|
984
|
-
import { defineRule as
|
|
985
|
-
var noObjectParametersRule =
|
|
1176
|
+
import { defineRule as defineRule7 } from "@oxlint/plugins";
|
|
1177
|
+
var noObjectParametersRule = defineRule7({
|
|
986
1178
|
meta: {
|
|
987
1179
|
type: "problem",
|
|
988
1180
|
docs: {
|
|
@@ -1035,25 +1227,15 @@ var noObjectParametersRule = defineRule5({
|
|
|
1035
1227
|
});
|
|
1036
1228
|
|
|
1037
1229
|
// vendor/anti-slop/src/rules/no-reflect-apply.ts
|
|
1038
|
-
import { defineRule as
|
|
1230
|
+
import { defineRule as defineRule8 } from "@oxlint/plugins";
|
|
1039
1231
|
|
|
1040
1232
|
// vendor/anti-slop/src/shared/reflect-method.ts
|
|
1041
|
-
function resolveVariable3(sourceCode, identifier) {
|
|
1042
|
-
let scope = sourceCode.getScope(identifier);
|
|
1043
|
-
while (scope !== null) {
|
|
1044
|
-
const variable = scope.set.get(identifier.name);
|
|
1045
|
-
if (variable !== undefined)
|
|
1046
|
-
return variable;
|
|
1047
|
-
scope = scope.upper;
|
|
1048
|
-
}
|
|
1049
|
-
return null;
|
|
1050
|
-
}
|
|
1051
1233
|
function isGlobalReflect(sourceCode, expression) {
|
|
1052
1234
|
if (expression.type !== "Identifier" || expression.name !== "Reflect")
|
|
1053
1235
|
return false;
|
|
1054
1236
|
if (sourceCode.isGlobalReference(expression))
|
|
1055
1237
|
return true;
|
|
1056
|
-
const variable =
|
|
1238
|
+
const variable = resolveVariable(sourceCode, expression);
|
|
1057
1239
|
return variable === null || variable.defs.length === 0;
|
|
1058
1240
|
}
|
|
1059
1241
|
function isGlobalReflectMethodCall(sourceCode, callee, methodName) {
|
|
@@ -1066,7 +1248,7 @@ function isGlobalReflectMethodCall(sourceCode, callee, methodName) {
|
|
|
1066
1248
|
}
|
|
1067
1249
|
|
|
1068
1250
|
// vendor/anti-slop/src/rules/no-reflect-apply.ts
|
|
1069
|
-
var noReflectApplyRule =
|
|
1251
|
+
var noReflectApplyRule = defineRule8({
|
|
1070
1252
|
meta: {
|
|
1071
1253
|
type: "problem",
|
|
1072
1254
|
docs: {
|
|
@@ -1090,8 +1272,8 @@ var noReflectApplyRule = defineRule6({
|
|
|
1090
1272
|
});
|
|
1091
1273
|
|
|
1092
1274
|
// vendor/anti-slop/src/rules/no-reflect-get.ts
|
|
1093
|
-
import { defineRule as
|
|
1094
|
-
var noReflectGetRule =
|
|
1275
|
+
import { defineRule as defineRule9 } from "@oxlint/plugins";
|
|
1276
|
+
var noReflectGetRule = defineRule9({
|
|
1095
1277
|
meta: {
|
|
1096
1278
|
type: "problem",
|
|
1097
1279
|
docs: {
|
|
@@ -1115,7 +1297,7 @@ var noReflectGetRule = defineRule7({
|
|
|
1115
1297
|
});
|
|
1116
1298
|
|
|
1117
1299
|
// vendor/anti-slop/src/rules/no-runtime-typeof.ts
|
|
1118
|
-
import { defineRule as
|
|
1300
|
+
import { defineRule as defineRule10 } from "@oxlint/plugins";
|
|
1119
1301
|
function isRuntimeFunction(node) {
|
|
1120
1302
|
return node.type === "ArrowFunctionExpression" || node.type === "FunctionDeclaration" || node.type === "FunctionExpression";
|
|
1121
1303
|
}
|
|
@@ -1138,7 +1320,7 @@ function isExistenceProbe(node) {
|
|
|
1138
1320
|
const other = parent.left === node ? parent.right : parent.left;
|
|
1139
1321
|
return other.type === "Literal" && other.value === "undefined";
|
|
1140
1322
|
}
|
|
1141
|
-
var noRuntimeTypeofRule =
|
|
1323
|
+
var noRuntimeTypeofRule = defineRule10({
|
|
1142
1324
|
meta: {
|
|
1143
1325
|
type: "problem",
|
|
1144
1326
|
docs: {
|
|
@@ -1172,7 +1354,7 @@ var noRuntimeTypeofRule = defineRule8({
|
|
|
1172
1354
|
});
|
|
1173
1355
|
|
|
1174
1356
|
// vendor/anti-slop/src/rules/no-shape-in-symbol-names.ts
|
|
1175
|
-
import { defineRule as
|
|
1357
|
+
import { defineRule as defineRule11 } from "@oxlint/plugins";
|
|
1176
1358
|
var FORBIDDEN_SYMBOL_NAME = "shape";
|
|
1177
1359
|
function containsForbiddenSymbolName(name) {
|
|
1178
1360
|
return name.toLowerCase().includes(FORBIDDEN_SYMBOL_NAME);
|
|
@@ -1183,7 +1365,7 @@ function isBorrowedMemberName(node) {
|
|
|
1183
1365
|
return false;
|
|
1184
1366
|
return parent.property === node && parent.computed === false;
|
|
1185
1367
|
}
|
|
1186
|
-
var noForbiddenTermInSymbolNamesRule =
|
|
1368
|
+
var noForbiddenTermInSymbolNamesRule = defineRule11({
|
|
1187
1369
|
meta: {
|
|
1188
1370
|
type: "problem",
|
|
1189
1371
|
docs: {
|
|
@@ -1212,12 +1394,12 @@ var noForbiddenTermInSymbolNamesRule = defineRule9({
|
|
|
1212
1394
|
});
|
|
1213
1395
|
|
|
1214
1396
|
// vendor/anti-slop/src/rules/no-unknown-parameters.ts
|
|
1215
|
-
import { defineRule as
|
|
1397
|
+
import { defineRule as defineRule12 } from "@oxlint/plugins";
|
|
1216
1398
|
function isTypePredicateSubject(owner, parameterName) {
|
|
1217
1399
|
const predicate = owner.returnType?.typeAnnotation;
|
|
1218
1400
|
return predicate?.type === "TSTypePredicate" && predicate.parameterName.type === "Identifier" && predicate.parameterName.name === parameterName;
|
|
1219
1401
|
}
|
|
1220
|
-
var noUnknownParametersRule =
|
|
1402
|
+
var noUnknownParametersRule = defineRule12({
|
|
1221
1403
|
meta: {
|
|
1222
1404
|
type: "problem",
|
|
1223
1405
|
docs: {
|
|
@@ -1261,8 +1443,8 @@ var noUnknownParametersRule = defineRule10({
|
|
|
1261
1443
|
});
|
|
1262
1444
|
|
|
1263
1445
|
// vendor/anti-slop/src/rules/no-unknown-returns.ts
|
|
1264
|
-
import { defineRule as
|
|
1265
|
-
var noUnknownReturnsRule =
|
|
1446
|
+
import { defineRule as defineRule13 } from "@oxlint/plugins";
|
|
1447
|
+
var noUnknownReturnsRule = defineRule13({
|
|
1266
1448
|
meta: {
|
|
1267
1449
|
type: "problem",
|
|
1268
1450
|
docs: {
|
|
@@ -1315,8 +1497,8 @@ var noUnknownReturnsRule = defineRule11({
|
|
|
1315
1497
|
});
|
|
1316
1498
|
|
|
1317
1499
|
// vendor/anti-slop/src/rules/no-unknown-type-aliases.ts
|
|
1318
|
-
import { defineRule as
|
|
1319
|
-
var noUnknownTypeAliasesRule =
|
|
1500
|
+
import { defineRule as defineRule14 } from "@oxlint/plugins";
|
|
1501
|
+
var noUnknownTypeAliasesRule = defineRule14({
|
|
1320
1502
|
meta: {
|
|
1321
1503
|
type: "problem",
|
|
1322
1504
|
docs: {
|
|
@@ -1354,7 +1536,7 @@ var noUnknownTypeAliasesRule = defineRule12({
|
|
|
1354
1536
|
});
|
|
1355
1537
|
|
|
1356
1538
|
// vendor/anti-slop/src/rules/no-unsafe-dictionary-type.ts
|
|
1357
|
-
import { defineRule as
|
|
1539
|
+
import { defineRule as defineRule15 } from "@oxlint/plugins";
|
|
1358
1540
|
var typeNodeKinds = new Set([
|
|
1359
1541
|
"JSDocNonNullableType",
|
|
1360
1542
|
"JSDocNullableType",
|
|
@@ -1441,7 +1623,7 @@ function shouldReportType(node, environment) {
|
|
|
1441
1623
|
}
|
|
1442
1624
|
return true;
|
|
1443
1625
|
}
|
|
1444
|
-
var noUnsafeDictionaryTypeRule =
|
|
1626
|
+
var noUnsafeDictionaryTypeRule = defineRule15({
|
|
1445
1627
|
meta: {
|
|
1446
1628
|
type: "problem",
|
|
1447
1629
|
docs: {
|
|
@@ -1483,7 +1665,7 @@ var noUnsafeDictionaryTypeRule = defineRule13({
|
|
|
1483
1665
|
});
|
|
1484
1666
|
|
|
1485
1667
|
// vendor/anti-slop/src/rules/no-widen-then-assert.ts
|
|
1486
|
-
import { defineRule as
|
|
1668
|
+
import { defineRule as defineRule16 } from "@oxlint/plugins";
|
|
1487
1669
|
var functionBoundaryTypes = new Set([
|
|
1488
1670
|
"ArrowFunctionExpression",
|
|
1489
1671
|
"FunctionDeclaration",
|
|
@@ -1679,7 +1861,7 @@ function assertionIsNarrower(sourceText, broadKind, evidence, assertedType) {
|
|
|
1679
1861
|
return isDefinitelyObjectType(assertedType);
|
|
1680
1862
|
return isDefinitelyNarrowerRecordType(assertedType);
|
|
1681
1863
|
}
|
|
1682
|
-
var noWidenThenAssertRule =
|
|
1864
|
+
var noWidenThenAssertRule = defineRule16({
|
|
1683
1865
|
meta: {
|
|
1684
1866
|
type: "problem",
|
|
1685
1867
|
docs: {
|
|
@@ -1718,8 +1900,530 @@ var noWidenThenAssertRule = defineRule14({
|
|
|
1718
1900
|
}
|
|
1719
1901
|
});
|
|
1720
1902
|
|
|
1903
|
+
// vendor/anti-slop/src/vendor/eslint-stylistic/padding-line-ast.ts
|
|
1904
|
+
var LINEBREAKS = new Set([`\r
|
|
1905
|
+
`, "\r", `
|
|
1906
|
+
`, "\u2028", "\u2029"]);
|
|
1907
|
+
var isClosingBraceToken = (token) => token.type === "Punctuator" && token.value === "}";
|
|
1908
|
+
var isSemicolonToken = (token) => token.type === "Punctuator" && token.value === ";";
|
|
1909
|
+
var isNotSemicolonToken = (token) => !isSemicolonToken(token);
|
|
1910
|
+
var isTokenOnSameLine = (left, right) => left.loc.end.line === right.loc.start.line;
|
|
1911
|
+
var isFunction = (node) => node.type === "FunctionDeclaration" || node.type === "FunctionExpression" || node.type === "ArrowFunctionExpression";
|
|
1912
|
+
var isSingleLine = (node) => node.loc.start.line === node.loc.end.line;
|
|
1913
|
+
var skipChainExpression = (node) => node.type === "ChainExpression" ? node.expression : node;
|
|
1914
|
+
var isTopLevelExpressionStatement = (node) => node.type === "ExpressionStatement" && (node.parent.type === "Program" || node.parent.type === "BlockStatement" && isFunction(node.parent.parent));
|
|
1915
|
+
function isParenthesized(node, sourceCode) {
|
|
1916
|
+
const before = sourceCode.getTokenBefore(node);
|
|
1917
|
+
const after = sourceCode.getTokenAfter(node);
|
|
1918
|
+
return before?.value === "(" && after?.value === ")";
|
|
1919
|
+
}
|
|
1920
|
+
|
|
1921
|
+
// vendor/anti-slop/src/vendor/eslint-stylistic/padding-line-between-statements.ts
|
|
1922
|
+
var CJS_EXPORT = /^(?:module\s*\.\s*)?exports(?:\s*\.|\s*\[|$)/u;
|
|
1923
|
+
var CJS_IMPORT = /^require\(/u;
|
|
1924
|
+
var LT = `[${Array.from(LINEBREAKS).join("")}]`;
|
|
1925
|
+
var PADDING_LINE_SEQUENCE = new RegExp(String.raw`^(\s*?${LT})\s*${LT}(\s*;?)$`, "u");
|
|
1926
|
+
function isSelectorOption(option) {
|
|
1927
|
+
return typeof option === "object" && !Array.isArray(option);
|
|
1928
|
+
}
|
|
1929
|
+
function newKeywordTester(type, keyword) {
|
|
1930
|
+
return {
|
|
1931
|
+
test(node, sourceCode) {
|
|
1932
|
+
const isSameKeyword = sourceCode.getFirstToken(node)?.value === keyword;
|
|
1933
|
+
const isSameType = Array.isArray(type) ? type.includes(node.type) : type === node.type;
|
|
1934
|
+
return isSameKeyword && isSameType;
|
|
1935
|
+
}
|
|
1936
|
+
};
|
|
1937
|
+
}
|
|
1938
|
+
function newNodeTypeTester(type) {
|
|
1939
|
+
return {
|
|
1940
|
+
test: (node) => node.type === type
|
|
1941
|
+
};
|
|
1942
|
+
}
|
|
1943
|
+
function isIIFEStatement(node) {
|
|
1944
|
+
if (node.type === "ExpressionStatement") {
|
|
1945
|
+
let expression = skipChainExpression(node.expression);
|
|
1946
|
+
if (expression.type === "UnaryExpression")
|
|
1947
|
+
expression = skipChainExpression(expression.argument);
|
|
1948
|
+
if (expression.type === "CallExpression") {
|
|
1949
|
+
let node = expression.callee;
|
|
1950
|
+
while (node.type === "SequenceExpression") {
|
|
1951
|
+
const lastExpression = node.expressions.at(-1);
|
|
1952
|
+
if (lastExpression === undefined)
|
|
1953
|
+
throw new Error("Padding rule invariant: sequence expression is empty");
|
|
1954
|
+
node = lastExpression;
|
|
1955
|
+
}
|
|
1956
|
+
return isFunction(node);
|
|
1957
|
+
}
|
|
1958
|
+
}
|
|
1959
|
+
return false;
|
|
1960
|
+
}
|
|
1961
|
+
function isCJSRequire(node) {
|
|
1962
|
+
if (node.type === "VariableDeclaration") {
|
|
1963
|
+
const declaration = node.declarations[0];
|
|
1964
|
+
if (declaration?.init) {
|
|
1965
|
+
let call = declaration?.init;
|
|
1966
|
+
while (call.type === "MemberExpression")
|
|
1967
|
+
call = call.object;
|
|
1968
|
+
if (call.type === "CallExpression" && call.callee.type === "Identifier") {
|
|
1969
|
+
return call.callee.name === "require";
|
|
1970
|
+
}
|
|
1971
|
+
}
|
|
1972
|
+
}
|
|
1973
|
+
return false;
|
|
1974
|
+
}
|
|
1975
|
+
function isBlockLikeStatement(node, sourceCode) {
|
|
1976
|
+
if (node.type === "DoWhileStatement" && node.body.type === "BlockStatement") {
|
|
1977
|
+
return true;
|
|
1978
|
+
}
|
|
1979
|
+
if (isIIFEStatement(node))
|
|
1980
|
+
return true;
|
|
1981
|
+
const lastToken = sourceCode.getLastToken(node, isNotSemicolonToken);
|
|
1982
|
+
const belongingNode = lastToken && isClosingBraceToken(lastToken) ? sourceCode.getNodeByRangeIndex(lastToken.range[0]) : null;
|
|
1983
|
+
return !!belongingNode && (belongingNode.type === "BlockStatement" || belongingNode.type === "SwitchStatement");
|
|
1984
|
+
}
|
|
1985
|
+
function isDirective(node, sourceCode) {
|
|
1986
|
+
return isTopLevelExpressionStatement(node) && node.expression.type === "Literal" && typeof node.expression.value === "string" && !isParenthesized(node.expression, sourceCode);
|
|
1987
|
+
}
|
|
1988
|
+
function isDirectivePrologue(node, sourceCode) {
|
|
1989
|
+
if (isDirective(node, sourceCode) && node.parent && "body" in node.parent && Array.isArray(node.parent.body)) {
|
|
1990
|
+
for (const sibling of node.parent.body) {
|
|
1991
|
+
if (sibling === node)
|
|
1992
|
+
break;
|
|
1993
|
+
if (!isDirective(sibling, sourceCode))
|
|
1994
|
+
return false;
|
|
1995
|
+
}
|
|
1996
|
+
return true;
|
|
1997
|
+
}
|
|
1998
|
+
return false;
|
|
1999
|
+
}
|
|
2000
|
+
function isCJSExport(node) {
|
|
2001
|
+
if (node.type === "ExpressionStatement") {
|
|
2002
|
+
const expression = node.expression;
|
|
2003
|
+
if (expression.type === "AssignmentExpression") {
|
|
2004
|
+
let left = expression.left;
|
|
2005
|
+
if (left.type === "MemberExpression") {
|
|
2006
|
+
while (left.object.type === "MemberExpression")
|
|
2007
|
+
left = left.object;
|
|
2008
|
+
return left.object.type === "Identifier" && (left.object.name === "exports" || left.object.name === "module" && left.property.type === "Identifier" && left.property.name === "exports");
|
|
2009
|
+
}
|
|
2010
|
+
}
|
|
2011
|
+
}
|
|
2012
|
+
return false;
|
|
2013
|
+
}
|
|
2014
|
+
function isExpression(node, sourceCode) {
|
|
2015
|
+
return node.type === "ExpressionStatement" && !isDirectivePrologue(node, sourceCode);
|
|
2016
|
+
}
|
|
2017
|
+
function getActualLastToken(node, sourceCode) {
|
|
2018
|
+
const semiToken = sourceCode.getLastToken(node);
|
|
2019
|
+
const prevToken = sourceCode.getTokenBefore(semiToken);
|
|
2020
|
+
const nextToken = sourceCode.getTokenAfter(semiToken);
|
|
2021
|
+
const isSemicolonLessStyle = prevToken && nextToken && prevToken.range[0] >= node.range[0] && isSemicolonToken(semiToken) && !isTokenOnSameLine(prevToken, semiToken) && isTokenOnSameLine(semiToken, nextToken);
|
|
2022
|
+
return isSemicolonLessStyle ? prevToken : semiToken;
|
|
2023
|
+
}
|
|
2024
|
+
function replacerToRemovePaddingLines(_, trailingSpaces, indentSpaces) {
|
|
2025
|
+
return trailingSpaces + indentSpaces;
|
|
2026
|
+
}
|
|
2027
|
+
function getReportLoc(node, sourceCode) {
|
|
2028
|
+
if (isSingleLine(node))
|
|
2029
|
+
return node.loc;
|
|
2030
|
+
const line = node.loc.start.line;
|
|
2031
|
+
const sourceLine = sourceCode.lines[line - 1];
|
|
2032
|
+
if (sourceLine === undefined)
|
|
2033
|
+
throw new Error("Padding rule invariant: statement source line is missing");
|
|
2034
|
+
return {
|
|
2035
|
+
start: node.loc.start,
|
|
2036
|
+
end: {
|
|
2037
|
+
line,
|
|
2038
|
+
column: sourceLine.length
|
|
2039
|
+
}
|
|
2040
|
+
};
|
|
2041
|
+
}
|
|
2042
|
+
function verifyForAny() {}
|
|
2043
|
+
function verifyForNever(context, _, nextNode, paddingLines) {
|
|
2044
|
+
if (paddingLines.length === 0)
|
|
2045
|
+
return;
|
|
2046
|
+
context.report({
|
|
2047
|
+
node: nextNode,
|
|
2048
|
+
messageId: "unexpectedBlankLine",
|
|
2049
|
+
loc: getReportLoc(nextNode, context.sourceCode),
|
|
2050
|
+
fix(fixer) {
|
|
2051
|
+
if (paddingLines.length >= 2)
|
|
2052
|
+
return null;
|
|
2053
|
+
const paddingPair = paddingLines[0];
|
|
2054
|
+
if (paddingPair === undefined)
|
|
2055
|
+
throw new Error("Padding rule invariant: reported padding pair is missing");
|
|
2056
|
+
const [prevToken, nextToken] = paddingPair;
|
|
2057
|
+
const start = prevToken.range[1];
|
|
2058
|
+
const end = nextToken.range[0];
|
|
2059
|
+
const text = context.sourceCode.text.slice(start, end).replace(PADDING_LINE_SEQUENCE, replacerToRemovePaddingLines);
|
|
2060
|
+
return fixer.replaceTextRange([start, end], text);
|
|
2061
|
+
}
|
|
2062
|
+
});
|
|
2063
|
+
}
|
|
2064
|
+
function verifyForAlways(context, prevNode, nextNode, paddingLines) {
|
|
2065
|
+
if (paddingLines.length > 0)
|
|
2066
|
+
return;
|
|
2067
|
+
context.report({
|
|
2068
|
+
node: nextNode,
|
|
2069
|
+
messageId: "expectedBlankLine",
|
|
2070
|
+
loc: getReportLoc(nextNode, context.sourceCode),
|
|
2071
|
+
fix(fixer) {
|
|
2072
|
+
const sourceCode = context.sourceCode;
|
|
2073
|
+
let prevToken = getActualLastToken(prevNode, sourceCode);
|
|
2074
|
+
const nextToken = sourceCode.getFirstTokenBetween(prevToken, nextNode, {
|
|
2075
|
+
includeComments: true,
|
|
2076
|
+
filter(token) {
|
|
2077
|
+
if (isTokenOnSameLine(prevToken, token)) {
|
|
2078
|
+
prevToken = token;
|
|
2079
|
+
return false;
|
|
2080
|
+
}
|
|
2081
|
+
return true;
|
|
2082
|
+
}
|
|
2083
|
+
}) || nextNode;
|
|
2084
|
+
const insertText = isTokenOnSameLine(prevToken, nextToken) ? `
|
|
2085
|
+
|
|
2086
|
+
` : `
|
|
2087
|
+
`;
|
|
2088
|
+
return fixer.insertTextAfter(prevToken, insertText);
|
|
2089
|
+
}
|
|
2090
|
+
});
|
|
2091
|
+
}
|
|
2092
|
+
var PaddingTypes = {
|
|
2093
|
+
any: { verify: verifyForAny },
|
|
2094
|
+
never: { verify: verifyForNever },
|
|
2095
|
+
always: { verify: verifyForAlways }
|
|
2096
|
+
};
|
|
2097
|
+
var MaybeMultilineStatementType = {
|
|
2098
|
+
"block-like": { test: isBlockLikeStatement },
|
|
2099
|
+
expression: { test: isExpression },
|
|
2100
|
+
return: newKeywordTester("ReturnStatement", "return"),
|
|
2101
|
+
export: newKeywordTester([
|
|
2102
|
+
"ExportAllDeclaration",
|
|
2103
|
+
"ExportDefaultDeclaration",
|
|
2104
|
+
"ExportNamedDeclaration"
|
|
2105
|
+
], "export"),
|
|
2106
|
+
var: newKeywordTester("VariableDeclaration", "var"),
|
|
2107
|
+
let: newKeywordTester("VariableDeclaration", "let"),
|
|
2108
|
+
const: newKeywordTester("VariableDeclaration", "const"),
|
|
2109
|
+
using: {
|
|
2110
|
+
test: (node) => node.type === "VariableDeclaration" && (node.kind === "using" || node.kind === "await using")
|
|
2111
|
+
},
|
|
2112
|
+
type: newKeywordTester("TSTypeAliasDeclaration", "type")
|
|
2113
|
+
};
|
|
2114
|
+
var StatementTypes = {
|
|
2115
|
+
"*": { test: () => true },
|
|
2116
|
+
exports: { test: isCJSExport },
|
|
2117
|
+
require: { test: isCJSRequire },
|
|
2118
|
+
directive: { test: isDirectivePrologue },
|
|
2119
|
+
iife: { test: isIIFEStatement },
|
|
2120
|
+
block: newNodeTypeTester("BlockStatement"),
|
|
2121
|
+
empty: newNodeTypeTester("EmptyStatement"),
|
|
2122
|
+
function: newNodeTypeTester("FunctionDeclaration"),
|
|
2123
|
+
"ts-method": newNodeTypeTester("TSMethodSignature"),
|
|
2124
|
+
break: newKeywordTester("BreakStatement", "break"),
|
|
2125
|
+
case: newKeywordTester("SwitchCase", "case"),
|
|
2126
|
+
class: newKeywordTester("ClassDeclaration", "class"),
|
|
2127
|
+
continue: newKeywordTester("ContinueStatement", "continue"),
|
|
2128
|
+
debugger: newKeywordTester("DebuggerStatement", "debugger"),
|
|
2129
|
+
default: newKeywordTester(["SwitchCase", "ExportDefaultDeclaration"], "default"),
|
|
2130
|
+
do: newKeywordTester("DoWhileStatement", "do"),
|
|
2131
|
+
for: newKeywordTester([
|
|
2132
|
+
"ForStatement",
|
|
2133
|
+
"ForInStatement",
|
|
2134
|
+
"ForOfStatement"
|
|
2135
|
+
], "for"),
|
|
2136
|
+
if: newKeywordTester("IfStatement", "if"),
|
|
2137
|
+
import: newKeywordTester("ImportDeclaration", "import"),
|
|
2138
|
+
switch: newKeywordTester("SwitchStatement", "switch"),
|
|
2139
|
+
throw: newKeywordTester("ThrowStatement", "throw"),
|
|
2140
|
+
try: newKeywordTester("TryStatement", "try"),
|
|
2141
|
+
while: newKeywordTester(["WhileStatement", "DoWhileStatement"], "while"),
|
|
2142
|
+
with: newKeywordTester("WithStatement", "with"),
|
|
2143
|
+
"cjs-export": {
|
|
2144
|
+
test: (node, sourceCode) => node.type === "ExpressionStatement" && node.expression.type === "AssignmentExpression" && CJS_EXPORT.test(sourceCode.getText(node.expression.left))
|
|
2145
|
+
},
|
|
2146
|
+
"cjs-import": {
|
|
2147
|
+
test: (node, sourceCode) => node.type === "VariableDeclaration" && node.declarations.length > 0 && node.declarations[0]?.init != null && CJS_IMPORT.test(sourceCode.getText(node.declarations[0].init))
|
|
2148
|
+
},
|
|
2149
|
+
enum: newKeywordTester("TSEnumDeclaration", "enum"),
|
|
2150
|
+
interface: newKeywordTester("TSInterfaceDeclaration", "interface"),
|
|
2151
|
+
"function-overload": newNodeTypeTester("TSDeclareFunction"),
|
|
2152
|
+
...Object.fromEntries(Object.entries(MaybeMultilineStatementType).flatMap(([key, value]) => [
|
|
2153
|
+
[key, value],
|
|
2154
|
+
[
|
|
2155
|
+
`singleline-${key}`,
|
|
2156
|
+
{
|
|
2157
|
+
...value,
|
|
2158
|
+
test: (node, sourceCode) => value.test(node, sourceCode) && isSingleLine(node)
|
|
2159
|
+
}
|
|
2160
|
+
],
|
|
2161
|
+
[
|
|
2162
|
+
`multiline-${key}`,
|
|
2163
|
+
{
|
|
2164
|
+
...value,
|
|
2165
|
+
test: (node, sourceCode) => value.test(node, sourceCode) && !isSingleLine(node)
|
|
2166
|
+
}
|
|
2167
|
+
]
|
|
2168
|
+
]))
|
|
2169
|
+
};
|
|
2170
|
+
function createPaddingLineRule(options) {
|
|
2171
|
+
return {
|
|
2172
|
+
meta: {
|
|
2173
|
+
type: "layout",
|
|
2174
|
+
docs: {
|
|
2175
|
+
description: "Require or disallow padding lines between statements"
|
|
2176
|
+
},
|
|
2177
|
+
fixable: "whitespace",
|
|
2178
|
+
hasSuggestions: false,
|
|
2179
|
+
schema: {
|
|
2180
|
+
$defs: {
|
|
2181
|
+
paddingType: {
|
|
2182
|
+
type: "string",
|
|
2183
|
+
enum: Object.keys(PaddingTypes)
|
|
2184
|
+
},
|
|
2185
|
+
statementType: {
|
|
2186
|
+
type: "string",
|
|
2187
|
+
enum: Object.keys(StatementTypes)
|
|
2188
|
+
},
|
|
2189
|
+
selectorOption: {
|
|
2190
|
+
type: "object",
|
|
2191
|
+
properties: {
|
|
2192
|
+
selector: {
|
|
2193
|
+
type: "string"
|
|
2194
|
+
},
|
|
2195
|
+
lineMode: {
|
|
2196
|
+
type: "string",
|
|
2197
|
+
enum: ["any", "singleline", "multiline"]
|
|
2198
|
+
}
|
|
2199
|
+
},
|
|
2200
|
+
required: ["selector"],
|
|
2201
|
+
additionalProperties: false
|
|
2202
|
+
},
|
|
2203
|
+
statementMatcher: {
|
|
2204
|
+
anyOf: [
|
|
2205
|
+
{ $ref: "#/$defs/statementType" },
|
|
2206
|
+
{ $ref: "#/$defs/selectorOption" }
|
|
2207
|
+
]
|
|
2208
|
+
},
|
|
2209
|
+
statementOption: {
|
|
2210
|
+
anyOf: [
|
|
2211
|
+
{ $ref: "#/$defs/statementMatcher" },
|
|
2212
|
+
{
|
|
2213
|
+
type: "array",
|
|
2214
|
+
items: { $ref: "#/$defs/statementMatcher" },
|
|
2215
|
+
minItems: 1,
|
|
2216
|
+
uniqueItems: true,
|
|
2217
|
+
additionalItems: false
|
|
2218
|
+
}
|
|
2219
|
+
]
|
|
2220
|
+
}
|
|
2221
|
+
},
|
|
2222
|
+
type: "array",
|
|
2223
|
+
additionalItems: false,
|
|
2224
|
+
items: {
|
|
2225
|
+
type: "object",
|
|
2226
|
+
properties: {
|
|
2227
|
+
blankLine: { $ref: "#/$defs/paddingType" },
|
|
2228
|
+
prev: { $ref: "#/$defs/statementOption" },
|
|
2229
|
+
next: { $ref: "#/$defs/statementOption" }
|
|
2230
|
+
},
|
|
2231
|
+
additionalProperties: false,
|
|
2232
|
+
required: ["blankLine", "prev", "next"]
|
|
2233
|
+
}
|
|
2234
|
+
},
|
|
2235
|
+
messages: {
|
|
2236
|
+
unexpectedBlankLine: "Unexpected blank line before this statement.",
|
|
2237
|
+
expectedBlankLine: "Expected blank line before this statement."
|
|
2238
|
+
}
|
|
2239
|
+
},
|
|
2240
|
+
create(context) {
|
|
2241
|
+
const sourceCode = context.sourceCode;
|
|
2242
|
+
const selectorMatchedNodes = new Map;
|
|
2243
|
+
const pendingPairs = [];
|
|
2244
|
+
function collectSelectorOption(option) {
|
|
2245
|
+
if (Array.isArray(option)) {
|
|
2246
|
+
for (const item of option)
|
|
2247
|
+
collectSelectorOption(item);
|
|
2248
|
+
return;
|
|
2249
|
+
}
|
|
2250
|
+
if (!isSelectorOption(option))
|
|
2251
|
+
return;
|
|
2252
|
+
selectorMatchedNodes.set(option.selector, new Set);
|
|
2253
|
+
}
|
|
2254
|
+
for (const configure of options) {
|
|
2255
|
+
collectSelectorOption(configure.prev);
|
|
2256
|
+
collectSelectorOption(configure.next);
|
|
2257
|
+
}
|
|
2258
|
+
let scopeInfo = null;
|
|
2259
|
+
function enterScope() {
|
|
2260
|
+
scopeInfo = {
|
|
2261
|
+
upper: scopeInfo,
|
|
2262
|
+
prevNode: null
|
|
2263
|
+
};
|
|
2264
|
+
}
|
|
2265
|
+
function exitScope() {
|
|
2266
|
+
if (scopeInfo)
|
|
2267
|
+
scopeInfo = scopeInfo.upper;
|
|
2268
|
+
}
|
|
2269
|
+
function match(node, type) {
|
|
2270
|
+
let innerStatementNode = node;
|
|
2271
|
+
while (innerStatementNode.type === "LabeledStatement")
|
|
2272
|
+
innerStatementNode = innerStatementNode.body;
|
|
2273
|
+
if (Array.isArray(type))
|
|
2274
|
+
return type.some(match.bind(null, innerStatementNode));
|
|
2275
|
+
if (isSelectorOption(type)) {
|
|
2276
|
+
const matchedNodes = selectorMatchedNodes.get(type.selector);
|
|
2277
|
+
if (!matchedNodes?.has(innerStatementNode))
|
|
2278
|
+
return false;
|
|
2279
|
+
const lineMode = type.lineMode;
|
|
2280
|
+
if (lineMode === "singleline")
|
|
2281
|
+
return isSingleLine(innerStatementNode);
|
|
2282
|
+
else if (lineMode === "multiline")
|
|
2283
|
+
return !isSingleLine(innerStatementNode);
|
|
2284
|
+
return true;
|
|
2285
|
+
} else {
|
|
2286
|
+
const statementType = StatementTypes[type];
|
|
2287
|
+
if (statementType === undefined)
|
|
2288
|
+
throw new Error(`Padding rule invariant: unsupported statement type ${type}`);
|
|
2289
|
+
return statementType.test(innerStatementNode, sourceCode);
|
|
2290
|
+
}
|
|
2291
|
+
}
|
|
2292
|
+
function getPaddingType(prevNode, nextNode) {
|
|
2293
|
+
for (let i = options.length - 1;i >= 0; --i) {
|
|
2294
|
+
const configure = options[i];
|
|
2295
|
+
if (configure === undefined)
|
|
2296
|
+
throw new Error("Padding rule invariant: configuration entry is missing");
|
|
2297
|
+
if (match(prevNode, configure.prev) && match(nextNode, configure.next)) {
|
|
2298
|
+
return PaddingTypes[configure.blankLine];
|
|
2299
|
+
}
|
|
2300
|
+
}
|
|
2301
|
+
return PaddingTypes.any;
|
|
2302
|
+
}
|
|
2303
|
+
function getPaddingLineSequences(prevNode, nextNode) {
|
|
2304
|
+
const pairs = [];
|
|
2305
|
+
let prevToken = getActualLastToken(prevNode, sourceCode);
|
|
2306
|
+
if (nextNode.loc.start.line - prevToken.loc.end.line >= 2) {
|
|
2307
|
+
do {
|
|
2308
|
+
const token = sourceCode.getTokenAfter(prevToken, {
|
|
2309
|
+
includeComments: true
|
|
2310
|
+
});
|
|
2311
|
+
if (token.loc.start.line - prevToken.loc.end.line >= 2)
|
|
2312
|
+
pairs.push([prevToken, token]);
|
|
2313
|
+
prevToken = token;
|
|
2314
|
+
} while (prevToken.range[0] < nextNode.range[0]);
|
|
2315
|
+
}
|
|
2316
|
+
return pairs;
|
|
2317
|
+
}
|
|
2318
|
+
function verify(node) {
|
|
2319
|
+
if (!node.parent || ![
|
|
2320
|
+
"BlockStatement",
|
|
2321
|
+
"Program",
|
|
2322
|
+
"StaticBlock",
|
|
2323
|
+
"SwitchCase",
|
|
2324
|
+
"SwitchStatement",
|
|
2325
|
+
"TSInterfaceBody",
|
|
2326
|
+
"TSModuleBlock",
|
|
2327
|
+
"TSTypeLiteral"
|
|
2328
|
+
].includes(node.parent.type)) {
|
|
2329
|
+
return;
|
|
2330
|
+
}
|
|
2331
|
+
const prevNode = scopeInfo.prevNode;
|
|
2332
|
+
if (prevNode)
|
|
2333
|
+
pendingPairs.push({ prevNode, nextNode: node });
|
|
2334
|
+
scopeInfo.prevNode = node;
|
|
2335
|
+
}
|
|
2336
|
+
function verifyPendingPairs() {
|
|
2337
|
+
for (const { prevNode, nextNode } of pendingPairs) {
|
|
2338
|
+
const type = getPaddingType(prevNode, nextNode);
|
|
2339
|
+
const paddingLines = getPaddingLineSequences(prevNode, nextNode);
|
|
2340
|
+
type.verify(context, prevNode, nextNode, paddingLines);
|
|
2341
|
+
}
|
|
2342
|
+
}
|
|
2343
|
+
function verifyThenEnterScope(node) {
|
|
2344
|
+
verify(node);
|
|
2345
|
+
enterScope();
|
|
2346
|
+
}
|
|
2347
|
+
const selectorMatchListeners = Object.fromEntries(Array.from(selectorMatchedNodes.keys(), (selector) => [
|
|
2348
|
+
selector,
|
|
2349
|
+
(node) => {
|
|
2350
|
+
selectorMatchedNodes.get(selector)?.add(node);
|
|
2351
|
+
}
|
|
2352
|
+
]));
|
|
2353
|
+
return {
|
|
2354
|
+
Program: enterScope,
|
|
2355
|
+
"Program:exit": () => {
|
|
2356
|
+
verifyPendingPairs();
|
|
2357
|
+
exitScope();
|
|
2358
|
+
},
|
|
2359
|
+
BlockStatement: enterScope,
|
|
2360
|
+
"BlockStatement:exit": exitScope,
|
|
2361
|
+
SwitchStatement: enterScope,
|
|
2362
|
+
"SwitchStatement:exit": exitScope,
|
|
2363
|
+
SwitchCase: verifyThenEnterScope,
|
|
2364
|
+
"SwitchCase:exit": exitScope,
|
|
2365
|
+
StaticBlock: enterScope,
|
|
2366
|
+
"StaticBlock:exit": exitScope,
|
|
2367
|
+
TSInterfaceBody: enterScope,
|
|
2368
|
+
"TSInterfaceBody:exit": exitScope,
|
|
2369
|
+
TSModuleBlock: enterScope,
|
|
2370
|
+
"TSModuleBlock:exit": exitScope,
|
|
2371
|
+
TSTypeLiteral: enterScope,
|
|
2372
|
+
"TSTypeLiteral:exit": exitScope,
|
|
2373
|
+
TSDeclareFunction: verifyThenEnterScope,
|
|
2374
|
+
"TSDeclareFunction:exit": exitScope,
|
|
2375
|
+
TSMethodSignature: verifyThenEnterScope,
|
|
2376
|
+
"TSMethodSignature:exit": exitScope,
|
|
2377
|
+
":statement": verify,
|
|
2378
|
+
...selectorMatchListeners
|
|
2379
|
+
};
|
|
2380
|
+
}
|
|
2381
|
+
};
|
|
2382
|
+
}
|
|
2383
|
+
|
|
2384
|
+
// vendor/anti-slop/src/rules/require-readable-spacing.ts
|
|
2385
|
+
var paddingRule = createPaddingLineRule([
|
|
2386
|
+
{ blankLine: "always", prev: "import", next: "*" },
|
|
2387
|
+
{ blankLine: "always", prev: "*", next: { selector: "Program > :not(ImportDeclaration)" } },
|
|
2388
|
+
{ blankLine: "always", prev: { selector: "Program > :not(ImportDeclaration)" }, next: "*" },
|
|
2389
|
+
{ blankLine: "always", prev: "*", next: ["function", "class", "interface", "type"] },
|
|
2390
|
+
{ blankLine: "always", prev: ["function", "class", "interface", "type"], next: "*" },
|
|
2391
|
+
{
|
|
2392
|
+
blankLine: "always",
|
|
2393
|
+
prev: "*",
|
|
2394
|
+
next: ["multiline-const", "multiline-let", "multiline-var", "multiline-using"]
|
|
2395
|
+
},
|
|
2396
|
+
{
|
|
2397
|
+
blankLine: "always",
|
|
2398
|
+
prev: ["multiline-const", "multiline-let", "multiline-var", "multiline-using"],
|
|
2399
|
+
next: "*"
|
|
2400
|
+
},
|
|
2401
|
+
{ blankLine: "always", prev: "*", next: ["return", "if", "switch", "try", "for", "while", "do"] },
|
|
2402
|
+
{ blankLine: "always", prev: "block-like", next: "*" },
|
|
2403
|
+
{ blankLine: "any", prev: "import", next: "import" },
|
|
2404
|
+
{
|
|
2405
|
+
blankLine: "any",
|
|
2406
|
+
prev: {
|
|
2407
|
+
selector: ':matches(TSDeclareFunction, ExportNamedDeclaration[declaration.type="TSDeclareFunction"])'
|
|
2408
|
+
},
|
|
2409
|
+
next: {
|
|
2410
|
+
selector: ':matches(TSDeclareFunction, FunctionDeclaration, ExportNamedDeclaration[declaration.type="TSDeclareFunction"], ExportNamedDeclaration[declaration.type="FunctionDeclaration"])'
|
|
2411
|
+
}
|
|
2412
|
+
}
|
|
2413
|
+
]);
|
|
2414
|
+
var requireReadableSpacingRule = {
|
|
2415
|
+
...paddingRule,
|
|
2416
|
+
meta: {
|
|
2417
|
+
...paddingRule.meta,
|
|
2418
|
+
docs: {
|
|
2419
|
+
description: "Require readable spacing between declarations and logical statement groups."
|
|
2420
|
+
},
|
|
2421
|
+
schema: []
|
|
2422
|
+
}
|
|
2423
|
+
};
|
|
2424
|
+
|
|
1721
2425
|
// vendor/anti-slop/src/rules/require-safety-comment-for-type-assertion.ts
|
|
1722
|
-
import { defineRule as
|
|
2426
|
+
import { defineRule as defineRule17 } from "@oxlint/plugins";
|
|
1723
2427
|
var DEFAULT_SAFETY_MARKERS = ["SAFETY"];
|
|
1724
2428
|
var commentOwnerKinds = new Set([
|
|
1725
2429
|
"ExpressionStatement",
|
|
@@ -1762,7 +2466,7 @@ function hasSafetyComment(sourceCode, node, pattern) {
|
|
|
1762
2466
|
current = current.parent;
|
|
1763
2467
|
}
|
|
1764
2468
|
}
|
|
1765
|
-
var requireSafetyCommentForTypeAssertionRule =
|
|
2469
|
+
var requireSafetyCommentForTypeAssertionRule = defineRule17({
|
|
1766
2470
|
meta: {
|
|
1767
2471
|
type: "problem",
|
|
1768
2472
|
docs: {
|
|
@@ -1815,6 +2519,8 @@ var requireSafetyCommentForTypeAssertionRule = defineRule15({
|
|
|
1815
2519
|
var antiSlopPlugin = eslintCompatPlugin({
|
|
1816
2520
|
meta: { name: "anti-slop" },
|
|
1817
2521
|
rules: {
|
|
2522
|
+
"no-array-filter-map": noArrayFilterMapRule,
|
|
2523
|
+
"no-reduce-accumulator-copy": noReduceAccumulatorCopyRule,
|
|
1818
2524
|
"no-chained-type-assertions": noChainedTypeAssertionsRule,
|
|
1819
2525
|
"no-conditional-empty-object-spread": noConditionalEmptyObjectSpreadRule,
|
|
1820
2526
|
"no-known-value-widening": noKnownValueWideningRule,
|
|
@@ -1829,6 +2535,7 @@ var antiSlopPlugin = eslintCompatPlugin({
|
|
|
1829
2535
|
"no-unknown-returns": noUnknownReturnsRule,
|
|
1830
2536
|
"no-unknown-type-aliases": noUnknownTypeAliasesRule,
|
|
1831
2537
|
"no-widen-then-assert": noWidenThenAssertRule,
|
|
2538
|
+
"require-readable-spacing": requireReadableSpacingRule,
|
|
1832
2539
|
"require-safety-comment-for-type-assertion": requireSafetyCommentForTypeAssertionRule
|
|
1833
2540
|
}
|
|
1834
2541
|
});
|
|
@@ -1837,7 +2544,7 @@ var src_default = antiSlopPlugin;
|
|
|
1837
2544
|
import { eslintCompatPlugin as eslintCompatPlugin2 } from "@oxlint/plugins";
|
|
1838
2545
|
|
|
1839
2546
|
// src/generic/rules/prefer-event-parameter-type.ts
|
|
1840
|
-
import { defineRule as
|
|
2547
|
+
import { defineRule as defineRule18 } from "@oxlint/plugins";
|
|
1841
2548
|
function nearestEnclosingFunction(node) {
|
|
1842
2549
|
let current = node.parent;
|
|
1843
2550
|
while (current) {
|
|
@@ -1864,7 +2571,7 @@ function assertedEventParameter(node) {
|
|
|
1864
2571
|
property
|
|
1865
2572
|
};
|
|
1866
2573
|
}
|
|
1867
|
-
var preferEventParameterTypeRule =
|
|
2574
|
+
var preferEventParameterTypeRule = defineRule18({
|
|
1868
2575
|
meta: {
|
|
1869
2576
|
type: "suggestion",
|
|
1870
2577
|
docs: {
|
|
@@ -1901,11 +2608,6 @@ var timmoPlugin = eslintCompatPlugin2({
|
|
|
1901
2608
|
});
|
|
1902
2609
|
var generic_default = timmoPlugin;
|
|
1903
2610
|
|
|
1904
|
-
// node_modules/oxlint/dist/index.js
|
|
1905
|
-
function defineConfig(config) {
|
|
1906
|
-
return config;
|
|
1907
|
-
}
|
|
1908
|
-
|
|
1909
2611
|
// src/configs/enable-plugin-rules.ts
|
|
1910
2612
|
function enablePluginRules(namespace, plugin) {
|
|
1911
2613
|
return Object.fromEntries(Object.keys(plugin.rules).sort().map((rule) => [`${namespace}/${rule}`, "error"]));
|