@kikiutils/eslint-config 9.3.2 → 10.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +8 -0
- package/dist/_internals/rules/consistent-parameter-layout.d.ts.map +1 -1
- package/dist/_internals/rules/consistent-parameter-layout.js +102 -55
- package/dist/_internals/rules/consistent-parameter-layout.js.map +1 -1
- package/dist/_internals/rules/statement-padding.js +21 -11
- package/dist/_internals/rules/statement-padding.js.map +1 -1
- package/dist/_internals/type-aware.d.ts +3 -0
- package/dist/_internals/type-aware.d.ts.map +1 -0
- package/dist/_internals/type-aware.js +25 -0
- package/dist/_internals/type-aware.js.map +1 -0
- package/dist/base.d.ts.map +1 -1
- package/dist/base.js +43 -16
- package/dist/base.js.map +1 -1
- package/dist/style.js +1 -5
- package/dist/style.js.map +1 -1
- package/dist/vue.d.ts.map +1 -1
- package/dist/vue.js +7 -3
- package/dist/vue.js.map +1 -1
- package/package.json +11 -38
- package/src/_internals/rules/consistent-parameter-layout.ts +179 -98
- package/src/_internals/rules/statement-padding.ts +33 -22
- package/src/_internals/type-aware.ts +28 -0
- package/src/base.ts +66 -23
- package/src/style.ts +1 -2
- package/src/vue.ts +10 -3
package/README.md
CHANGED
|
@@ -26,6 +26,14 @@ You can also use `yarn`, `npm`, or `bun`.
|
|
|
26
26
|
|
|
27
27
|
## Usage
|
|
28
28
|
|
|
29
|
+
TypeScript and Vue configs enable type-aware checks using TypeScript's Project Service.
|
|
30
|
+
Linted files must belong to a discoverable `tsconfig.json`; project references are supported.
|
|
31
|
+
The default setup does not require an additional `typescript.tsconfigPath` option.
|
|
32
|
+
JavaScript files retain syntax-only linting.
|
|
33
|
+
TypeScript tool configs (`*.config.ts`, `*.config.mts`, `*.config.cts`) are excluded from type-aware checks.
|
|
34
|
+
Base configs keep linting Markdown itself, but exclude its code blocks from all lint rules.
|
|
35
|
+
Style configs format CSS and SCSS; indented Sass (`.sass`) is not supported.
|
|
36
|
+
|
|
29
37
|
## License
|
|
30
38
|
|
|
31
39
|
[MIT License](./LICENSE)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"consistent-parameter-layout.d.ts","names":[],"sources":["../../../src/_internals/rules/consistent-parameter-layout.ts"],"mappings":";
|
|
1
|
+
{"version":3,"file":"consistent-parameter-layout.d.ts","names":[],"sources":["../../../src/_internals/rules/consistent-parameter-layout.ts"],"mappings":";qBAgBa,2BAA2B,KAAK"}
|
|
@@ -2,86 +2,133 @@ import { defineScriptAndTemplateVisitors } from "../utils.js";
|
|
|
2
2
|
// src/_internals/rules/consistent-parameter-layout.ts
|
|
3
3
|
const consistentParameterLayout = {
|
|
4
4
|
create(context) {
|
|
5
|
-
const
|
|
6
|
-
function
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
5
|
+
const compactTestCalls = context.options[0]?.compactTestCalls === true;
|
|
6
|
+
function createVisitor(tokenStore, isTemplate) {
|
|
7
|
+
function checkTestCallLayout(node) {
|
|
8
|
+
const items = node.arguments;
|
|
9
|
+
if (!items.length) return;
|
|
10
|
+
const openingParen = tokenStore.getTokenAfter(node.typeArguments ?? node.callee, (token) => token.type === "Punctuator" && token.value === "(");
|
|
11
|
+
const closingParen = tokenStore.getLastToken(node);
|
|
12
|
+
const previous = tokenStore.getTokenBefore(closingParen);
|
|
13
|
+
const gaps = [[
|
|
14
|
+
openingParen,
|
|
15
|
+
tokenStore.getTokenAfter(openingParen),
|
|
16
|
+
""
|
|
17
|
+
], [
|
|
18
|
+
previous,
|
|
19
|
+
closingParen,
|
|
20
|
+
""
|
|
21
|
+
]];
|
|
22
|
+
for (let index = 1; index < items.length; index++) {
|
|
23
|
+
const comma = tokenStore.getTokensBetween(items[index - 1], items[index]).find((token) => token.type === "Punctuator" && token.value === ",");
|
|
24
|
+
gaps.push([
|
|
25
|
+
tokenStore.getTokenBefore(comma),
|
|
26
|
+
comma,
|
|
27
|
+
""
|
|
28
|
+
], [
|
|
29
|
+
comma,
|
|
30
|
+
tokenStore.getTokenAfter(comma),
|
|
31
|
+
" "
|
|
32
|
+
]);
|
|
33
|
+
}
|
|
34
|
+
if (previous.value === ",") gaps.push([
|
|
35
|
+
tokenStore.getTokenBefore(previous),
|
|
36
|
+
previous,
|
|
37
|
+
""
|
|
38
|
+
]);
|
|
39
|
+
if (gaps.some(([left, right]) => tokenStore.commentsExistBetween(left, right))) return;
|
|
40
|
+
const multilineGaps = gaps.filter(([left, right]) => left.loc.end.line !== right.loc.start.line);
|
|
41
|
+
if (!multilineGaps.length) return;
|
|
28
42
|
context.report({
|
|
29
|
-
fix: (fixer) =>
|
|
30
|
-
messageId: "
|
|
43
|
+
fix: (fixer) => multilineGaps.map(([left, right, text]) => fixer.replaceTextRange([left.range[1], right.range[0]], text)),
|
|
44
|
+
messageId: "compactTestCall",
|
|
31
45
|
node
|
|
32
46
|
});
|
|
33
|
-
return;
|
|
34
47
|
}
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
48
|
+
function checkParameterLayout(node, items) {
|
|
49
|
+
const first = items[0];
|
|
50
|
+
if (!first) return;
|
|
51
|
+
const isSingleParameter = items.length === 1;
|
|
52
|
+
const firstType = first.type;
|
|
53
|
+
if (isSingleParameter && (firstType === "JSXElement" || firstType === "JSXFragment")) return;
|
|
54
|
+
let openingParen;
|
|
55
|
+
if (node.type === "CallExpression" || node.type === "NewExpression") openingParen = tokenStore.getTokenAfter(node.typeArguments ?? node.callee, (token) => token.type === "Punctuator" && token.value === "(");
|
|
56
|
+
else openingParen = tokenStore.getTokenBefore(first);
|
|
57
|
+
if (!openingParen || openingParen.value !== "(") return;
|
|
58
|
+
if (openingParen.range[0] < node.range[0]) return;
|
|
59
|
+
const closingParen = node.type === "CallExpression" || node.type === "NewExpression" ? tokenStore.getLastToken(node) : tokenStore.getTokenAfter(items.at(-1), (token) => token.value === ")");
|
|
60
|
+
const next = tokenStore.getTokenAfter(openingParen);
|
|
61
|
+
if (isSingleParameter) {
|
|
62
|
+
if (!closingParen || closingParen.value !== ")") return;
|
|
63
|
+
let previous = tokenStore.getTokenBefore(closingParen);
|
|
64
|
+
if (previous.value === ",") previous = tokenStore.getTokenBefore(previous);
|
|
65
|
+
if (tokenStore.commentsExistBetween(openingParen, next) || tokenStore.commentsExistBetween(previous, closingParen)) return;
|
|
66
|
+
const hasOpeningNewline = openingParen.loc.end.line !== next.loc.start.line;
|
|
67
|
+
if (hasOpeningNewline === (tokenStore.getTokenBefore(closingParen).loc.end.line !== closingParen.loc.start.line)) return;
|
|
68
|
+
context.report({
|
|
69
|
+
fix: (fixer) => hasOpeningNewline ? fixer.insertTextBefore(closingParen, "\n") : fixer.insertTextAfter(openingParen, "\n"),
|
|
70
|
+
messageId: "singleBoundary",
|
|
71
|
+
node
|
|
72
|
+
});
|
|
73
|
+
return;
|
|
43
74
|
}
|
|
44
|
-
if (closingParen
|
|
45
|
-
if (
|
|
46
|
-
|
|
75
|
+
if (!closingParen || openingParen.loc.start.line === closingParen.loc.end.line) return;
|
|
76
|
+
if (isTemplate) {
|
|
77
|
+
const newlineOffsets = [];
|
|
78
|
+
if (openingParen.loc.end.line === next.loc.start.line) newlineOffsets.push(openingParen.range[1]);
|
|
79
|
+
for (let index = 1; index < items.length; index++) {
|
|
80
|
+
const item = items[index];
|
|
81
|
+
const comma = tokenStore.getTokensBetween(items[index - 1], item).find((token) => token.value === ",");
|
|
82
|
+
if (comma && comma.loc.end.line === tokenStore.getTokenAfter(comma).loc.start.line) newlineOffsets.push(comma.range[1]);
|
|
83
|
+
}
|
|
84
|
+
if (closingParen.value === ")" && tokenStore.getTokenBefore(closingParen).loc.end.line === closingParen.loc.start.line) newlineOffsets.push(closingParen.range[0]);
|
|
85
|
+
if (newlineOffsets.length) context.report({
|
|
86
|
+
fix: (fixer) => newlineOffsets.map((offset) => fixer.insertTextBeforeRange([offset, offset], "\n")),
|
|
87
|
+
messageId: "newline",
|
|
88
|
+
node: first
|
|
89
|
+
});
|
|
90
|
+
return;
|
|
91
|
+
}
|
|
92
|
+
if (openingParen.loc.end.line !== next.loc.start.line) return;
|
|
93
|
+
context.report({
|
|
94
|
+
fix: (fixer) => fixer.insertTextAfter(openingParen, "\n"),
|
|
47
95
|
messageId: "newline",
|
|
48
96
|
node: first
|
|
49
97
|
});
|
|
50
|
-
return;
|
|
51
98
|
}
|
|
52
|
-
if (openingParen.loc.end.line !== next.loc.start.line) return;
|
|
53
|
-
context.report({
|
|
54
|
-
fix: (fixer) => fixer.insertTextAfter(openingParen, "\n"),
|
|
55
|
-
messageId: "newline",
|
|
56
|
-
node: first
|
|
57
|
-
});
|
|
58
|
-
}
|
|
59
|
-
function createVisitor(tokenStore, isTemplate) {
|
|
60
99
|
return {
|
|
61
|
-
ArrowFunctionExpression: (node) => checkParameterLayout(node, node.params
|
|
100
|
+
ArrowFunctionExpression: (node) => checkParameterLayout(node, node.params),
|
|
62
101
|
CallExpression: (node) => {
|
|
63
102
|
const { callee } = node;
|
|
64
|
-
if (
|
|
103
|
+
if (compactTestCalls) {
|
|
65
104
|
const target = callee.type === "MemberExpression" && !callee.computed && callee.property.type === "Identifier" && callee.property.name === "concurrent" ? callee.object : callee;
|
|
66
|
-
if (target.type === "Identifier" && (target.name === "describe" || target.name === "it"))
|
|
105
|
+
if (target.type === "Identifier" && (target.name === "describe" || target.name === "it")) {
|
|
106
|
+
checkTestCallLayout(node);
|
|
107
|
+
return;
|
|
108
|
+
}
|
|
67
109
|
}
|
|
68
|
-
checkParameterLayout(node, node.arguments
|
|
110
|
+
checkParameterLayout(node, node.arguments);
|
|
69
111
|
},
|
|
70
|
-
FunctionDeclaration: (node) => checkParameterLayout(node, node.params
|
|
71
|
-
FunctionExpression: (node) => checkParameterLayout(node, node.params
|
|
72
|
-
NewExpression: (node) => checkParameterLayout(node, node.arguments
|
|
112
|
+
FunctionDeclaration: (node) => checkParameterLayout(node, node.params),
|
|
113
|
+
FunctionExpression: (node) => checkParameterLayout(node, node.params),
|
|
114
|
+
NewExpression: (node) => checkParameterLayout(node, node.arguments)
|
|
73
115
|
};
|
|
74
116
|
}
|
|
75
117
|
return defineScriptAndTemplateVisitors(context.sourceCode, createVisitor);
|
|
76
118
|
},
|
|
77
119
|
meta: {
|
|
78
|
-
docs: { description: "
|
|
120
|
+
docs: { description: "Keep parameter boundaries consistent, expand multiline lists, and compact test calls." },
|
|
79
121
|
fixable: "whitespace",
|
|
80
122
|
messages: {
|
|
123
|
+
compactTestCall: "Keep test-call arguments beside their parentheses and each other.",
|
|
81
124
|
newline: "Start a multiline parameter list on a new line.",
|
|
82
125
|
singleBoundary: "Use matching newline boundaries around a single parameter."
|
|
83
126
|
},
|
|
84
|
-
schema: [
|
|
127
|
+
schema: [{
|
|
128
|
+
additionalProperties: false,
|
|
129
|
+
properties: { compactTestCalls: { type: "boolean" } },
|
|
130
|
+
type: "object"
|
|
131
|
+
}],
|
|
85
132
|
type: "layout"
|
|
86
133
|
}
|
|
87
134
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"consistent-parameter-layout.js","names":[],"sources":["../../../src/_internals/rules/consistent-parameter-layout.ts"],"sourcesContent":["import type { Rule } from 'eslint';\n\nimport type { TokenStore } from '../utils';\nimport { defineScriptAndTemplateVisitors } from '../utils';\n\ntype CallNode = Extract<Rule.Node, { type: 'CallExpression' | 'NewExpression' }> & { typeArguments?: Rule.Node };\ntype FunctionNode = Extract<\n Rule.Node,\n { type: 'ArrowFunctionExpression' | 'FunctionDeclaration' | 'FunctionExpression' }\n>;\n\ntype ListItem = CallNode['arguments'][number] | FunctionNode['params'][number];\n\nexport const consistentParameterLayout: Rule.RuleModule = {\n create(context) {\n const isTestFile = /\\.test\\.[jt]sx?$/.test(context.filename);\n\n function checkParameterLayout(\n node: Rule.Node,\n items: readonly ListItem[],\n tokenStore: TokenStore,\n isTemplate: boolean,\n ): void {\n const first = items[0];\n if (!first) return;\n const isSingleParameter = items.length === 1;\n\n // JSX argument layout belongs to the JSX formatting rules.\n const firstType: string = first.type;\n if (isSingleParameter && (firstType === 'JSXElement' || firstType === 'JSXFragment')) return;\n let openingParen;\n if (node.type === 'CallExpression' || node.type === 'NewExpression') {\n const call = node as CallNode;\n openingParen = tokenStore.getTokenAfter(\n call.typeArguments ?? call.callee,\n (token) => token.type === 'Punctuator' && token.value === '(',\n );\n } else {\n openingParen = tokenStore.getTokenBefore(first);\n }\n\n if (!openingParen || openingParen.value !== '(') return;\n // An unparenthesized arrow must not borrow its parent's delimiters.\n if (openingParen.range[0] < node.range![0]) return;\n const closingParen = node.type === 'CallExpression' || node.type === 'NewExpression'\n ? tokenStore.getLastToken(node)\n : tokenStore.getTokenAfter(items.at(-1)!, (token) => token.value === ')');\n\n const next = tokenStore.getTokenAfter(openingParen)!;\n\n if (isSingleParameter) {\n if (!closingParen || closingParen.value !== ')') return;\n let previous = tokenStore.getTokenBefore(closingParen)!;\n if (previous.value === ',') previous = tokenStore.getTokenBefore(previous)!;\n if (\n tokenStore.commentsExistBetween(openingParen, next)\n || tokenStore.commentsExistBetween(previous, closingParen)\n ) return;\n\n const hasOpeningNewline = openingParen.loc.end.line !== next.loc.start.line;\n const hasClosingNewline = tokenStore.getTokenBefore(closingParen)!.loc.end.line\n !== closingParen.loc.start.line;\n\n if (hasOpeningNewline === hasClosingNewline) return;\n\n context.report({\n fix: (fixer) => hasOpeningNewline\n ? fixer.insertTextBefore(closingParen, '\\n')\n : fixer.insertTextAfter(openingParen, '\\n'),\n messageId: 'singleBoundary',\n node,\n });\n\n return;\n }\n\n if (!closingParen || openingParen.loc.start.line === closingParen.loc.end.line) return;\n\n if (isTemplate) {\n // Script list formatters do not traverse Vue template expressions.\n const newlineOffsets: number[] = [];\n if (openingParen.loc.end.line === next.loc.start.line) newlineOffsets.push(openingParen.range[1]);\n for (let index = 1; index < items.length; index++) {\n const item = items[index]!;\n const comma = tokenStore.getTokensBetween(items[index - 1]!, item)\n .find((token) => token.value === ',');\n\n if (comma && comma.loc.end.line === tokenStore.getTokenAfter(comma)!.loc.start.line) {\n newlineOffsets.push(comma.range[1]);\n }\n }\n\n if (\n closingParen.value === ')'\n && tokenStore.getTokenBefore(closingParen)!.loc.end.line === closingParen.loc.start.line\n ) newlineOffsets.push(closingParen.range[0]);\n\n if (newlineOffsets.length) {\n context.report({\n fix: (fixer) => newlineOffsets.map((offset) => fixer.insertTextAfterRange(\n [\n offset,\n offset,\n ],\n '\\n',\n )),\n messageId: 'newline',\n node: first,\n });\n }\n\n return;\n }\n\n if (openingParen.loc.end.line !== next.loc.start.line) return;\n\n context.report({\n fix: (fixer) => fixer.insertTextAfter(openingParen, '\\n'),\n messageId: 'newline',\n node: first,\n });\n }\n\n function createVisitor(tokenStore: TokenStore, isTemplate: boolean): Rule.RuleListener {\n return {\n ArrowFunctionExpression: (node) => checkParameterLayout(node, node.params, tokenStore, isTemplate),\n CallExpression: (node) => {\n const { callee } = node;\n if (isTestFile) {\n const target = callee.type === 'MemberExpression'\n && !callee.computed\n && callee.property.type === 'Identifier'\n && callee.property.name === 'concurrent'\n ? callee.object\n : callee;\n\n if (\n target.type === 'Identifier'\n && (target.name === 'describe' || target.name === 'it')\n ) return;\n }\n\n checkParameterLayout(node, node.arguments, tokenStore, isTemplate);\n },\n FunctionDeclaration: (node) => checkParameterLayout(node, node.params, tokenStore, isTemplate),\n FunctionExpression: (node) => checkParameterLayout(node, node.params, tokenStore, isTemplate),\n NewExpression: (node) => checkParameterLayout(node, node.arguments, tokenStore, isTemplate),\n };\n }\n\n return defineScriptAndTemplateVisitors(context.sourceCode, createVisitor);\n },\n meta: {\n docs: { description: 'Preserve consistent single-parameter boundaries and expand multiline parameter lists.' },\n fixable: 'whitespace',\n messages: {\n newline: 'Start a multiline parameter list on a new line.',\n singleBoundary: 'Use matching newline boundaries around a single parameter.',\n },\n schema: [],\n type: 'layout',\n },\n};\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"consistent-parameter-layout.js","names":[],"sources":["../../../src/_internals/rules/consistent-parameter-layout.ts"],"sourcesContent":["import type {\n AST,\n Rule,\n} from 'eslint';\n\nimport type { TokenStore } from '../utils';\nimport { defineScriptAndTemplateVisitors } from '../utils';\n\ntype CallNode = Extract<Rule.Node, { type: 'CallExpression' | 'NewExpression' }> & { typeArguments?: Rule.Node };\ntype FunctionNode = Extract<\n Rule.Node,\n { type: 'ArrowFunctionExpression' | 'FunctionDeclaration' | 'FunctionExpression' }\n>;\n\ntype ListItem = CallNode['arguments'][number] | FunctionNode['params'][number];\n\nexport const consistentParameterLayout: Rule.RuleModule = {\n create(context) {\n const compactTestCalls = context.options[0]?.compactTestCalls === true;\n\n function createVisitor(tokenStore: TokenStore, isTemplate: boolean): Rule.RuleListener {\n function checkTestCallLayout(node: CallNode): void {\n const items = node.arguments;\n if (!items.length) return;\n const openingParen = tokenStore.getTokenAfter(\n node.typeArguments ?? node.callee,\n (token) => token.type === 'Punctuator' && token.value === '(',\n )!;\n\n const closingParen = tokenStore.getLastToken(node)!;\n const previous = tokenStore.getTokenBefore(closingParen)!;\n const gaps: Array<[AST.Token, AST.Token, string]> = [\n [\n openingParen,\n tokenStore.getTokenAfter(openingParen)!,\n '',\n ],\n [\n previous,\n closingParen,\n '',\n ],\n ];\n\n for (let index = 1; index < items.length; index++) {\n const comma = tokenStore.getTokensBetween(items[index - 1]!, items[index]!)\n .find((token) => token.type === 'Punctuator' && token.value === ',')!;\n\n gaps.push(\n [\n tokenStore.getTokenBefore(comma)!,\n comma,\n '',\n ],\n [\n comma,\n tokenStore.getTokenAfter(comma)!,\n ' ',\n ],\n );\n }\n\n if (previous.value === ',') {\n gaps.push([\n tokenStore.getTokenBefore(previous)!,\n previous,\n '',\n ]);\n }\n\n // Keep the whole list's layout when a boundary comment prevents safe compaction.\n if (gaps.some(([left, right]) => tokenStore.commentsExistBetween(left, right))) return;\n const multilineGaps = gaps.filter(([left, right]) => left.loc.end.line !== right.loc.start.line);\n if (!multilineGaps.length) return;\n\n context.report({\n fix: (fixer) => multilineGaps.map(([\n left,\n right,\n text,\n ]) => fixer.replaceTextRange(\n [\n left.range[1],\n right.range[0],\n ],\n text,\n )),\n messageId: 'compactTestCall',\n node,\n });\n }\n\n function checkParameterLayout(\n node: CallNode | FunctionNode,\n items: readonly ListItem[],\n ): void {\n const first = items[0];\n if (!first) return;\n const isSingleParameter = items.length === 1;\n\n // JSX argument layout belongs to the JSX formatting rules.\n const firstType: string = first.type;\n if (isSingleParameter && (firstType === 'JSXElement' || firstType === 'JSXFragment')) return;\n let openingParen;\n if (node.type === 'CallExpression' || node.type === 'NewExpression') {\n openingParen = tokenStore.getTokenAfter(\n node.typeArguments ?? node.callee,\n (token) => token.type === 'Punctuator' && token.value === '(',\n );\n } else {\n openingParen = tokenStore.getTokenBefore(first);\n }\n\n if (!openingParen || openingParen.value !== '(') return;\n // An unparenthesized arrow must not borrow its parent's delimiters.\n if (openingParen.range[0] < node.range![0]) return;\n const closingParen = node.type === 'CallExpression' || node.type === 'NewExpression'\n ? tokenStore.getLastToken(node)\n : tokenStore.getTokenAfter(items.at(-1)!, (token) => token.value === ')');\n\n const next = tokenStore.getTokenAfter(openingParen)!;\n\n if (isSingleParameter) {\n if (!closingParen || closingParen.value !== ')') return;\n let previous = tokenStore.getTokenBefore(closingParen)!;\n if (previous.value === ',') previous = tokenStore.getTokenBefore(previous)!;\n if (\n tokenStore.commentsExistBetween(openingParen, next)\n || tokenStore.commentsExistBetween(previous, closingParen)\n ) return;\n\n const hasOpeningNewline = openingParen.loc.end.line !== next.loc.start.line;\n const hasClosingNewline = tokenStore.getTokenBefore(closingParen)!.loc.end.line\n !== closingParen.loc.start.line;\n\n if (hasOpeningNewline === hasClosingNewline) return;\n\n context.report({\n fix: (fixer) => hasOpeningNewline\n ? fixer.insertTextBefore(closingParen, '\\n')\n : fixer.insertTextAfter(openingParen, '\\n'),\n messageId: 'singleBoundary',\n node,\n });\n\n return;\n }\n\n if (!closingParen || openingParen.loc.start.line === closingParen.loc.end.line) return;\n\n if (isTemplate) {\n // Script list formatters do not traverse Vue template expressions.\n const newlineOffsets: number[] = [];\n if (openingParen.loc.end.line === next.loc.start.line) newlineOffsets.push(openingParen.range[1]);\n for (let index = 1; index < items.length; index++) {\n const item = items[index]!;\n const comma = tokenStore.getTokensBetween(items[index - 1]!, item)\n .find((token) => token.value === ',');\n\n if (comma && comma.loc.end.line === tokenStore.getTokenAfter(comma)!.loc.start.line) {\n newlineOffsets.push(comma.range[1]);\n }\n }\n\n if (\n closingParen.value === ')'\n && tokenStore.getTokenBefore(closingParen)!.loc.end.line === closingParen.loc.start.line\n ) newlineOffsets.push(closingParen.range[0]);\n\n if (newlineOffsets.length) {\n context.report({\n fix: (fixer) => newlineOffsets.map((offset) => fixer.insertTextBeforeRange(\n [\n offset,\n offset,\n ],\n '\\n',\n )),\n messageId: 'newline',\n node: first,\n });\n }\n\n return;\n }\n\n if (openingParen.loc.end.line !== next.loc.start.line) return;\n\n context.report({\n fix: (fixer) => fixer.insertTextAfter(openingParen, '\\n'),\n messageId: 'newline',\n node: first,\n });\n }\n\n return {\n ArrowFunctionExpression: (node) => checkParameterLayout(node, node.params),\n CallExpression: (node) => {\n const { callee } = node;\n if (compactTestCalls) {\n const target = callee.type === 'MemberExpression'\n && !callee.computed\n && callee.property.type === 'Identifier'\n && callee.property.name === 'concurrent'\n ? callee.object\n : callee;\n\n if (\n target.type === 'Identifier'\n && (target.name === 'describe' || target.name === 'it')\n ) {\n checkTestCallLayout(node);\n return;\n }\n }\n\n checkParameterLayout(node, node.arguments);\n },\n FunctionDeclaration: (node) => checkParameterLayout(node, node.params),\n FunctionExpression: (node) => checkParameterLayout(node, node.params),\n NewExpression: (node) => checkParameterLayout(node, node.arguments),\n };\n }\n\n return defineScriptAndTemplateVisitors(context.sourceCode, createVisitor);\n },\n meta: {\n docs: { description: 'Keep parameter boundaries consistent, expand multiline lists, and compact test calls.' },\n fixable: 'whitespace',\n messages: {\n compactTestCall: 'Keep test-call arguments beside their parentheses and each other.',\n newline: 'Start a multiline parameter list on a new line.',\n singleBoundary: 'Use matching newline boundaries around a single parameter.',\n },\n schema: [\n {\n additionalProperties: false,\n properties: { compactTestCalls: { type: 'boolean' } },\n type: 'object',\n },\n ],\n type: 'layout',\n },\n};\n"],"mappings":"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"}
|
|
@@ -6,12 +6,11 @@ const statementPadding = {
|
|
|
6
6
|
for (let index = 1; index < statements.length; index++) {
|
|
7
7
|
const previous = statements[index - 1];
|
|
8
8
|
const next = statements[index];
|
|
9
|
+
if ([previous, next].some((node) => node.type === "ImportDeclaration" || node.type === "ExportAllDeclaration" || node.type === "ExportNamedDeclaration" && node.source)) continue;
|
|
10
|
+
const previousFirstToken = sourceCode.getFirstToken(previous);
|
|
9
11
|
const lastToken = sourceCode.getLastToken(previous);
|
|
10
12
|
const firstToken = sourceCode.getFirstToken(next);
|
|
11
|
-
const
|
|
12
|
-
const openingLine = sourceCode.lines[firstToken.loc.start.line - 1];
|
|
13
|
-
const hasDifferentIndent = /^\s*/.exec(closingLine)[0] !== /^\s*/.exec(openingLine)[0];
|
|
14
|
-
const hasStandaloneClosing = /^[)\]}]+;?$/.test(closingLine.slice(0, lastToken.loc.end.column).trim());
|
|
13
|
+
const isMultiline = previousFirstToken.loc.start.line !== lastToken.loc.end.line;
|
|
15
14
|
const blockNode = previous.type === "ExportDefaultDeclaration" || previous.type === "ExportNamedDeclaration" ? previous.declaration : previous;
|
|
16
15
|
const hasBlockClosing = lastToken.value === "}" && blockNode && [
|
|
17
16
|
"BlockStatement",
|
|
@@ -27,13 +26,24 @@ const statementPadding = {
|
|
|
27
26
|
"WhileStatement",
|
|
28
27
|
"WithStatement"
|
|
29
28
|
].includes(blockNode.type);
|
|
30
|
-
if (!
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
29
|
+
if (!isMultiline && !hasBlockClosing) continue;
|
|
30
|
+
let previousEnd = lastToken.range[1];
|
|
31
|
+
let previousEndLine = lastToken.loc.end.line;
|
|
32
|
+
let nextStart = firstToken.range[0];
|
|
33
|
+
let nextStartLine = firstToken.loc.start.line;
|
|
34
|
+
for (const comment of sourceCode.getCommentsBefore(next)) if (comment.loc.start.line === previousEndLine) {
|
|
35
|
+
previousEnd = comment.range[1];
|
|
36
|
+
previousEndLine = comment.loc.end.line;
|
|
37
|
+
} else {
|
|
38
|
+
nextStart = comment.range[0];
|
|
39
|
+
nextStartLine = comment.loc.start.line;
|
|
40
|
+
break;
|
|
41
|
+
}
|
|
42
|
+
if (nextStartLine > previousEndLine + 1) continue;
|
|
43
|
+
const linebreakIndex = sourceCode.text.slice(previousEnd, nextStart).indexOf("\n");
|
|
44
|
+
const offset = linebreakIndex === -1 ? nextStart : previousEnd + linebreakIndex + 1;
|
|
35
45
|
context.report({
|
|
36
|
-
fix: (fixer) => fixer.insertTextBeforeRange([offset, offset],
|
|
46
|
+
fix: (fixer) => fixer.insertTextBeforeRange([offset, offset], linebreakIndex === -1 ? "\n\n" : "\n"),
|
|
37
47
|
messageId: "blankLine",
|
|
38
48
|
node: next
|
|
39
49
|
});
|
|
@@ -47,7 +57,7 @@ const statementPadding = {
|
|
|
47
57
|
};
|
|
48
58
|
},
|
|
49
59
|
meta: {
|
|
50
|
-
docs: { description: "Separate statements
|
|
60
|
+
docs: { description: "Separate complete multiline statements and block-ending statements with blank lines." },
|
|
51
61
|
fixable: "whitespace",
|
|
52
62
|
messages: { blankLine: "Add a blank line between these complete statements." },
|
|
53
63
|
schema: [],
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"statement-padding.js","names":[],"sources":["../../../src/_internals/rules/statement-padding.ts"],"sourcesContent":["import type { Rule } from 'eslint';\n\ntype StatementNode = Extract<Rule.Node, { type: 'Program' }>['body'][number];\n\nexport const statementPadding: Rule.RuleModule = {\n create(context) {\n const { sourceCode } = context;\n\n function checkStatements(statements: readonly StatementNode[]): void {\n for (let index = 1; index < statements.length; index++) {\n const previous = statements[index - 1]!;\n const next = statements[index]!;\n const
|
|
1
|
+
{"version":3,"file":"statement-padding.js","names":[],"sources":["../../../src/_internals/rules/statement-padding.ts"],"sourcesContent":["import type { Rule } from 'eslint';\n\ntype StatementNode = Extract<Rule.Node, { type: 'Program' }>['body'][number];\n\nexport const statementPadding: Rule.RuleModule = {\n create(context) {\n const { sourceCode } = context;\n\n function checkStatements(statements: readonly StatementNode[]): void {\n for (let index = 1; index < statements.length; index++) {\n const previous = statements[index - 1]!;\n const next = statements[index]!;\n if (\n [\n previous,\n next,\n ].some((node) =>\n node.type === 'ImportDeclaration'\n || node.type === 'ExportAllDeclaration'\n || (node.type === 'ExportNamedDeclaration' && node.source))\n ) continue;\n\n const previousFirstToken = sourceCode.getFirstToken(previous)!;\n const lastToken = sourceCode.getLastToken(previous)!;\n const firstToken = sourceCode.getFirstToken(next)!;\n const isMultiline = previousFirstToken.loc.start.line !== lastToken.loc.end.line;\n const blockNode = previous.type === 'ExportDefaultDeclaration'\n || previous.type === 'ExportNamedDeclaration'\n ? previous.declaration\n : previous;\n\n const hasBlockClosing = lastToken.value === '}' && blockNode && [\n 'BlockStatement',\n 'ClassDeclaration',\n 'ForInStatement',\n 'ForOfStatement',\n 'ForStatement',\n 'FunctionDeclaration',\n 'IfStatement',\n 'LabeledStatement',\n 'SwitchStatement',\n 'TryStatement',\n 'WhileStatement',\n 'WithStatement',\n ].includes(blockNode.type);\n\n if (!isMultiline && !hasBlockClosing) continue;\n let previousEnd = lastToken.range[1];\n let previousEndLine = lastToken.loc.end.line;\n let nextStart = firstToken.range[0];\n let nextStartLine = firstToken.loc.start.line;\n\n // Include trailing comments in the previous boundary, not leading comments of the next statement.\n for (const comment of sourceCode.getCommentsBefore(next)) {\n if (comment.loc!.start.line === previousEndLine) {\n previousEnd = comment.range![1];\n previousEndLine = comment.loc!.end.line;\n } else {\n nextStart = comment.range![0];\n nextStartLine = comment.loc!.start.line;\n break;\n }\n }\n\n if (nextStartLine > previousEndLine + 1) continue;\n const linebreakIndex = sourceCode.text.slice(previousEnd, nextStart).indexOf('\\n');\n const offset = linebreakIndex === -1 ? nextStart : previousEnd + linebreakIndex + 1;\n\n context.report({\n fix: (fixer) => fixer.insertTextBeforeRange(\n [\n offset,\n offset,\n ],\n linebreakIndex === -1 ? '\\n\\n' : '\\n',\n ),\n messageId: 'blankLine',\n node: next,\n });\n }\n }\n\n return {\n BlockStatement: (node) => checkStatements(node.body),\n Program: (node) => checkStatements(node.body),\n StaticBlock: (node) => checkStatements(node.body),\n SwitchCase: (node) => checkStatements(node.consequent),\n };\n },\n meta: {\n docs: { description: 'Separate complete multiline statements and block-ending statements with blank lines.' },\n fixable: 'whitespace',\n messages: { blankLine: 'Add a blank line between these complete statements.' },\n schema: [],\n type: 'layout',\n },\n};\n"],"mappings":";AAIA,MAAa,mBAAoC;CAC7C,OAAO,SAAS;EACZ,MAAM,EAAE,eAAe;EAEvB,SAAS,gBAAgB,YAA4C;GACjE,KAAK,IAAI,QAAQ,GAAG,QAAQ,WAAW,QAAQ,SAAS;IACpD,MAAM,WAAW,WAAW,QAAQ;IACpC,MAAM,OAAO,WAAW;IACxB,IACI,CACI,UACA,IACJ,CAAC,CAAC,MAAM,SACJ,KAAK,SAAS,uBACX,KAAK,SAAS,0BACb,KAAK,SAAS,4BAA4B,KAAK,MAAO,GAChE;IAEF,MAAM,qBAAqB,WAAW,cAAc,QAAQ;IAC5D,MAAM,YAAY,WAAW,aAAa,QAAQ;IAClD,MAAM,aAAa,WAAW,cAAc,IAAI;IAChD,MAAM,cAAc,mBAAmB,IAAI,MAAM,SAAS,UAAU,IAAI,IAAI;IAC5E,MAAM,YAAY,SAAS,SAAS,8BAC/B,SAAS,SAAS,2BACjB,SAAS,cACT;IAEN,MAAM,kBAAkB,UAAU,UAAU,OAAO,aAAa;KAC5D;KACA;KACA;KACA;KACA;KACA;KACA;KACA;KACA;KACA;KACA;KACA;IACJ,CAAC,CAAC,SAAS,UAAU,IAAI;IAEzB,IAAI,CAAC,eAAe,CAAC,iBAAiB;IACtC,IAAI,cAAc,UAAU,MAAM;IAClC,IAAI,kBAAkB,UAAU,IAAI,IAAI;IACxC,IAAI,YAAY,WAAW,MAAM;IACjC,IAAI,gBAAgB,WAAW,IAAI,MAAM;IAGzC,KAAK,MAAM,WAAW,WAAW,kBAAkB,IAAI,GACnD,IAAI,QAAQ,IAAK,MAAM,SAAS,iBAAiB;KAC7C,cAAc,QAAQ,MAAO;KAC7B,kBAAkB,QAAQ,IAAK,IAAI;IACvC,OAAO;KACH,YAAY,QAAQ,MAAO;KAC3B,gBAAgB,QAAQ,IAAK,MAAM;KACnC;IACJ;IAGJ,IAAI,gBAAgB,kBAAkB,GAAG;IACzC,MAAM,iBAAiB,WAAW,KAAK,MAAM,aAAa,SAAS,CAAC,CAAC,QAAQ,IAAI;IACjF,MAAM,SAAS,mBAAmB,KAAK,YAAY,cAAc,iBAAiB;IAElF,QAAQ,OAAO;KACX,MAAM,UAAU,MAAM,sBAClB,CACI,QACA,MACJ,GACA,mBAAmB,KAAK,SAAS,IACrC;KACA,WAAW;KACX,MAAM;IACV,CAAC;GACL;EACJ;EAEA,OAAO;GACH,iBAAiB,SAAS,gBAAgB,KAAK,IAAI;GACnD,UAAU,SAAS,gBAAgB,KAAK,IAAI;GAC5C,cAAc,SAAS,gBAAgB,KAAK,IAAI;GAChD,aAAa,SAAS,gBAAgB,KAAK,UAAU;EACzD;CACJ;CACA,MAAM;EACF,MAAM,EAAE,aAAa,uFAAuF;EAC5G,SAAS;EACT,UAAU,EAAE,WAAW,sDAAsD;EAC7E,QAAQ,CAAC;EACT,MAAM;CACV;AACJ"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"type-aware.d.ts","names":[],"sources":["../../src/_internals/type-aware.ts"],"mappings":";wBAEgB,yBAAyB"}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
// src/_internals/type-aware.ts
|
|
2
|
+
function createTypeAwareConfig() {
|
|
3
|
+
return {
|
|
4
|
+
languageOptions: { parserOptions: {
|
|
5
|
+
projectService: true,
|
|
6
|
+
tsconfigRootDir: process.cwd()
|
|
7
|
+
} },
|
|
8
|
+
rules: {
|
|
9
|
+
"require-await": "off",
|
|
10
|
+
"ts/await-thenable": "error",
|
|
11
|
+
"ts/no-base-to-string": "error",
|
|
12
|
+
"ts/no-floating-promises": "error",
|
|
13
|
+
"ts/no-for-in-array": "error",
|
|
14
|
+
"ts/no-misused-promises": "error",
|
|
15
|
+
"ts/no-misused-spread": "error",
|
|
16
|
+
"ts/no-unnecessary-type-assertion": "error",
|
|
17
|
+
"ts/require-await": "error",
|
|
18
|
+
"ts/return-await": "error",
|
|
19
|
+
"ts/switch-exhaustiveness-check": ["error", { considerDefaultExhaustiveForUnions: true }]
|
|
20
|
+
}
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
export { createTypeAwareConfig };
|
|
24
|
+
|
|
25
|
+
//# sourceMappingURL=type-aware.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"type-aware.js","names":[],"sources":["../../src/_internals/type-aware.ts"],"sourcesContent":["import type { TypedFlatConfigItem } from '@antfu/eslint-config';\n\nexport function createTypeAwareConfig(): TypedFlatConfigItem {\n return {\n languageOptions: {\n parserOptions: {\n projectService: true,\n tsconfigRootDir: process.cwd(),\n },\n },\n rules: {\n 'require-await': 'off',\n 'ts/await-thenable': 'error',\n 'ts/no-base-to-string': 'error',\n 'ts/no-floating-promises': 'error',\n 'ts/no-for-in-array': 'error',\n 'ts/no-misused-promises': 'error',\n 'ts/no-misused-spread': 'error',\n 'ts/no-unnecessary-type-assertion': 'error',\n 'ts/require-await': 'error',\n 'ts/return-await': 'error',\n 'ts/switch-exhaustiveness-check': [\n 'error',\n { considerDefaultExhaustiveForUnions: true },\n ],\n },\n };\n}\n"],"mappings":";AAEA,SAAgB,wBAA6C;CACzD,OAAO;EACH,iBAAiB,EACb,eAAe;GACX,gBAAgB;GAChB,iBAAiB,QAAQ,IAAI;EACjC,EACJ;EACA,OAAO;GACH,iBAAiB;GACjB,qBAAqB;GACrB,wBAAwB;GACxB,2BAA2B;GAC3B,sBAAsB;GACtB,0BAA0B;GAC1B,wBAAwB;GACxB,oCAAoC;GACpC,oBAAoB;GACpB,mBAAmB;GACnB,kCAAkC,CAC9B,SACA,EAAE,oCAAoC,KAAK,CAC/C;EACJ;CACJ;AACJ"}
|
package/dist/base.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"base.d.ts","names":[],"sources":["../src/base.ts"],"mappings":";
|
|
1
|
+
{"version":3,"file":"base.d.ts","names":[],"sources":["../src/base.ts"],"mappings":";wBAoCgB,kBAAkB,+BAAuC;wBAsGzD,gBAAgB,+BAAuC"}
|
package/dist/base.js
CHANGED
|
@@ -1,18 +1,36 @@
|
|
|
1
1
|
import { customPlugins } from "./_internals/plugins.js";
|
|
2
|
+
import { createTypeAwareConfig } from "./_internals/type-aware.js";
|
|
3
|
+
import { GLOB_JS, GLOB_JSX, GLOB_TESTS, GLOB_TS, GLOB_TSX } from "@antfu/eslint-config";
|
|
2
4
|
import promise from "eslint-plugin-promise";
|
|
3
5
|
// src/base.ts
|
|
4
6
|
const basePerfectionistSortOptions = {
|
|
5
7
|
ignoreCase: false,
|
|
6
8
|
type: "natural"
|
|
7
9
|
};
|
|
10
|
+
const vscodeOrderSensitiveArrayProperties = [
|
|
11
|
+
"args",
|
|
12
|
+
"autoAttachSmartPattern",
|
|
13
|
+
"dependsOn",
|
|
14
|
+
"options",
|
|
15
|
+
"outFiles",
|
|
16
|
+
"problemMatcher",
|
|
17
|
+
"resolveSourceMapLocations",
|
|
18
|
+
"runtimeArgs",
|
|
19
|
+
"skipFiles"
|
|
20
|
+
].join("|");
|
|
8
21
|
function createBaseConfigs(environment = "node") {
|
|
9
22
|
return [
|
|
10
23
|
{ rules: {
|
|
11
|
-
"e18e/ban-dependencies": ["error", { allowed: ["axios"
|
|
12
|
-
"e18e/prefer-static-regex":
|
|
24
|
+
"e18e/ban-dependencies": ["error", { allowed: ["axios"] }],
|
|
25
|
+
"e18e/prefer-static-regex": "off"
|
|
13
26
|
} },
|
|
14
27
|
{
|
|
15
|
-
files: [
|
|
28
|
+
files: [
|
|
29
|
+
GLOB_JS,
|
|
30
|
+
GLOB_JSX,
|
|
31
|
+
GLOB_TS,
|
|
32
|
+
GLOB_TSX
|
|
33
|
+
],
|
|
16
34
|
plugins: {
|
|
17
35
|
kikiutils: customPlugins,
|
|
18
36
|
promise
|
|
@@ -23,18 +41,26 @@ function createBaseConfigs(environment = "node") {
|
|
|
23
41
|
}
|
|
24
42
|
},
|
|
25
43
|
{
|
|
26
|
-
files: [
|
|
27
|
-
plugins: {
|
|
28
|
-
kikiutils: customPlugins,
|
|
29
|
-
promise
|
|
30
|
-
},
|
|
44
|
+
files: [GLOB_TS, GLOB_TSX],
|
|
31
45
|
rules: {
|
|
32
|
-
|
|
33
|
-
"node/prefer-global/process": ["error", "always"],
|
|
46
|
+
"ts/array-type": ["error", { default: "array-simple" }],
|
|
34
47
|
"ts/consistent-generic-constructors": ["error", "constructor"],
|
|
35
48
|
"ts/no-redeclare": "off"
|
|
36
49
|
}
|
|
37
50
|
},
|
|
51
|
+
{
|
|
52
|
+
...createTypeAwareConfig(),
|
|
53
|
+
files: [GLOB_TS, GLOB_TSX],
|
|
54
|
+
ignores: ["**/*.config.?([cm])ts"]
|
|
55
|
+
},
|
|
56
|
+
{
|
|
57
|
+
files: GLOB_TESTS,
|
|
58
|
+
rules: {
|
|
59
|
+
"kikiutils/consistent-parameter-layout": ["error", { compactTestCalls: true }],
|
|
60
|
+
"test/valid-expect": "error",
|
|
61
|
+
"test/valid-expect-in-promise": "error"
|
|
62
|
+
}
|
|
63
|
+
},
|
|
38
64
|
{
|
|
39
65
|
files: ["**/.vscode/*.json"],
|
|
40
66
|
rules: {
|
|
@@ -43,7 +69,7 @@ function createBaseConfigs(environment = "node") {
|
|
|
43
69
|
natural: true,
|
|
44
70
|
type: "asc"
|
|
45
71
|
},
|
|
46
|
-
pathPattern: "
|
|
72
|
+
pathPattern: String.raw`^(?!.*(?:^|\.|\[")(?:${vscodeOrderSensitiveArrayProperties})(?:$|\.|\[|"\])).*`
|
|
47
73
|
}],
|
|
48
74
|
"jsonc/sort-keys": [
|
|
49
75
|
"error",
|
|
@@ -54,7 +80,8 @@ function createBaseConfigs(environment = "node") {
|
|
|
54
80
|
}
|
|
55
81
|
]
|
|
56
82
|
}
|
|
57
|
-
}
|
|
83
|
+
},
|
|
84
|
+
{ ignores: ["**/*.md/**"] }
|
|
58
85
|
];
|
|
59
86
|
}
|
|
60
87
|
function createBaseRules(environment = "node") {
|
|
@@ -74,16 +101,15 @@ function createBaseRules(environment = "node") {
|
|
|
74
101
|
"kikiutils/consistent-parameter-layout": "error",
|
|
75
102
|
"kikiutils/statement-padding": "error",
|
|
76
103
|
"max-classes-per-file": ["error", 1],
|
|
104
|
+
"no-constant-binary-expression": "error",
|
|
77
105
|
"no-promise-executor-return": ["error", { allowVoid: true }],
|
|
106
|
+
"no-useless-assignment": "error",
|
|
78
107
|
"perfectionist/sort-array-includes": ["error", basePerfectionistSortOptions],
|
|
79
108
|
"perfectionist/sort-enums": ["error", {
|
|
80
109
|
...basePerfectionistSortOptions,
|
|
81
110
|
sortByValue: "never"
|
|
82
111
|
}],
|
|
83
|
-
"perfectionist/sort-heritage-clauses": ["error",
|
|
84
|
-
ignoreCase: false,
|
|
85
|
-
type: "natural"
|
|
86
|
-
}],
|
|
112
|
+
"perfectionist/sort-heritage-clauses": ["error", basePerfectionistSortOptions],
|
|
87
113
|
"perfectionist/sort-imports": ["error", {
|
|
88
114
|
environment,
|
|
89
115
|
groups: [
|
|
@@ -133,6 +159,7 @@ function createBaseRules(environment = "node") {
|
|
|
133
159
|
}],
|
|
134
160
|
"perfectionist/sort-union-types": ["error", basePerfectionistSortOptions],
|
|
135
161
|
"perfectionist/sort-variable-declarations": ["error", basePerfectionistSortOptions],
|
|
162
|
+
"preserve-caught-error": "error",
|
|
136
163
|
"promise/no-multiple-resolved": "error",
|
|
137
164
|
"promise/no-return-in-finally": "error",
|
|
138
165
|
"promise/no-return-wrap": "error",
|
package/dist/base.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"base.js","names":[],"sources":["../src/base.ts"],"sourcesContent":["import type {\n Rules,\n TypedFlatConfigItem,\n} from '@antfu/eslint-config';\n// @ts-expect-error No declare file.\nimport promise from 'eslint-plugin-promise';\n\nimport { customPlugins } from './_internals/plugins';\n\n// Constants/Variables\nconst basePerfectionistSortOptions = {\n ignoreCase: false,\n type: 'natural',\n} as const;\n\n// Functions\nexport function createBaseConfigs(environment: 'bun' | 'node' = 'node'): TypedFlatConfigItem[] {\n return [\n // All files\n {\n rules: {\n 'e18e/ban-dependencies': [\n 'error',\n {\n allowed: [\n 'axios',\n 'rimraf',\n ],\n },\n ],\n 'e18e/prefer-static-regex': ['off'],\n },\n },\n // JavaScript\n {\n files: ['**/*.{cjs,js,mjs}'],\n plugins: {\n kikiutils: customPlugins,\n promise,\n },\n rules: {\n ...createBaseRules(environment),\n 'node/prefer-global/process': [\n 'error',\n 'always',\n ],\n },\n },\n // TypeScript\n {\n files: ['**/*.{ts,tsx}'],\n plugins: {\n kikiutils: customPlugins,\n promise,\n },\n rules: {\n ...createBaseRules(environment),\n 'node/prefer-global/process': [\n 'error',\n 'always',\n ],\n 'ts/consistent-generic-constructors': [\n 'error',\n 'constructor',\n ],\n 'ts/no-redeclare': 'off',\n },\n },\n // VsCode jsonc\n {\n files: ['**/.vscode/*.json'],\n rules: {\n 'jsonc/sort-array-values': [\n 'error',\n {\n order: {\n natural: true,\n type: 'asc',\n },\n pathPattern: '^.*$',\n },\n ],\n 'jsonc/sort-keys': [\n 'error',\n 'asc',\n {\n caseSensitive: true,\n natural: true,\n },\n ],\n },\n },\n ];\n}\n\nexport function createBaseRules(environment: 'bun' | 'node' = 'node'): Rules {\n return {\n 'antfu/consistent-list-newline': [\n 'error',\n {\n ArrayExpression: false,\n ArrayPattern: false,\n },\n ],\n 'antfu/curly': 'off',\n 'antfu/if-newline': 'off',\n 'antfu/no-top-level-await': 'off',\n 'antfu/reasonable-newline': 'off',\n 'arrow-body-style': [\n 'error',\n 'as-needed',\n ],\n 'curly': [\n 'error',\n 'multi-line',\n ],\n 'kikiutils/compact-iteration-layout': 'error',\n 'kikiutils/consistent-condition-layout': 'error',\n 'kikiutils/consistent-parameter-layout': 'error',\n 'kikiutils/statement-padding': 'error',\n 'max-classes-per-file': [\n 'error',\n 1,\n ],\n 'no-promise-executor-return': [\n 'error',\n { allowVoid: true },\n ],\n 'perfectionist/sort-array-includes': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-enums': [\n 'error',\n {\n ...basePerfectionistSortOptions,\n sortByValue: 'never',\n },\n ],\n 'perfectionist/sort-heritage-clauses': [\n 'error',\n {\n ignoreCase: false,\n type: 'natural',\n },\n ],\n 'perfectionist/sort-imports': [\n 'error',\n {\n environment,\n groups: [\n 'side-effect',\n 'side-effect-style',\n 'style',\n [\n 'value-builtin',\n 'type-builtin',\n ],\n [\n 'value-external',\n 'type-external',\n ],\n [\n 'value-internal',\n 'type-internal',\n ],\n [\n 'value-parent',\n 'type-parent',\n ],\n [\n 'value-sibling',\n 'type-sibling',\n ],\n [\n 'value-index',\n 'type-index',\n ],\n 'unknown',\n ],\n ignoreCase: false,\n internalPattern: [\n '^#.*',\n '^@/.*',\n '^~/.*',\n ],\n type: 'natural',\n },\n ],\n 'perfectionist/sort-interfaces': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-intersection-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-maps': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-modules': [\n 'error',\n {\n ...basePerfectionistSortOptions,\n groups: [\n 'declare-type',\n [\n 'export-type',\n 'type',\n ],\n 'declare-interface',\n [\n 'export-interface',\n 'interface',\n ],\n 'declare-enum',\n [\n 'enum',\n 'export-enum',\n ],\n 'declare-class',\n [\n 'class',\n 'export-class',\n ],\n 'declare-function',\n [\n 'export-function',\n 'function',\n ],\n ],\n },\n ],\n 'perfectionist/sort-object-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-objects': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-sets': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-switch-case': [\n 'error',\n {\n ignoreCase: false,\n type: 'natural',\n },\n ],\n 'perfectionist/sort-union-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-variable-declarations': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'promise/no-multiple-resolved': 'error',\n 'promise/no-return-in-finally': 'error',\n 'promise/no-return-wrap': 'error',\n 'require-await': 'error',\n 'style/array-bracket-newline': [\n 'error',\n { multiline: true },\n ],\n 'style/array-element-newline': [\n 'error',\n {\n ArrayExpression: {\n consistent: true,\n minItems: 2,\n },\n ArrayPattern: { minItems: 3 },\n },\n ],\n 'style/arrow-parens': [\n 'error',\n 'always',\n ],\n 'style/brace-style': [\n 'error',\n '1tbs',\n { allowSingleLine: false },\n ],\n 'style/function-call-spacing': [\n 'error',\n 'never',\n ],\n 'style/indent': [\n 'error',\n 4,\n ],\n 'style/max-len': [\n 'warn',\n {\n code: 120,\n comments: 120,\n },\n ],\n 'style/member-delimiter-style': [\n 'error',\n {\n multiline: {\n delimiter: 'semi',\n requireLast: true,\n },\n },\n ],\n 'style/no-extra-parens': [\n 'error',\n 'all',\n { nestedBinaryExpressions: false },\n ],\n 'style/no-extra-semi': 'error',\n 'style/object-curly-newline': [\n 'error',\n {\n ExportDeclaration: {\n minProperties: 2,\n multiline: true,\n },\n ImportDeclaration: {\n minProperties: 2,\n multiline: true,\n },\n ObjectExpression: {\n minProperties: 2,\n multiline: true,\n },\n ObjectPattern: {\n minProperties: 3,\n multiline: true,\n },\n },\n ],\n 'style/operator-linebreak': [\n 'error',\n 'before',\n { overrides: { '=': 'after' } },\n ],\n 'style/padding-line-between-statements': [\n 'error',\n {\n blankLine: 'always',\n next: [\n 'class',\n 'enum',\n 'function',\n ],\n prev: '*',\n },\n {\n blankLine: 'always',\n next: '*',\n prev: [\n 'class',\n 'function',\n ],\n },\n ],\n 'style/semi': [\n 'error',\n 'always',\n ],\n };\n}\n"],"mappings":";;;AAUA,MAAM,+BAA+B;CACjC,YAAY;CACZ,MAAM;AACV;AAGA,SAAgB,kBAAkB,cAA8B,QAA+B;CAC3F,OAAO;EAEH,EACI,OAAO;GACH,yBAAyB,CACrB,SACA,EACI,SAAS,CACL,SACA,QACJ,EACJ,CACJ;GACA,4BAA4B,CAAC,KAAK;EACtC,EACJ;EAEA;GACI,OAAO,CAAC,mBAAmB;GAC3B,SAAS;IACL,WAAW;IACX;GACJ;GACA,OAAO;IACH,GAAG,gBAAgB,WAAW;IAC9B,8BAA8B,CAC1B,SACA,QACJ;GACJ;EACJ;EAEA;GACI,OAAO,CAAC,eAAe;GACvB,SAAS;IACL,WAAW;IACX;GACJ;GACA,OAAO;IACH,GAAG,gBAAgB,WAAW;IAC9B,8BAA8B,CAC1B,SACA,QACJ;IACA,sCAAsC,CAClC,SACA,aACJ;IACA,mBAAmB;GACvB;EACJ;EAEA;GACI,OAAO,CAAC,mBAAmB;GAC3B,OAAO;IACH,2BAA2B,CACvB,SACA;KACI,OAAO;MACH,SAAS;MACT,MAAM;KACV;KACA,aAAa;IACjB,CACJ;IACA,mBAAmB;KACf;KACA;KACA;MACI,eAAe;MACf,SAAS;KACb;IACJ;GACJ;EACJ;CACJ;AACJ;AAEA,SAAgB,gBAAgB,cAA8B,QAAe;CACzE,OAAO;EACH,iCAAiC,CAC7B,SACA;GACI,iBAAiB;GACjB,cAAc;EAClB,CACJ;EACA,eAAe;EACf,oBAAoB;EACpB,4BAA4B;EAC5B,4BAA4B;EAC5B,oBAAoB,CAChB,SACA,WACJ;EACA,SAAS,CACL,SACA,YACJ;EACA,sCAAsC;EACtC,yCAAyC;EACzC,yCAAyC;EACzC,+BAA+B;EAC/B,wBAAwB,CACpB,SACA,CACJ;EACA,8BAA8B,CAC1B,SACA,EAAE,WAAW,KAAK,CACtB;EACA,qCAAqC,CACjC,SACA,4BACJ;EACA,4BAA4B,CACxB,SACA;GACI,GAAG;GACH,aAAa;EACjB,CACJ;EACA,uCAAuC,CACnC,SACA;GACI,YAAY;GACZ,MAAM;EACV,CACJ;EACA,8BAA8B,CAC1B,SACA;GACI;GACA,QAAQ;IACJ;IACA;IACA;IACA,CACI,iBACA,cACJ;IACA,CACI,kBACA,eACJ;IACA,CACI,kBACA,eACJ;IACA,CACI,gBACA,aACJ;IACA,CACI,iBACA,cACJ;IACA,CACI,eACA,YACJ;IACA;GACJ;GACA,YAAY;GACZ,iBAAiB;IACb;IACA;IACA;GACJ;GACA,MAAM;EACV,CACJ;EACA,iCAAiC,CAC7B,SACA,4BACJ;EACA,yCAAyC,CACrC,SACA,4BACJ;EACA,2BAA2B,CACvB,SACA,4BACJ;EACA,8BAA8B,CAC1B,SACA;GACI,GAAG;GACH,QAAQ;IACJ;IACA,CACI,eACA,MACJ;IACA;IACA,CACI,oBACA,WACJ;IACA;IACA,CACI,QACA,aACJ;IACA;IACA,CACI,SACA,cACJ;IACA;IACA,CACI,mBACA,UACJ;GACJ;EACJ,CACJ;EACA,mCAAmC,CAC/B,SACA,4BACJ;EACA,8BAA8B,CAC1B,SACA,4BACJ;EACA,2BAA2B,CACvB,SACA,4BACJ;EACA,kCAAkC,CAC9B,SACA;GACI,YAAY;GACZ,MAAM;EACV,CACJ;EACA,kCAAkC,CAC9B,SACA,4BACJ;EACA,4CAA4C,CACxC,SACA,4BACJ;EACA,gCAAgC;EAChC,gCAAgC;EAChC,0BAA0B;EAC1B,iBAAiB;EACjB,+BAA+B,CAC3B,SACA,EAAE,WAAW,KAAK,CACtB;EACA,+BAA+B,CAC3B,SACA;GACI,iBAAiB;IACb,YAAY;IACZ,UAAU;GACd;GACA,cAAc,EAAE,UAAU,EAAE;EAChC,CACJ;EACA,sBAAsB,CAClB,SACA,QACJ;EACA,qBAAqB;GACjB;GACA;GACA,EAAE,iBAAiB,MAAM;EAC7B;EACA,+BAA+B,CAC3B,SACA,OACJ;EACA,gBAAgB,CACZ,SACA,CACJ;EACA,iBAAiB,CACb,QACA;GACI,MAAM;GACN,UAAU;EACd,CACJ;EACA,gCAAgC,CAC5B,SACA,EACI,WAAW;GACP,WAAW;GACX,aAAa;EACjB,EACJ,CACJ;EACA,yBAAyB;GACrB;GACA;GACA,EAAE,yBAAyB,MAAM;EACrC;EACA,uBAAuB;EACvB,8BAA8B,CAC1B,SACA;GACI,mBAAmB;IACf,eAAe;IACf,WAAW;GACf;GACA,mBAAmB;IACf,eAAe;IACf,WAAW;GACf;GACA,kBAAkB;IACd,eAAe;IACf,WAAW;GACf;GACA,eAAe;IACX,eAAe;IACf,WAAW;GACf;EACJ,CACJ;EACA,4BAA4B;GACxB;GACA;GACA,EAAE,WAAW,EAAE,KAAK,QAAQ,EAAE;EAClC;EACA,yCAAyC;GACrC;GACA;IACI,WAAW;IACX,MAAM;KACF;KACA;KACA;IACJ;IACA,MAAM;GACV;GACA;IACI,WAAW;IACX,MAAM;IACN,MAAM,CACF,SACA,UACJ;GACJ;EACJ;EACA,cAAc,CACV,SACA,QACJ;CACJ;AACJ"}
|
|
1
|
+
{"version":3,"file":"base.js","names":[],"sources":["../src/base.ts"],"sourcesContent":["import type {\n Rules,\n TypedFlatConfigItem,\n} from '@antfu/eslint-config';\nimport {\n GLOB_JS,\n GLOB_JSX,\n GLOB_TESTS,\n GLOB_TS,\n GLOB_TSX,\n} from '@antfu/eslint-config';\n// @ts-expect-error No declare file.\nimport promise from 'eslint-plugin-promise';\n\nimport { customPlugins } from './_internals/plugins';\nimport { createTypeAwareConfig } from './_internals/type-aware';\n\n// Constants/Variables\nconst basePerfectionistSortOptions = {\n ignoreCase: false,\n type: 'natural',\n} as const;\n\nconst vscodeOrderSensitiveArrayProperties = [\n 'args',\n 'autoAttachSmartPattern',\n 'dependsOn',\n 'options',\n 'outFiles',\n 'problemMatcher',\n 'resolveSourceMapLocations',\n 'runtimeArgs',\n 'skipFiles',\n].join('|');\n\n// Functions\nexport function createBaseConfigs(environment: 'bun' | 'node' = 'node'): TypedFlatConfigItem[] {\n return [\n // All files\n {\n rules: {\n 'e18e/ban-dependencies': [\n 'error',\n { allowed: ['axios'] },\n ],\n 'e18e/prefer-static-regex': 'off',\n },\n },\n // JavaScript and TypeScript\n {\n files: [\n GLOB_JS,\n GLOB_JSX,\n GLOB_TS,\n GLOB_TSX,\n ],\n plugins: {\n kikiutils: customPlugins,\n promise,\n },\n rules: {\n ...createBaseRules(environment),\n 'node/prefer-global/process': [\n 'error',\n 'always',\n ],\n },\n },\n // TypeScript\n {\n files: [\n GLOB_TS,\n GLOB_TSX,\n ],\n rules: {\n 'ts/array-type': [\n 'error',\n { default: 'array-simple' },\n ],\n 'ts/consistent-generic-constructors': [\n 'error',\n 'constructor',\n ],\n 'ts/no-redeclare': 'off',\n },\n },\n // Type-aware TypeScript\n {\n ...createTypeAwareConfig(),\n files: [\n GLOB_TS,\n GLOB_TSX,\n ],\n ignores: ['**/*.config.?([cm])ts'],\n },\n // Tests\n {\n files: GLOB_TESTS,\n rules: {\n 'kikiutils/consistent-parameter-layout': [\n 'error',\n { compactTestCalls: true },\n ],\n 'test/valid-expect': 'error',\n 'test/valid-expect-in-promise': 'error',\n },\n },\n // VS Code JSONC\n {\n files: ['**/.vscode/*.json'],\n rules: {\n 'jsonc/sort-array-values': [\n 'error',\n {\n order: {\n natural: true,\n type: 'asc',\n },\n // Preserve ordered fields and any argument or option arrays nested inside them.\n // eslint-disable-next-line style/max-len\n pathPattern: String.raw`^(?!.*(?:^|\\.|\\[\")(?:${vscodeOrderSensitiveArrayProperties})(?:$|\\.|\\[|\"\\])).*`,\n },\n ],\n 'jsonc/sort-keys': [\n 'error',\n 'asc',\n {\n caseSensitive: true,\n natural: true,\n },\n ],\n },\n },\n // Ignore all extracted Markdown code blocks, but keep linting Markdown itself.\n { ignores: ['**/*.md/**'] },\n ];\n}\n\nexport function createBaseRules(environment: 'bun' | 'node' = 'node'): Rules {\n return {\n 'antfu/consistent-list-newline': [\n 'error',\n {\n ArrayExpression: false,\n ArrayPattern: false,\n },\n ],\n 'antfu/curly': 'off',\n 'antfu/if-newline': 'off',\n 'antfu/no-top-level-await': 'off',\n 'antfu/reasonable-newline': 'off',\n 'arrow-body-style': [\n 'error',\n 'as-needed',\n ],\n 'curly': [\n 'error',\n 'multi-line',\n ],\n 'kikiutils/compact-iteration-layout': 'error',\n 'kikiutils/consistent-condition-layout': 'error',\n 'kikiutils/consistent-parameter-layout': 'error',\n 'kikiutils/statement-padding': 'error',\n 'max-classes-per-file': [\n 'error',\n 1,\n ],\n 'no-constant-binary-expression': 'error',\n 'no-promise-executor-return': [\n 'error',\n { allowVoid: true },\n ],\n 'no-useless-assignment': 'error',\n 'perfectionist/sort-array-includes': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-enums': [\n 'error',\n {\n ...basePerfectionistSortOptions,\n sortByValue: 'never',\n },\n ],\n 'perfectionist/sort-heritage-clauses': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-imports': [\n 'error',\n {\n environment,\n groups: [\n 'side-effect',\n 'side-effect-style',\n 'style',\n [\n 'value-builtin',\n 'type-builtin',\n ],\n [\n 'value-external',\n 'type-external',\n ],\n [\n 'value-internal',\n 'type-internal',\n ],\n [\n 'value-parent',\n 'type-parent',\n ],\n [\n 'value-sibling',\n 'type-sibling',\n ],\n [\n 'value-index',\n 'type-index',\n ],\n 'unknown',\n ],\n ignoreCase: false,\n internalPattern: [\n '^#.*',\n '^@/.*',\n '^~/.*',\n ],\n type: 'natural',\n },\n ],\n 'perfectionist/sort-interfaces': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-intersection-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-maps': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-modules': [\n 'error',\n {\n ...basePerfectionistSortOptions,\n groups: [\n 'declare-type',\n [\n 'export-type',\n 'type',\n ],\n 'declare-interface',\n [\n 'export-interface',\n 'interface',\n ],\n 'declare-enum',\n [\n 'enum',\n 'export-enum',\n ],\n 'declare-class',\n [\n 'class',\n 'export-class',\n ],\n 'declare-function',\n [\n 'export-function',\n 'function',\n ],\n ],\n },\n ],\n 'perfectionist/sort-object-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-objects': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-sets': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-switch-case': [\n 'error',\n {\n ignoreCase: false,\n type: 'natural',\n },\n ],\n 'perfectionist/sort-union-types': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'perfectionist/sort-variable-declarations': [\n 'error',\n basePerfectionistSortOptions,\n ],\n 'preserve-caught-error': 'error',\n 'promise/no-multiple-resolved': 'error',\n 'promise/no-return-in-finally': 'error',\n 'promise/no-return-wrap': 'error',\n 'require-await': 'error',\n 'style/array-bracket-newline': [\n 'error',\n { multiline: true },\n ],\n 'style/array-element-newline': [\n 'error',\n {\n ArrayExpression: {\n consistent: true,\n minItems: 2,\n },\n ArrayPattern: { minItems: 3 },\n },\n ],\n 'style/arrow-parens': [\n 'error',\n 'always',\n ],\n 'style/brace-style': [\n 'error',\n '1tbs',\n { allowSingleLine: false },\n ],\n 'style/function-call-spacing': [\n 'error',\n 'never',\n ],\n 'style/indent': [\n 'error',\n 4,\n ],\n 'style/max-len': [\n 'warn',\n {\n code: 120,\n comments: 120,\n },\n ],\n 'style/member-delimiter-style': [\n 'error',\n {\n multiline: {\n delimiter: 'semi',\n requireLast: true,\n },\n },\n ],\n 'style/no-extra-parens': [\n 'error',\n 'all',\n { nestedBinaryExpressions: false },\n ],\n 'style/no-extra-semi': 'error',\n 'style/object-curly-newline': [\n 'error',\n {\n ExportDeclaration: {\n minProperties: 2,\n multiline: true,\n },\n ImportDeclaration: {\n minProperties: 2,\n multiline: true,\n },\n ObjectExpression: {\n minProperties: 2,\n multiline: true,\n },\n ObjectPattern: {\n minProperties: 3,\n multiline: true,\n },\n },\n ],\n 'style/operator-linebreak': [\n 'error',\n 'before',\n { overrides: { '=': 'after' } },\n ],\n 'style/padding-line-between-statements': [\n 'error',\n {\n blankLine: 'always',\n next: [\n 'class',\n 'enum',\n 'function',\n ],\n prev: '*',\n },\n {\n blankLine: 'always',\n next: '*',\n prev: [\n 'class',\n 'function',\n ],\n },\n ],\n 'style/semi': [\n 'error',\n 'always',\n ],\n };\n}\n"],"mappings":";;;;;AAkBA,MAAM,+BAA+B;CACjC,YAAY;CACZ,MAAM;AACV;AAEA,MAAM,sCAAsC;CACxC;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;AACJ,CAAC,CAAC,KAAK,GAAG;AAGV,SAAgB,kBAAkB,cAA8B,QAA+B;CAC3F,OAAO;EAEH,EACI,OAAO;GACH,yBAAyB,CACrB,SACA,EAAE,SAAS,CAAC,OAAO,EAAE,CACzB;GACA,4BAA4B;EAChC,EACJ;EAEA;GACI,OAAO;IACH;IACA;IACA;IACA;GACJ;GACA,SAAS;IACL,WAAW;IACX;GACJ;GACA,OAAO;IACH,GAAG,gBAAgB,WAAW;IAC9B,8BAA8B,CAC1B,SACA,QACJ;GACJ;EACJ;EAEA;GACI,OAAO,CACH,SACA,QACJ;GACA,OAAO;IACH,iBAAiB,CACb,SACA,EAAE,SAAS,eAAe,CAC9B;IACA,sCAAsC,CAClC,SACA,aACJ;IACA,mBAAmB;GACvB;EACJ;EAEA;GACI,GAAG,sBAAsB;GACzB,OAAO,CACH,SACA,QACJ;GACA,SAAS,CAAC,uBAAuB;EACrC;EAEA;GACI,OAAO;GACP,OAAO;IACH,yCAAyC,CACrC,SACA,EAAE,kBAAkB,KAAK,CAC7B;IACA,qBAAqB;IACrB,gCAAgC;GACpC;EACJ;EAEA;GACI,OAAO,CAAC,mBAAmB;GAC3B,OAAO;IACH,2BAA2B,CACvB,SACA;KACI,OAAO;MACH,SAAS;MACT,MAAM;KACV;KAGA,aAAa,OAAO,GAAG,wBAAwB,oCAAoC;IACvF,CACJ;IACA,mBAAmB;KACf;KACA;KACA;MACI,eAAe;MACf,SAAS;KACb;IACJ;GACJ;EACJ;EAEA,EAAE,SAAS,CAAC,YAAY,EAAE;CAC9B;AACJ;AAEA,SAAgB,gBAAgB,cAA8B,QAAe;CACzE,OAAO;EACH,iCAAiC,CAC7B,SACA;GACI,iBAAiB;GACjB,cAAc;EAClB,CACJ;EACA,eAAe;EACf,oBAAoB;EACpB,4BAA4B;EAC5B,4BAA4B;EAC5B,oBAAoB,CAChB,SACA,WACJ;EACA,SAAS,CACL,SACA,YACJ;EACA,sCAAsC;EACtC,yCAAyC;EACzC,yCAAyC;EACzC,+BAA+B;EAC/B,wBAAwB,CACpB,SACA,CACJ;EACA,iCAAiC;EACjC,8BAA8B,CAC1B,SACA,EAAE,WAAW,KAAK,CACtB;EACA,yBAAyB;EACzB,qCAAqC,CACjC,SACA,4BACJ;EACA,4BAA4B,CACxB,SACA;GACI,GAAG;GACH,aAAa;EACjB,CACJ;EACA,uCAAuC,CACnC,SACA,4BACJ;EACA,8BAA8B,CAC1B,SACA;GACI;GACA,QAAQ;IACJ;IACA;IACA;IACA,CACI,iBACA,cACJ;IACA,CACI,kBACA,eACJ;IACA,CACI,kBACA,eACJ;IACA,CACI,gBACA,aACJ;IACA,CACI,iBACA,cACJ;IACA,CACI,eACA,YACJ;IACA;GACJ;GACA,YAAY;GACZ,iBAAiB;IACb;IACA;IACA;GACJ;GACA,MAAM;EACV,CACJ;EACA,iCAAiC,CAC7B,SACA,4BACJ;EACA,yCAAyC,CACrC,SACA,4BACJ;EACA,2BAA2B,CACvB,SACA,4BACJ;EACA,8BAA8B,CAC1B,SACA;GACI,GAAG;GACH,QAAQ;IACJ;IACA,CACI,eACA,MACJ;IACA;IACA,CACI,oBACA,WACJ;IACA;IACA,CACI,QACA,aACJ;IACA;IACA,CACI,SACA,cACJ;IACA;IACA,CACI,mBACA,UACJ;GACJ;EACJ,CACJ;EACA,mCAAmC,CAC/B,SACA,4BACJ;EACA,8BAA8B,CAC1B,SACA,4BACJ;EACA,2BAA2B,CACvB,SACA,4BACJ;EACA,kCAAkC,CAC9B,SACA;GACI,YAAY;GACZ,MAAM;EACV,CACJ;EACA,kCAAkC,CAC9B,SACA,4BACJ;EACA,4CAA4C,CACxC,SACA,4BACJ;EACA,yBAAyB;EACzB,gCAAgC;EAChC,gCAAgC;EAChC,0BAA0B;EAC1B,iBAAiB;EACjB,+BAA+B,CAC3B,SACA,EAAE,WAAW,KAAK,CACtB;EACA,+BAA+B,CAC3B,SACA;GACI,iBAAiB;IACb,YAAY;IACZ,UAAU;GACd;GACA,cAAc,EAAE,UAAU,EAAE;EAChC,CACJ;EACA,sBAAsB,CAClB,SACA,QACJ;EACA,qBAAqB;GACjB;GACA;GACA,EAAE,iBAAiB,MAAM;EAC7B;EACA,+BAA+B,CAC3B,SACA,OACJ;EACA,gBAAgB,CACZ,SACA,CACJ;EACA,iBAAiB,CACb,QACA;GACI,MAAM;GACN,UAAU;EACd,CACJ;EACA,gCAAgC,CAC5B,SACA,EACI,WAAW;GACP,WAAW;GACX,aAAa;EACjB,EACJ,CACJ;EACA,yBAAyB;GACrB;GACA;GACA,EAAE,yBAAyB,MAAM;EACrC;EACA,uBAAuB;EACvB,8BAA8B,CAC1B,SACA;GACI,mBAAmB;IACf,eAAe;IACf,WAAW;GACf;GACA,mBAAmB;IACf,eAAe;IACf,WAAW;GACf;GACA,kBAAkB;IACd,eAAe;IACf,WAAW;GACf;GACA,eAAe;IACX,eAAe;IACf,WAAW;GACf;EACJ,CACJ;EACA,4BAA4B;GACxB;GACA;GACA,EAAE,WAAW,EAAE,KAAK,QAAQ,EAAE;EAClC;EACA,yCAAyC;GACrC;GACA;IACI,WAAW;IACX,MAAM;KACF;KACA;KACA;IACJ;IACA,MAAM;GACV;GACA;IACI,WAAW;IACX,MAAM;IACN,MAAM,CACF,SACA,UACJ;GACJ;EACJ;EACA,cAAc,CACV,SACA,QACJ;CACJ;AACJ"}
|