@kouts/eslint-config 3.1.1 → 3.1.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/dist/index.js CHANGED
@@ -2,11 +2,640 @@ import js from '@eslint/js';
2
2
  import pluginHtml from 'eslint-plugin-html';
3
3
  import pluginPrettier from 'eslint-plugin-prettier/recommended';
4
4
  import pluginSimpleImportSort from 'eslint-plugin-simple-import-sort';
5
- import neostandard, { plugins, resolveIgnoresFromGitignore } from 'neostandard';
6
- export { plugins } from 'neostandard';
5
+ import { readFileSync } from 'node:fs';
6
+ import { join, dirname } from 'node:path';
7
+ import { fixupConfigRules } from '@eslint/compat';
8
+ import { gitignoreToMinimatch } from '@humanwhocodes/gitignore-to-minimatch';
9
+ import stylistic from '@stylistic/eslint-plugin';
10
+ import importX from 'eslint-plugin-import-x';
11
+ import pluginN from 'eslint-plugin-n';
12
+ import pluginPromise from 'eslint-plugin-promise';
13
+ import { findUpSync } from 'find-up';
14
+ import globals from 'globals';
15
+ import tseslint from 'typescript-eslint';
7
16
  import pluginVitest from '@vitest/eslint-plugin';
8
17
  import pluginVue from 'eslint-plugin-vue';
9
18
 
19
+ const plugins = {
20
+ "@stylistic": stylistic,
21
+ "import-x": importX,
22
+ n: pluginN,
23
+ promise: pluginPromise,
24
+ // react: pluginReact,
25
+ "typescript-eslint": tseslint
26
+ };
27
+ const base = {
28
+ name: "neostandard/base",
29
+ languageOptions: {
30
+ ecmaVersion: 2022,
31
+ sourceType: "module",
32
+ globals: {
33
+ ...globals.es2022,
34
+ ...globals.node,
35
+ document: "readonly",
36
+ navigator: "readonly",
37
+ window: "readonly"
38
+ }
39
+ },
40
+ plugins: {
41
+ n: plugins.n
42
+ },
43
+ rules: {
44
+ "no-var": "warn",
45
+ "object-shorthand": ["warn", "properties"],
46
+ "accessor-pairs": ["error", { setWithoutGet: true, enforceForClassMembers: true }],
47
+ "array-callback-return": [
48
+ "error",
49
+ {
50
+ allowImplicit: false,
51
+ checkForEach: false
52
+ }
53
+ ],
54
+ camelcase: [
55
+ "error",
56
+ {
57
+ allow: ["^UNSAFE_"],
58
+ properties: "never",
59
+ ignoreGlobals: true
60
+ }
61
+ ],
62
+ "constructor-super": "error",
63
+ curly: ["error", "multi-line"],
64
+ "default-case-last": "error",
65
+ "dot-notation": ["error", { allowKeywords: true }],
66
+ eqeqeq: ["error", "always", { null: "ignore" }],
67
+ "new-cap": ["error", { newIsCap: true, capIsNew: false, properties: true }],
68
+ "no-array-constructor": "error",
69
+ "no-async-promise-executor": "error",
70
+ "no-caller": "error",
71
+ "no-case-declarations": "error",
72
+ "no-class-assign": "error",
73
+ "no-compare-neg-zero": "error",
74
+ "no-cond-assign": "error",
75
+ "no-const-assign": "error",
76
+ "no-constant-condition": ["error", { checkLoops: false }],
77
+ "no-control-regex": "error",
78
+ "no-debugger": "error",
79
+ "no-delete-var": "error",
80
+ "no-dupe-args": "error",
81
+ "no-dupe-class-members": "error",
82
+ "no-dupe-keys": "error",
83
+ "no-duplicate-case": "error",
84
+ "no-useless-backreference": "error",
85
+ "no-empty": ["error", { allowEmptyCatch: true }],
86
+ "no-empty-character-class": "error",
87
+ "no-empty-pattern": "error",
88
+ "no-eval": "error",
89
+ "no-ex-assign": "error",
90
+ "no-extend-native": "error",
91
+ "no-extra-bind": "error",
92
+ "no-extra-boolean-cast": "error",
93
+ "no-fallthrough": "error",
94
+ "no-func-assign": "error",
95
+ "no-global-assign": "error",
96
+ "no-implied-eval": "error",
97
+ "no-import-assign": "error",
98
+ "no-invalid-regexp": "error",
99
+ "no-irregular-whitespace": "error",
100
+ "no-iterator": "error",
101
+ "no-labels": ["error", { allowLoop: false, allowSwitch: false }],
102
+ "no-lone-blocks": "error",
103
+ "no-loss-of-precision": "error",
104
+ "no-misleading-character-class": "error",
105
+ "no-prototype-builtins": "error",
106
+ "no-useless-catch": "error",
107
+ "no-multi-str": "error",
108
+ "no-new": "error",
109
+ "no-new-func": "error",
110
+ "no-object-constructor": "error",
111
+ "no-new-native-nonconstructor": "error",
112
+ "no-new-wrappers": "error",
113
+ "no-obj-calls": "error",
114
+ "no-octal": "error",
115
+ "no-octal-escape": "error",
116
+ "no-proto": "error",
117
+ "no-redeclare": ["error", { builtinGlobals: false }],
118
+ "no-regex-spaces": "error",
119
+ "no-return-assign": ["error", "except-parens"],
120
+ "no-self-assign": ["error", { props: true }],
121
+ "no-self-compare": "error",
122
+ "no-sequences": "error",
123
+ "no-shadow-restricted-names": "error",
124
+ "no-sparse-arrays": "error",
125
+ "no-template-curly-in-string": "error",
126
+ "no-this-before-super": "error",
127
+ "no-throw-literal": "error",
128
+ "no-undef": "error",
129
+ "no-undef-init": "error",
130
+ "no-unexpected-multiline": "error",
131
+ "no-unmodified-loop-condition": "error",
132
+ "no-unneeded-ternary": ["error", { defaultAssignment: false }],
133
+ "no-unreachable": "error",
134
+ "no-unreachable-loop": "error",
135
+ "no-unsafe-finally": "error",
136
+ "no-unsafe-negation": "error",
137
+ "no-unused-expressions": [
138
+ "error",
139
+ {
140
+ allowShortCircuit: true,
141
+ allowTernary: true,
142
+ allowTaggedTemplates: true
143
+ }
144
+ ],
145
+ "no-unused-vars": [
146
+ "error",
147
+ {
148
+ args: "none",
149
+ caughtErrors: "none",
150
+ ignoreRestSiblings: true,
151
+ vars: "all"
152
+ }
153
+ ],
154
+ "no-use-before-define": ["error", { functions: false, classes: false, variables: false }],
155
+ "no-useless-call": "error",
156
+ "no-useless-computed-key": "error",
157
+ "no-useless-constructor": "error",
158
+ "no-useless-escape": "error",
159
+ "no-useless-rename": "error",
160
+ "no-useless-return": "error",
161
+ "no-void": "error",
162
+ "no-with": "error",
163
+ "one-var": ["error", { initialized: "never" }],
164
+ "prefer-const": ["error", { destructuring: "all" }],
165
+ "prefer-promise-reject-errors": "error",
166
+ "prefer-regex-literals": ["error", { disallowRedundantWrapping: true }],
167
+ "symbol-description": "error",
168
+ "unicode-bom": ["error", "never"],
169
+ "use-isnan": [
170
+ "error",
171
+ {
172
+ enforceForSwitchCase: true,
173
+ enforceForIndexOf: true
174
+ }
175
+ ],
176
+ "valid-typeof": ["error", { requireStringLiterals: true }],
177
+ yoda: ["error", "never"],
178
+ "n/handle-callback-err": ["error", "^(err|error)$"],
179
+ "n/no-callback-literal": "error",
180
+ "n/no-deprecated-api": "error",
181
+ "n/no-exports-assign": "error",
182
+ "n/no-new-require": "error",
183
+ "n/no-path-concat": "error",
184
+ "n/process-exit-as-throw": "error",
185
+ "promise/param-names": "error"
186
+ }
187
+ };
188
+ const modernization = {
189
+ name: "neostandard/modernization-since-standard-17",
190
+ rules: {
191
+ "dot-notation": "off",
192
+ "n/no-deprecated-api": "warn"
193
+ }
194
+ };
195
+ const promise = fixupConfigRules(pluginPromise.configs["flat/recommended"]);
196
+ const promiseConfigs = Array.isArray(promise) ? promise : [promise];
197
+ const modernizationStyles = {
198
+ name: "neostandard/style/modernization-since-standard-17",
199
+ rules: {
200
+ "@stylistic/comma-dangle": [
201
+ "warn",
202
+ {
203
+ arrays: "ignore",
204
+ enums: "ignore",
205
+ exports: "ignore",
206
+ imports: "ignore",
207
+ objects: "ignore"
208
+ }
209
+ ],
210
+ "@stylistic/no-multi-spaces": ["error", { ignoreEOLComments: true }]
211
+ }
212
+ };
213
+ const style = {
214
+ name: "neostandard/style",
215
+ plugins: {
216
+ "@stylistic": plugins["@stylistic"]
217
+ },
218
+ rules: {
219
+ "@stylistic/array-bracket-spacing": ["error", "never"],
220
+ "@stylistic/arrow-spacing": ["error", { before: true, after: true }],
221
+ "@stylistic/block-spacing": ["error", "always"],
222
+ "@stylistic/brace-style": ["error", "1tbs", { allowSingleLine: true }],
223
+ "@stylistic/comma-dangle": [
224
+ "error",
225
+ {
226
+ arrays: "never",
227
+ objects: "never",
228
+ imports: "never",
229
+ exports: "never",
230
+ functions: "never"
231
+ }
232
+ ],
233
+ "@stylistic/comma-spacing": ["error", { before: false, after: true }],
234
+ "@stylistic/comma-style": ["error", "last"],
235
+ "@stylistic/computed-property-spacing": ["error", "never", { enforceForClassMembers: true }],
236
+ "@stylistic/dot-location": ["error", "property"],
237
+ "@stylistic/eol-last": "error",
238
+ "@stylistic/func-call-spacing": ["error", "never"],
239
+ "@stylistic/generator-star-spacing": ["error", { before: true, after: true }],
240
+ "@stylistic/indent": [
241
+ "error",
242
+ 2,
243
+ {
244
+ SwitchCase: 1,
245
+ VariableDeclarator: 1,
246
+ outerIIFEBody: 1,
247
+ MemberExpression: 1,
248
+ FunctionDeclaration: { parameters: 1, body: 1 },
249
+ FunctionExpression: { parameters: 1, body: 1 },
250
+ CallExpression: { arguments: 1 },
251
+ ArrayExpression: 1,
252
+ ObjectExpression: 1,
253
+ ImportDeclaration: 1,
254
+ flatTernaryExpressions: false,
255
+ ignoreComments: false,
256
+ ignoredNodes: [
257
+ "TemplateLiteral *",
258
+ "JSXElement",
259
+ "JSXElement > *",
260
+ "JSXAttribute",
261
+ "JSXIdentifier",
262
+ "JSXNamespacedName",
263
+ "JSXMemberExpression",
264
+ "JSXSpreadAttribute",
265
+ "JSXExpressionContainer",
266
+ "JSXOpeningElement",
267
+ "JSXClosingElement",
268
+ "JSXFragment",
269
+ "JSXOpeningFragment",
270
+ "JSXClosingFragment",
271
+ "JSXText",
272
+ "JSXEmptyExpression",
273
+ "JSXSpreadChild"
274
+ ],
275
+ offsetTernaryExpressions: true
276
+ }
277
+ ],
278
+ "@stylistic/key-spacing": ["error", { beforeColon: false, afterColon: true }],
279
+ "@stylistic/keyword-spacing": ["error", { before: true, after: true }],
280
+ "@stylistic/lines-between-class-members": ["error", "always", { exceptAfterSingleLine: true }],
281
+ "@stylistic/multiline-ternary": ["error", "always-multiline"],
282
+ "@stylistic/new-parens": "error",
283
+ "@stylistic/no-extra-parens": ["error", "functions"],
284
+ "@stylistic/no-floating-decimal": "error",
285
+ "@stylistic/no-mixed-operators": [
286
+ "error",
287
+ {
288
+ groups: [
289
+ ["==", "!=", "===", "!==", ">", ">=", "<", "<="],
290
+ ["&&", "||"],
291
+ ["in", "instanceof"]
292
+ ],
293
+ allowSamePrecedence: true
294
+ }
295
+ ],
296
+ "@stylistic/no-mixed-spaces-and-tabs": "error",
297
+ "@stylistic/no-multi-spaces": "error",
298
+ "@stylistic/no-multiple-empty-lines": ["error", { max: 1, maxBOF: 0, maxEOF: 0 }],
299
+ "@stylistic/no-tabs": "error",
300
+ "@stylistic/no-trailing-spaces": "error",
301
+ "@stylistic/no-whitespace-before-property": "error",
302
+ "@stylistic/object-curly-newline": ["error", { multiline: true, consistent: true }],
303
+ "@stylistic/object-curly-spacing": ["error", "always"],
304
+ "@stylistic/object-property-newline": ["error", { allowMultiplePropertiesPerLine: true }],
305
+ "@stylistic/operator-linebreak": ["error", "after", { overrides: { "?": "before", ":": "before", "|>": "before" } }],
306
+ "@stylistic/padded-blocks": ["error", { blocks: "never", switches: "never", classes: "never" }],
307
+ "@stylistic/quote-props": ["error", "as-needed"],
308
+ "@stylistic/quotes": ["error", "single", { avoidEscape: true, allowTemplateLiterals: false }],
309
+ "@stylistic/rest-spread-spacing": ["error", "never"],
310
+ "@stylistic/semi": ["error", "never"],
311
+ "@stylistic/semi-spacing": ["error", { before: false, after: true }],
312
+ "@stylistic/space-before-blocks": ["error", "always"],
313
+ "@stylistic/space-before-function-paren": ["error", "always"],
314
+ "@stylistic/space-in-parens": ["error", "never"],
315
+ "@stylistic/space-infix-ops": "error",
316
+ "@stylistic/space-unary-ops": ["error", { words: true, nonwords: false }],
317
+ "@stylistic/spaced-comment": [
318
+ "error",
319
+ "always",
320
+ {
321
+ line: { markers: ["*package", "!", "/", ",", "="] },
322
+ block: { balanced: true, markers: ["*package", "!", ",", ":", "::", "flow-include"], exceptions: ["*"] }
323
+ }
324
+ ],
325
+ "@stylistic/template-curly-spacing": ["error", "never"],
326
+ "@stylistic/template-tag-spacing": ["error", "never"],
327
+ "@stylistic/wrap-iife": ["error", "any", { functionPrototypeMethods: true }],
328
+ "@stylistic/yield-star-spacing": ["error", "both"]
329
+ }
330
+ };
331
+ const jsxIgnores = ["**/*.js", "**/*.mjs", "**/*.cjs", "**/*.ts"];
332
+ const jsx = {
333
+ name: "neostandard/jsx",
334
+ ignores: [...jsxIgnores],
335
+ languageOptions: {
336
+ parserOptions: {
337
+ ecmaFeatures: {
338
+ jsx: true
339
+ }
340
+ }
341
+ }
342
+ /*
343
+ * React support is temporarily disabled.
344
+ * plugins: {
345
+ * react: plugins.react,
346
+ * },
347
+ * settings: {
348
+ * react: {
349
+ * version: '17',
350
+ * },
351
+ * linkComponents: ['Link'],
352
+ * },
353
+ * rules: {
354
+ * 'react/jsx-boolean-value': 'error',
355
+ * 'react/jsx-fragments': ['error', 'syntax'],
356
+ * 'react/jsx-handler-names': 'error',
357
+ * 'react/jsx-key': [
358
+ * 'error',
359
+ * {
360
+ * checkFragmentShorthand: true,
361
+ * },
362
+ * ],
363
+ * 'react/jsx-no-comment-textnodes': 'error',
364
+ * 'react/jsx-no-duplicate-props': 'error',
365
+ * 'react/jsx-no-target-blank': ['error', { enforceDynamicLinks: 'always' }],
366
+ * 'react/jsx-no-undef': ['error', { allowGlobals: true }],
367
+ * 'react/jsx-uses-react': 'error',
368
+ * 'react/jsx-uses-vars': 'error',
369
+ * 'react/no-children-prop': 'error',
370
+ * 'react/no-danger-with-children': 'error',
371
+ * 'react/no-deprecated': 'error',
372
+ * 'react/no-direct-mutation-state': 'error',
373
+ * 'react/no-find-dom-node': 'error',
374
+ * 'react/no-is-mounted': 'error',
375
+ * 'react/no-string-refs': [
376
+ * 'error',
377
+ * {
378
+ * noTemplateLiterals: true,
379
+ * },
380
+ * ],
381
+ * 'react/no-unescaped-entities': [
382
+ * 'error',
383
+ * {
384
+ * forbid: ['>', '}'],
385
+ * },
386
+ * ],
387
+ * 'react/no-render-return-value': 'error',
388
+ * 'react/require-render-return': 'error',
389
+ * 'react/self-closing-comp': 'error',
390
+ * },
391
+ */
392
+ };
393
+ const jsxStyles = {
394
+ name: "neostandard/style/jsx",
395
+ ignores: [...jsxIgnores],
396
+ rules: {
397
+ "@stylistic/jsx-quotes": ["error", "prefer-single"],
398
+ "@stylistic/jsx-closing-bracket-location": ["error", "tag-aligned"],
399
+ "@stylistic/jsx-closing-tag-location": "error",
400
+ "@stylistic/jsx-curly-brace-presence": [
401
+ "error",
402
+ {
403
+ props: "never",
404
+ children: "never"
405
+ }
406
+ ],
407
+ "@stylistic/jsx-curly-newline": [
408
+ "error",
409
+ {
410
+ multiline: "consistent",
411
+ singleline: "consistent"
412
+ }
413
+ ],
414
+ "@stylistic/jsx-curly-spacing": [
415
+ "error",
416
+ {
417
+ attributes: { when: "never", allowMultiline: true },
418
+ children: { when: "never", allowMultiline: true }
419
+ }
420
+ ],
421
+ "@stylistic/jsx-equals-spacing": ["error", "never"],
422
+ "@stylistic/jsx-first-prop-new-line": ["error", "multiline-multiprop"],
423
+ "@stylistic/jsx-indent": [
424
+ "error",
425
+ 2,
426
+ {
427
+ checkAttributes: false,
428
+ indentLogicalExpressions: true
429
+ }
430
+ ],
431
+ "@stylistic/jsx-indent-props": ["error", 2],
432
+ "@stylistic/jsx-pascal-case": ["error", { allowAllCaps: false }],
433
+ "@stylistic/jsx-props-no-multi-spaces": "error",
434
+ "@stylistic/jsx-tag-spacing": [
435
+ "error",
436
+ {
437
+ closingSlash: "never",
438
+ beforeSelfClosing: "always",
439
+ afterOpening: "never",
440
+ beforeClosing: "never"
441
+ }
442
+ ],
443
+ "@stylistic/jsx-wrap-multilines": [
444
+ "error",
445
+ {
446
+ declaration: "parens-new-line",
447
+ assignment: "parens-new-line",
448
+ return: "parens-new-line",
449
+ arrow: "ignore",
450
+ condition: "ignore",
451
+ logical: "ignore",
452
+ prop: "ignore"
453
+ }
454
+ ]
455
+ }
456
+ };
457
+ const semiConfig = {
458
+ name: "neostandard/semi",
459
+ rules: {
460
+ "@stylistic/semi": ["error", "always"],
461
+ "@stylistic/no-extra-semi": "error"
462
+ }
463
+ };
464
+ const jsImportRules = {
465
+ name: "neostandard/import-x",
466
+ files: ["**/*.js", "**/*.mjs", "**/*.cjs", "**/*.jsx"],
467
+ plugins: {
468
+ "import-x": plugins["import-x"]
469
+ },
470
+ rules: {
471
+ "import-x/export": "error",
472
+ "import-x/first": "error",
473
+ "import-x/no-absolute-path": ["error", { esmodule: true, commonjs: true, amd: false }],
474
+ "import-x/no-duplicates": "error",
475
+ "import-x/no-named-default": "error",
476
+ "import-x/no-webpack-loader-syntax": "error",
477
+ // Custom rules
478
+ "import-x/no-mutable-exports": "error",
479
+ "import-x/newline-after-import": ["error", { count: 1 }],
480
+ "import-x/no-self-import": "error"
481
+ }
482
+ };
483
+ const isNonEmpty = (value) => Object.keys(value).length > 0;
484
+ const resolveIgnoresFromGitignore = () => {
485
+ const configFile = findFlatConfigFileSync();
486
+ if (!configFile) {
487
+ return [];
488
+ }
489
+ const result = [];
490
+ try {
491
+ const content = readFileSync(join(dirname(configFile), ".gitignore"), "utf8");
492
+ for (let line of content.split("\n")) {
493
+ line = line.trim();
494
+ if (line && !line.startsWith("#")) {
495
+ result.push(gitignoreToMinimatch(line));
496
+ }
497
+ }
498
+ } catch {
499
+ }
500
+ return result;
501
+ };
502
+ function findFlatConfigFileSync() {
503
+ return findUpSync([
504
+ "eslint.config.js",
505
+ "eslint.config.mjs",
506
+ "eslint.config.cjs",
507
+ "eslint.config.ts",
508
+ "eslint.config.mts",
509
+ "eslint.config.cts"
510
+ ]);
511
+ }
512
+ function typescriptify(configs, options) {
513
+ const { files, ignores, name, project, tsconfigRootDir, typeChecking = false } = options;
514
+ const deactivatedRules = {};
515
+ const replacementRules = {};
516
+ const tsPlugin = tseslint.plugin;
517
+ for (const config of configs) {
518
+ for (const ruleId of Object.keys(tsRedundant)) {
519
+ if (config.rules?.[ruleId]) {
520
+ deactivatedRules[ruleId] = "off";
521
+ }
522
+ }
523
+ for (const [ruleId, ruleDefinition] of Object.entries(tsPlugin.rules)) {
524
+ const currentRule = config.rules?.[ruleId];
525
+ if (currentRule === void 0) {
526
+ continue;
527
+ }
528
+ if (!ruleDefinition.meta?.docs || typeof ruleDefinition.meta.docs !== "object") {
529
+ continue;
530
+ }
531
+ const docs = ruleDefinition.meta.docs;
532
+ if (!docs.extendsBaseRule) {
533
+ continue;
534
+ }
535
+ if (docs.requiresTypeChecking && !typeChecking) {
536
+ continue;
537
+ }
538
+ deactivatedRules[ruleId] = "off";
539
+ if (ruleId !== "dot-notation") {
540
+ replacementRules[`@typescript-eslint/${ruleId}`] = currentRule;
541
+ }
542
+ }
543
+ }
544
+ return {
545
+ ...name ? { name } : {},
546
+ ...files ? { files } : {},
547
+ ...ignores ? { ignores } : {},
548
+ languageOptions: {
549
+ parser: tseslint.parser,
550
+ parserOptions: {
551
+ project: project === void 0 ? typeChecking : project,
552
+ ...tsconfigRootDir ? { tsconfigRootDir } : {}
553
+ }
554
+ },
555
+ plugins: {
556
+ "@typescript-eslint": tseslint.plugin
557
+ },
558
+ rules: {
559
+ ...deactivatedRules,
560
+ ...replacementRules
561
+ }
562
+ };
563
+ }
564
+ const tsRedundant = {
565
+ "getter-return": "off",
566
+ "constructor-super": "off",
567
+ "no-const-assign": "off",
568
+ "no-dupe-args": "off",
569
+ "no-dupe-class-members": "off",
570
+ "no-dupe-keys": "off",
571
+ "no-func-assign": "off",
572
+ "no-import-assign": "off",
573
+ "no-new-native-nonconstructor": "off",
574
+ "no-obj-calls": "off",
575
+ "no-redeclare": "off",
576
+ "no-setter-return": "off",
577
+ "no-this-before-super": "off",
578
+ "no-undef": "off",
579
+ "no-unreachable": "off",
580
+ "no-unsafe-negation": "off"
581
+ };
582
+ const getJsConfigs = (opts) => {
583
+ const jsxConfigs = opts.noJsx ? [] : [jsx, ...opts.noStyle ? [] : [jsxStyles]];
584
+ const styleConfigs = opts.noStyle ? [] : [style, modernizationStyles, ...opts.semi ? [semiConfig] : []];
585
+ return [...promiseConfigs, base, modernization, ...jsxConfigs, ...styleConfigs, jsImportRules];
586
+ };
587
+ const neostandard = (options) => {
588
+ const {
589
+ env,
590
+ files: rawFiles,
591
+ filesTs,
592
+ globals: rawGlobals,
593
+ ignores,
594
+ noJsx = false,
595
+ noStyle = false,
596
+ ts = false,
597
+ semi = false
598
+ } = options || {};
599
+ if (filesTs && !ts) {
600
+ throw new Error('"filesTs" is only usable with the "ts" option');
601
+ }
602
+ const resolvedGlobals = Array.isArray(rawGlobals) ? Object.fromEntries(rawGlobals.map((global) => [global, true])) : { ...rawGlobals };
603
+ for (const key of env || []) {
604
+ if (!globals[key]) {
605
+ throw new Error(`Invalid env definition: ${env}`);
606
+ }
607
+ const envGlobals = globals[key];
608
+ for (const [name, value] of Object.entries(envGlobals)) {
609
+ resolvedGlobals[name] = resolvedGlobals[name] || value;
610
+ }
611
+ }
612
+ const files = [...rawFiles || [], ...noJsx ? [] : ["**/*.jsx"]];
613
+ const jsConfigs = getJsConfigs({ noJsx, noStyle, semi });
614
+ return [
615
+ ...ignores ? [{ ignores }] : [],
616
+ ...files.length ? [
617
+ {
618
+ name: "neostandard/additional-files",
619
+ files
620
+ }
621
+ ] : [],
622
+ ...isNonEmpty(resolvedGlobals) ? [
623
+ {
624
+ name: "neostandard/globals",
625
+ languageOptions: { globals: resolvedGlobals }
626
+ }
627
+ ] : [],
628
+ ...jsConfigs,
629
+ ...ts ? [
630
+ typescriptify(jsConfigs, {
631
+ files: ["**/*.ts", ...noJsx ? [] : ["**/*.tsx"], ...filesTs || []],
632
+ ignores,
633
+ name: "neostandard/ts"
634
+ })
635
+ ] : []
636
+ ];
637
+ };
638
+
10
639
  const rule = {
11
640
  meta: {
12
641
  type: "suggestion",
@@ -243,15 +872,7 @@ const config = (options) => {
243
872
  "no-console": process.env.NODE_ENV === "production" ? "warn" : "off",
244
873
  "no-debugger": process.env.NODE_ENV === "production" ? "warn" : "off",
245
874
  // Enforce dot notation
246
- "dot-notation": ["error"],
247
- // Import rules
248
- ...opts.ts ? {
249
- "import-x/named": "off",
250
- "no-unused-vars": "off"
251
- } : {},
252
- "import-x/no-mutable-exports": "error",
253
- "import-x/newline-after-import": ["error", { count: 1 }],
254
- "import-x/no-self-import": "error"
875
+ "dot-notation": ["error"]
255
876
  }
256
877
  },
257
878
  // Sort imports
@@ -292,4 +913,4 @@ const config = (options) => {
292
913
  return linterConfig;
293
914
  };
294
915
 
295
- export { config };
916
+ export { config, plugins };