@coderwyd/eslint-config 2.7.0 → 2.7.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -52,14 +52,25 @@ module.exports = __toCommonJS(src_exports);
52
52
  var getImportMetaUrl = () => typeof document === "undefined" ? new URL(`file:${__filename}`).href : document.currentScript && document.currentScript.src || new URL("main.js", document.baseURI).href;
53
53
  var importMetaUrl = /* @__PURE__ */ getImportMetaUrl();
54
54
 
55
+ // src/configs/command.ts
56
+ var import_config = __toESM(require("eslint-plugin-command/config"), 1);
57
+ function command() {
58
+ return [
59
+ {
60
+ ...(0, import_config.default)(),
61
+ name: "coderwyd/command/rules"
62
+ }
63
+ ];
64
+ }
65
+
55
66
  // src/plugins/index.ts
56
- var import_eslint_plugin_antfu = __toESM(require("eslint-plugin-antfu"), 1);
57
67
  var import_eslint_plugin_eslint_comments = __toESM(require("@eslint-community/eslint-plugin-eslint-comments"), 1);
68
+ var import_eslint_plugin_antfu = __toESM(require("eslint-plugin-antfu"), 1);
58
69
  var pluginImport = __toESM(require("eslint-plugin-import-x"), 1);
59
70
  var import_eslint_plugin_n = __toESM(require("eslint-plugin-n"), 1);
71
+ var import_eslint_plugin_perfectionist = __toESM(require("eslint-plugin-perfectionist"), 1);
60
72
  var import_eslint_plugin_unicorn = __toESM(require("eslint-plugin-unicorn"), 1);
61
73
  var import_eslint_plugin_unused_imports = __toESM(require("eslint-plugin-unused-imports"), 1);
62
- var import_eslint_plugin_perfectionist = __toESM(require("eslint-plugin-perfectionist"), 1);
63
74
 
64
75
  // src/configs/comments.ts
65
76
  function comments() {
@@ -143,99 +154,406 @@ var GLOB_EXCLUDE = [
143
154
  "**/components.d.ts"
144
155
  ];
145
156
 
146
- // src/configs/ignores.ts
147
- function ignores(userIgnores = []) {
157
+ // src/configs/disables.ts
158
+ function disables() {
148
159
  return [
149
160
  {
150
- ignores: [
151
- ...GLOB_EXCLUDE,
152
- ...userIgnores
153
- ],
154
- name: "coderwyd/ignores"
155
- }
156
- ];
157
- }
158
-
159
- // src/configs/imports.ts
160
- function imports(options = {}) {
161
- const { stylistic: stylistic2 = true } = options;
162
- return [
161
+ files: [`scripts/${GLOB_SRC}`],
162
+ name: "coderwyd/disables/scripts",
163
+ rules: {
164
+ "no-console": "off",
165
+ "ts/explicit-function-return-type": "off",
166
+ "unicorn/consistent-function-scoping": "off"
167
+ }
168
+ },
163
169
  {
164
- name: "coderwyd/imports/rules",
165
- plugins: {
166
- antfu: import_eslint_plugin_antfu.default,
167
- import: pluginImport
168
- },
170
+ files: [`cli/${GLOB_SRC}`, `cli.${GLOB_SRC_EXT}`],
171
+ name: "coderwyd/disables/cli",
169
172
  rules: {
170
- "antfu/import-dedupe": "error",
171
- "antfu/no-import-dist": "error",
172
- "antfu/no-import-node-modules-by-path": "error",
173
- "import/first": "error",
174
- "import/no-duplicates": "error",
175
- "import/no-mutable-exports": "error",
176
- "import/no-named-default": "error",
177
- "import/no-self-import": "error",
178
- "import/no-webpack-loader-syntax": "error",
179
- ...stylistic2 ? {
180
- "import/newline-after-import": ["error", { count: 1 }]
181
- } : {}
173
+ "no-console": "off"
182
174
  }
183
175
  },
184
176
  {
185
177
  files: ["**/bin/**/*", `**/bin.${GLOB_SRC_EXT}`],
186
- name: "coderwyd/imports/disables/bin",
178
+ name: "coderwyd/disables/bin",
187
179
  rules: {
188
180
  "antfu/no-import-dist": "off",
189
181
  "antfu/no-import-node-modules-by-path": "off"
190
182
  }
183
+ },
184
+ {
185
+ files: [GLOB_DTS],
186
+ name: "coderwyd/disables/dts",
187
+ rules: {
188
+ "eslint-comments/no-unlimited-disable": "off",
189
+ "import/no-duplicates": "off",
190
+ "no-restricted-syntax": "off",
191
+ "unused-imports/no-unused-vars": "off"
192
+ }
193
+ },
194
+ {
195
+ files: ["**/*.{test,spec}.([tj])s?(x)"],
196
+ name: "coderwyd/disables/test",
197
+ rules: {
198
+ "no-unused-expressions": "off"
199
+ }
200
+ },
201
+ {
202
+ files: ["**/*.js", "**/*.cjs"],
203
+ name: "coderwyd/disables/cjs",
204
+ rules: {
205
+ "ts/no-require-imports": "off"
206
+ }
191
207
  }
192
208
  ];
193
209
  }
194
210
 
195
- // src/configs/javascript.ts
196
- var import_globals = __toESM(require("globals"), 1);
197
- function javascript(options = {}) {
198
- const { isInEditor: isInEditor2 = false, overrides = {} } = options;
199
- return [
200
- {
201
- languageOptions: {
202
- ecmaVersion: 2022,
203
- globals: {
204
- ...import_globals.default.browser,
205
- ...import_globals.default.es2021,
206
- ...import_globals.default.node,
207
- document: "readonly",
208
- navigator: "readonly",
209
- window: "readonly"
210
- },
211
- parserOptions: {
212
- ecmaFeatures: {
213
- jsx: true
214
- },
215
- ecmaVersion: 2022,
216
- sourceType: "module"
217
- },
218
- sourceType: "module"
219
- },
220
- linterOptions: {
221
- reportUnusedDisableDirectives: true
222
- },
223
- name: "coderwyd/javascript/setup"
211
+ // src/shared/index.ts
212
+ var import_node_process = __toESM(require("process"), 1);
213
+ var import_node_url = require("url");
214
+ var import_local_pkg = require("local-pkg");
215
+ var scopeUrl = (0, import_node_url.fileURLToPath)(new URL(".", importMetaUrl));
216
+ var isCwdInScope = (0, import_local_pkg.isPackageExists)("@coderwyd/eslint-config");
217
+ var parserPlain = {
218
+ meta: {
219
+ name: "parser-plain"
220
+ },
221
+ parseForESLint: (code) => ({
222
+ ast: {
223
+ body: [],
224
+ comments: [],
225
+ loc: { end: code.length, start: 0 },
226
+ range: [0, code.length],
227
+ tokens: [],
228
+ type: "Program"
224
229
  },
230
+ scopeManager: null,
231
+ services: { isPlain: true },
232
+ visitorKeys: {
233
+ Program: []
234
+ }
235
+ })
236
+ };
237
+ async function combine(...configs2) {
238
+ const resolved = await Promise.all(configs2);
239
+ return resolved.flat();
240
+ }
241
+ function renameRules(rules, map) {
242
+ return Object.fromEntries(
243
+ Object.entries(rules).map(([key, value]) => {
244
+ for (const [from, to] of Object.entries(map)) {
245
+ if (key.startsWith(`${from}/`))
246
+ return [to + key.slice(from.length), value];
247
+ }
248
+ return [key, value];
249
+ })
250
+ );
251
+ }
252
+ function renamePluginInConfigs(configs2, map) {
253
+ return configs2.map((i) => {
254
+ const clone = { ...i };
255
+ if (clone.rules)
256
+ clone.rules = renameRules(clone.rules, map);
257
+ if (clone.plugins) {
258
+ clone.plugins = Object.fromEntries(
259
+ Object.entries(clone.plugins).map(([key, value]) => {
260
+ if (key in map)
261
+ return [map[key], value];
262
+ return [key, value];
263
+ })
264
+ );
265
+ }
266
+ return clone;
267
+ });
268
+ }
269
+ function getVueVersion() {
270
+ const pkg = (0, import_local_pkg.getPackageInfoSync)("vue", { paths: [import_node_process.default.cwd()] });
271
+ if (pkg && typeof pkg.version === "string" && !Number.isNaN(+pkg.version[0]))
272
+ return +pkg.version[0];
273
+ return 3;
274
+ }
275
+ function toArray(value) {
276
+ return Array.isArray(value) ? value : [value];
277
+ }
278
+ async function interopDefault(m) {
279
+ const resolved = await m;
280
+ return resolved.default || resolved;
281
+ }
282
+ function isPackageInScope(name) {
283
+ return (0, import_local_pkg.isPackageExists)(name, { paths: [scopeUrl] });
284
+ }
285
+ async function ensurePackages(packages) {
286
+ if (import_node_process.default.env.CI || import_node_process.default.stdout.isTTY === false || isCwdInScope === false)
287
+ return;
288
+ const nonExistingPackages = packages.filter((i) => !isPackageInScope(i));
289
+ if (nonExistingPackages.length === 0)
290
+ return;
291
+ const { default: prompts } = await import("prompts");
292
+ const { result } = await prompts([
225
293
  {
226
- name: "coderwyd/javascript/rules",
294
+ message: `${nonExistingPackages.length === 1 ? "Package is" : "Packages are"} required for this config: ${nonExistingPackages.join(", ")}. Do you want to install them?`,
295
+ name: "result",
296
+ type: "confirm"
297
+ }
298
+ ]);
299
+ if (result) {
300
+ await import("@antfu/install-pkg").then(
301
+ (i) => i.installPackage(nonExistingPackages, { dev: true })
302
+ );
303
+ }
304
+ }
305
+ function resolveSubOptions(options, key) {
306
+ return typeof options[key] === "boolean" ? {} : options[key] || {};
307
+ }
308
+ function getOverrides(options, key) {
309
+ const sub = resolveSubOptions(options, key);
310
+ return {
311
+ ..."overrides" in sub ? sub.overrides || {} : {}
312
+ };
313
+ }
314
+ function isInEditorEnv() {
315
+ if (import_node_process.default.env.CI)
316
+ return false;
317
+ if (isInGitHooksOrLintStaged())
318
+ return false;
319
+ return !!(import_node_process.default.env.VSCODE_PID || import_node_process.default.env.VSCODE_CWD || import_node_process.default.env.JETBRAINS_IDE || import_node_process.default.env.VIM || import_node_process.default.env.NVIM || false);
320
+ }
321
+ function isInGitHooksOrLintStaged() {
322
+ return !!(import_node_process.default.env.GIT_PARAMS || import_node_process.default.env.VSCODE_GIT_COMMAND || import_node_process.default.env.npm_lifecycle_script?.startsWith("lint-staged") || import_node_process.default.env.npm_lifecycle_script?.startsWith("nano-staged") || false);
323
+ }
324
+
325
+ // src/configs/stylistic.ts
326
+ var StylisticConfigDefaults = {
327
+ indent: 2,
328
+ jsx: true,
329
+ quotes: "single",
330
+ semi: false
331
+ };
332
+ async function stylistic(options = {}) {
333
+ const {
334
+ indent,
335
+ jsx: jsx2,
336
+ overrides = {},
337
+ quotes,
338
+ semi
339
+ } = {
340
+ ...StylisticConfigDefaults,
341
+ ...options
342
+ };
343
+ const pluginStylistic = await interopDefault(
344
+ import("@stylistic/eslint-plugin")
345
+ );
346
+ const config = pluginStylistic.configs.customize({
347
+ flat: true,
348
+ indent,
349
+ jsx: jsx2,
350
+ pluginName: "style",
351
+ quotes,
352
+ semi
353
+ });
354
+ return [
355
+ {
356
+ name: "coderwyd/stylistic/rules",
227
357
  plugins: {
228
- "unused-imports": import_eslint_plugin_unused_imports.default
358
+ antfu: import_eslint_plugin_antfu.default,
359
+ style: pluginStylistic
229
360
  },
230
361
  rules: {
231
- "accessor-pairs": [
232
- "error",
233
- { enforceForClassMembers: true, setWithoutGet: true }
234
- ],
235
- "array-callback-return": "error",
236
- "block-scoped-var": "error",
237
- "constructor-super": "error",
238
- "default-case-last": "error",
362
+ ...config.rules,
363
+ "antfu/consistent-chaining": "error",
364
+ "antfu/consistent-list-newline": "error",
365
+ "antfu/curly": "error",
366
+ "antfu/if-newline": "warn",
367
+ "antfu/top-level-function": "warn",
368
+ ...overrides
369
+ }
370
+ }
371
+ ];
372
+ }
373
+
374
+ // src/configs/formatter.ts
375
+ async function formatter(options = {}, stylistic2 = {}) {
376
+ const { css, graphql, html, markdown, toml, yaml } = options === true ? {
377
+ css: true,
378
+ graphql: true,
379
+ html: true,
380
+ markdown: true,
381
+ toml: true,
382
+ yaml: true
383
+ } : options;
384
+ const { indent, quotes, semi } = {
385
+ ...StylisticConfigDefaults,
386
+ ...stylistic2
387
+ };
388
+ const prettierOptions = Object.assign(
389
+ {
390
+ endOfLine: "auto",
391
+ printWidth: 80,
392
+ semi,
393
+ singleQuote: quotes === "single",
394
+ tabWidth: typeof indent === "number" ? indent : 2,
395
+ trailingComma: "all",
396
+ useTabs: indent === "tab"
397
+ },
398
+ typeof options === "boolean" ? {} : options.prettierOptions || {}
399
+ );
400
+ await ensurePackages(["eslint-plugin-format"]);
401
+ const pluginFormat = await interopDefault(import("eslint-plugin-format"));
402
+ function createPrettierFormatter(files, parser, plugins) {
403
+ const rules = {
404
+ ...prettierOptions,
405
+ parser
406
+ };
407
+ const markdownRules = {
408
+ printWidth: 120,
409
+ ...rules,
410
+ embeddedLanguageFormatting: "off"
411
+ };
412
+ if (plugins?.length)
413
+ rules.plugins = [...rules.plugins || [], ...plugins];
414
+ const config = {
415
+ files,
416
+ languageOptions: {
417
+ parser: parserPlain
418
+ },
419
+ name: `coderwyd/formatter/${parser}`,
420
+ plugins: {
421
+ format: pluginFormat
422
+ },
423
+ rules: {
424
+ "format/prettier": [
425
+ "warn",
426
+ parser === "markdown" ? markdownRules : rules
427
+ ]
428
+ }
429
+ };
430
+ return config;
431
+ }
432
+ const configs2 = [
433
+ {
434
+ name: "coderwyd/formatter/setup",
435
+ plugins: {
436
+ format: pluginFormat
437
+ }
438
+ }
439
+ ];
440
+ if (html) {
441
+ const htmlConfig = createPrettierFormatter([GLOB_HTML], "html");
442
+ configs2.push(htmlConfig);
443
+ }
444
+ if (css) {
445
+ const cssConfig = createPrettierFormatter([GLOB_CSS, GLOB_POSTCSS], "css");
446
+ const scssConfig = createPrettierFormatter([GLOB_SCSS], "scss");
447
+ const lessConfig = createPrettierFormatter([GLOB_LESS], "less");
448
+ configs2.push(cssConfig, scssConfig, lessConfig);
449
+ }
450
+ if (markdown) {
451
+ const markdownConfig = createPrettierFormatter([GLOB_MARKDOWN], "markdown");
452
+ configs2.push(markdownConfig);
453
+ }
454
+ if (graphql) {
455
+ const graphqlConfig = createPrettierFormatter([GLOB_GRAPHQL], "graphql");
456
+ configs2.push(graphqlConfig);
457
+ }
458
+ if (yaml) {
459
+ const yamlConfig = createPrettierFormatter([GLOB_YAML], "yaml");
460
+ configs2.push(yamlConfig);
461
+ }
462
+ if (toml) {
463
+ await ensurePackages(["@toml-tools/parser", "prettier-plugin-toml"]);
464
+ const tomlConfig = createPrettierFormatter([GLOB_TOML], "toml", [
465
+ "prettier-plugin-toml"
466
+ ]);
467
+ configs2.push(tomlConfig);
468
+ }
469
+ return configs2;
470
+ }
471
+
472
+ // src/configs/ignores.ts
473
+ function ignores(userIgnores = []) {
474
+ return [
475
+ {
476
+ ignores: [
477
+ ...GLOB_EXCLUDE,
478
+ ...userIgnores
479
+ ],
480
+ name: "coderwyd/ignores"
481
+ }
482
+ ];
483
+ }
484
+
485
+ // src/configs/imports.ts
486
+ function imports(options = {}) {
487
+ const { stylistic: stylistic2 = true } = options;
488
+ return [
489
+ {
490
+ name: "coderwyd/imports/rules",
491
+ plugins: {
492
+ antfu: import_eslint_plugin_antfu.default,
493
+ import: pluginImport
494
+ },
495
+ rules: {
496
+ "antfu/import-dedupe": "error",
497
+ "antfu/no-import-dist": "error",
498
+ "antfu/no-import-node-modules-by-path": "error",
499
+ "import/first": "error",
500
+ "import/no-duplicates": "error",
501
+ "import/no-mutable-exports": "error",
502
+ "import/no-named-default": "error",
503
+ "import/no-self-import": "error",
504
+ "import/no-webpack-loader-syntax": "error",
505
+ ...stylistic2 ? {
506
+ "import/newline-after-import": ["error", { count: 1 }]
507
+ } : {}
508
+ }
509
+ }
510
+ ];
511
+ }
512
+
513
+ // src/configs/javascript.ts
514
+ var import_globals = __toESM(require("globals"), 1);
515
+ function javascript(options = {}) {
516
+ const { isInEditor: isInEditor2 = false, overrides = {} } = options;
517
+ return [
518
+ {
519
+ languageOptions: {
520
+ ecmaVersion: 2022,
521
+ globals: {
522
+ ...import_globals.default.browser,
523
+ ...import_globals.default.es2021,
524
+ ...import_globals.default.node,
525
+ document: "readonly",
526
+ navigator: "readonly",
527
+ window: "readonly"
528
+ },
529
+ parserOptions: {
530
+ ecmaFeatures: {
531
+ jsx: true
532
+ },
533
+ ecmaVersion: 2022,
534
+ sourceType: "module"
535
+ },
536
+ sourceType: "module"
537
+ },
538
+ linterOptions: {
539
+ reportUnusedDisableDirectives: true
540
+ },
541
+ name: "coderwyd/javascript/setup"
542
+ },
543
+ {
544
+ name: "coderwyd/javascript/rules",
545
+ plugins: {
546
+ "unused-imports": import_eslint_plugin_unused_imports.default
547
+ },
548
+ rules: {
549
+ "accessor-pairs": [
550
+ "error",
551
+ { enforceForClassMembers: true, setWithoutGet: true }
552
+ ],
553
+ "array-callback-return": "error",
554
+ "block-scoped-var": "error",
555
+ "constructor-super": "error",
556
+ "default-case-last": "error",
239
557
  "dot-notation": ["error", { allowKeywords: true }],
240
558
  "eqeqeq": ["error", "smart"],
241
559
  "for-direction": "error",
@@ -421,167 +739,39 @@ function javascript(options = {}) {
421
739
  "yoda": ["error", "never"],
422
740
  ...overrides
423
741
  }
424
- },
425
- {
426
- files: [`scripts/${GLOB_SRC}`, `cli.${GLOB_SRC_EXT}`],
427
- name: "coderwyd/javascript/disables/cli",
428
- rules: {
429
- "no-console": "off"
430
- }
431
- },
742
+ }
743
+ ];
744
+ }
745
+
746
+ // src/configs/jsdoc.ts
747
+ async function jsdoc(options = {}) {
748
+ const { stylistic: stylistic2 = true } = options;
749
+ return [
432
750
  {
433
- files: ["**/*.{test,spec}.js?(x)"],
434
- name: "coderwyd/javascript/disables/test",
751
+ name: "coderwyd/jsdoc/rules",
752
+ plugins: {
753
+ jsdoc: await interopDefault(import("eslint-plugin-jsdoc"))
754
+ },
435
755
  rules: {
436
- "no-unused-expressions": "off"
437
- }
438
- }
439
- ];
440
- }
441
-
442
- // src/shared/index.ts
443
- var import_node_process = __toESM(require("process"), 1);
444
- var import_node_url = require("url");
445
- var import_local_pkg = require("local-pkg");
446
- var scopeUrl = (0, import_node_url.fileURLToPath)(new URL(".", importMetaUrl));
447
- var isCwdInScope = (0, import_local_pkg.isPackageExists)("@coderwyd/eslint-config");
448
- var parserPlain = {
449
- meta: {
450
- name: "parser-plain"
451
- },
452
- parseForESLint: (code) => ({
453
- ast: {
454
- body: [],
455
- comments: [],
456
- loc: { end: code.length, start: 0 },
457
- range: [0, code.length],
458
- tokens: [],
459
- type: "Program"
460
- },
461
- scopeManager: null,
462
- services: { isPlain: true },
463
- visitorKeys: {
464
- Program: []
465
- }
466
- })
467
- };
468
- async function combine(...configs2) {
469
- const resolved = await Promise.all(configs2);
470
- return resolved.flat();
471
- }
472
- function renameRules(rules, map) {
473
- return Object.fromEntries(
474
- Object.entries(rules).map(([key, value]) => {
475
- for (const [from, to] of Object.entries(map)) {
476
- if (key.startsWith(`${from}/`))
477
- return [to + key.slice(from.length), value];
478
- }
479
- return [key, value];
480
- })
481
- );
482
- }
483
- function renamePluginInConfigs(configs2, map) {
484
- return configs2.map((i) => {
485
- const clone = { ...i };
486
- if (clone.rules)
487
- clone.rules = renameRules(clone.rules, map);
488
- if (clone.plugins) {
489
- clone.plugins = Object.fromEntries(
490
- Object.entries(clone.plugins).map(([key, value]) => {
491
- if (key in map)
492
- return [map[key], value];
493
- return [key, value];
494
- })
495
- );
496
- }
497
- return clone;
498
- });
499
- }
500
- function getVueVersion() {
501
- const pkg = (0, import_local_pkg.getPackageInfoSync)("vue", { paths: [import_node_process.default.cwd()] });
502
- if (pkg && typeof pkg.version === "string" && !Number.isNaN(+pkg.version[0]))
503
- return +pkg.version[0];
504
- return 3;
505
- }
506
- function toArray(value) {
507
- return Array.isArray(value) ? value : [value];
508
- }
509
- async function interopDefault(m) {
510
- const resolved = await m;
511
- return resolved.default || resolved;
512
- }
513
- function isPackageInScope(name) {
514
- return (0, import_local_pkg.isPackageExists)(name, { paths: [scopeUrl] });
515
- }
516
- async function ensurePackages(packages) {
517
- if (import_node_process.default.env.CI || import_node_process.default.stdout.isTTY === false || isCwdInScope === false)
518
- return;
519
- const nonExistingPackages = packages.filter((i) => !isPackageInScope(i));
520
- if (nonExistingPackages.length === 0)
521
- return;
522
- const { default: prompts } = await import("prompts");
523
- const { result } = await prompts([
524
- {
525
- message: `${nonExistingPackages.length === 1 ? "Package is" : "Packages are"} required for this config: ${nonExistingPackages.join(", ")}. Do you want to install them?`,
526
- name: "result",
527
- type: "confirm"
528
- }
529
- ]);
530
- if (result) {
531
- await import("@antfu/install-pkg").then(
532
- (i) => i.installPackage(nonExistingPackages, { dev: true })
533
- );
534
- }
535
- }
536
- function resolveSubOptions(options, key) {
537
- return typeof options[key] === "boolean" ? {} : options[key] || {};
538
- }
539
- function getOverrides(options, key) {
540
- const sub = resolveSubOptions(options, key);
541
- return {
542
- ..."overrides" in sub ? sub.overrides || {} : {}
543
- };
544
- }
545
- function isInEditorEnv() {
546
- if (import_node_process.default.env.CI)
547
- return false;
548
- if (isInGitHooksOrLintStaged())
549
- return false;
550
- return !!(import_node_process.default.env.VSCODE_PID || import_node_process.default.env.VSCODE_CWD || import_node_process.default.env.JETBRAINS_IDE || import_node_process.default.env.VIM || import_node_process.default.env.NVIM || false);
551
- }
552
- function isInGitHooksOrLintStaged() {
553
- return !!(import_node_process.default.env.GIT_PARAMS || import_node_process.default.env.VSCODE_GIT_COMMAND || import_node_process.default.env.npm_lifecycle_script?.startsWith("lint-staged") || import_node_process.default.env.npm_lifecycle_script?.startsWith("nano-staged") || false);
554
- }
555
-
556
- // src/configs/jsdoc.ts
557
- async function jsdoc(options = {}) {
558
- const { stylistic: stylistic2 = true } = options;
559
- return [
560
- {
561
- name: "coderwyd/jsdoc/rules",
562
- plugins: {
563
- jsdoc: await interopDefault(import("eslint-plugin-jsdoc"))
564
- },
565
- rules: {
566
- "jsdoc/check-access": "warn",
567
- "jsdoc/check-param-names": "warn",
568
- "jsdoc/check-property-names": "warn",
569
- "jsdoc/check-types": "warn",
570
- "jsdoc/empty-tags": "warn",
571
- "jsdoc/implements-on-classes": "warn",
572
- "jsdoc/no-defaults": "warn",
573
- "jsdoc/no-multi-asterisks": "warn",
574
- "jsdoc/require-param-name": "warn",
575
- "jsdoc/require-property": "warn",
576
- "jsdoc/require-property-description": "warn",
577
- "jsdoc/require-property-name": "warn",
578
- "jsdoc/require-returns-check": "warn",
579
- "jsdoc/require-returns-description": "warn",
580
- "jsdoc/require-yields-check": "warn",
581
- ...stylistic2 ? {
582
- "jsdoc/check-alignment": "warn",
583
- "jsdoc/multiline-blocks": "warn"
584
- } : {}
756
+ "jsdoc/check-access": "warn",
757
+ "jsdoc/check-param-names": "warn",
758
+ "jsdoc/check-property-names": "warn",
759
+ "jsdoc/check-types": "warn",
760
+ "jsdoc/empty-tags": "warn",
761
+ "jsdoc/implements-on-classes": "warn",
762
+ "jsdoc/no-defaults": "warn",
763
+ "jsdoc/no-multi-asterisks": "warn",
764
+ "jsdoc/require-param-name": "warn",
765
+ "jsdoc/require-property": "warn",
766
+ "jsdoc/require-property-description": "warn",
767
+ "jsdoc/require-property-name": "warn",
768
+ "jsdoc/require-returns-check": "warn",
769
+ "jsdoc/require-returns-description": "warn",
770
+ "jsdoc/require-yields-check": "warn",
771
+ ...stylistic2 ? {
772
+ "jsdoc/check-alignment": "warn",
773
+ "jsdoc/multiline-blocks": "warn"
774
+ } : {}
585
775
  }
586
776
  }
587
777
  ];
@@ -668,6 +858,23 @@ async function jsonc(options = {}) {
668
858
  ];
669
859
  }
670
860
 
861
+ // src/configs/jsx.ts
862
+ function jsx() {
863
+ return [
864
+ {
865
+ files: [GLOB_JSX, GLOB_TSX],
866
+ languageOptions: {
867
+ parserOptions: {
868
+ ecmaFeatures: {
869
+ jsx: true
870
+ }
871
+ }
872
+ },
873
+ name: "coderwyd/jsx/setup"
874
+ }
875
+ ];
876
+ }
877
+
671
878
  // src/configs/node.ts
672
879
  function node() {
673
880
  return [
@@ -691,1303 +898,1103 @@ function node() {
691
898
  ];
692
899
  }
693
900
 
694
- // src/configs/sort.ts
695
- function sortPackageJson() {
901
+ // src/configs/perfectionist.ts
902
+ function perfectionist() {
696
903
  return [
697
904
  {
698
- files: ["**/package.json"],
699
- name: "coderwyd/sort/package-json",
905
+ name: "coderwyd/perfectionist/rules",
906
+ plugins: {
907
+ perfectionist: import_eslint_plugin_perfectionist.default
908
+ },
700
909
  rules: {
701
- "jsonc/sort-array-values": [
702
- "error",
703
- {
704
- order: { type: "asc" },
705
- pathPattern: "^files$"
706
- }
707
- ],
708
- "jsonc/sort-keys": [
709
- "error",
910
+ "perfectionist/sort-exports": ["error", { order: "asc", type: "natural" }],
911
+ "perfectionist/sort-imports": [
912
+ "warn",
710
913
  {
711
- order: [
712
- "publisher",
713
- "name",
714
- "displayName",
914
+ groups: [
915
+ "builtin",
916
+ "external",
715
917
  "type",
716
- "version",
717
- "private",
718
- "packageManager",
719
- "description",
720
- "author",
721
- "license",
722
- "funding",
723
- "homepage",
724
- "repository",
725
- "bugs",
726
- "keywords",
727
- "categories",
728
- "sideEffects",
729
- "exports",
730
- "main",
731
- "module",
732
- "unpkg",
733
- "jsdelivr",
734
- "types",
735
- "typesVersions",
736
- "bin",
737
- "icon",
738
- "files",
739
- "engines",
740
- "activationEvents",
741
- "contributes",
742
- "scripts",
743
- "peerDependencies",
744
- "peerDependenciesMeta",
745
- "dependencies",
746
- "optionalDependencies",
747
- "devDependencies",
748
- "pnpm",
749
- "overrides",
750
- "resolutions",
751
- "husky",
752
- "simple-git-hooks",
753
- "lint-staged",
754
- "eslintConfig"
755
- ],
756
- pathPattern: "^$"
757
- },
758
- {
759
- order: { type: "asc" },
760
- pathPattern: "^(?:dev|peer|optional|bundled)?[Dd]ependencies(Meta)?$"
761
- },
762
- {
763
- order: { type: "asc" },
764
- pathPattern: "^(?:resolutions|overrides|pnpm.overrides)$"
765
- },
766
- {
767
- order: ["types", "import", "require", "default"],
768
- pathPattern: "^exports.*$"
769
- },
770
- {
771
- order: [
772
- // client hooks only
773
- "pre-commit",
774
- "prepare-commit-msg",
775
- "commit-msg",
776
- "post-commit",
777
- "pre-rebase",
778
- "post-rewrite",
779
- "post-checkout",
780
- "post-merge",
781
- "pre-push",
782
- "pre-auto-gc"
918
+ ["internal", "internal-type"],
919
+ ["parent", "sibling", "index"],
920
+ ["parent-type", "sibling-type", "index-type"],
921
+ "object",
922
+ "side-effect",
923
+ "side-effect-style",
924
+ "style",
925
+ "unknown"
783
926
  ],
784
- pathPattern: "^(?:gitHooks|husky|simple-git-hooks)$"
785
- }
786
- ]
787
- }
788
- }
789
- ];
790
- }
791
- function sortTsconfig() {
792
- return [
793
- {
794
- files: ["**/tsconfig.json", "**/tsconfig.*.json"],
795
- name: "coderwyd/sort/tsconfig-json",
796
- rules: {
797
- "jsonc/sort-keys": [
798
- "error",
799
- {
800
- order: [
801
- "extends",
802
- "compilerOptions",
803
- "references",
804
- "files",
805
- "include",
806
- "exclude"
807
- ],
808
- pathPattern: "^$"
809
- },
810
- {
811
- order: [
812
- /* Projects */
813
- "incremental",
814
- "composite",
815
- "tsBuildInfoFile",
816
- "disableSourceOfProjectReferenceRedirect",
817
- "disableSolutionSearching",
818
- "disableReferencedProjectLoad",
819
- /* Language and Environment */
820
- "target",
821
- "jsx",
822
- "jsxFactory",
823
- "jsxFragmentFactory",
824
- "jsxImportSource",
825
- "lib",
826
- "moduleDetection",
827
- "noLib",
828
- "reactNamespace",
829
- "useDefineForClassFields",
830
- "emitDecoratorMetadata",
831
- "experimentalDecorators",
832
- /* Modules */
833
- "baseUrl",
834
- "rootDir",
835
- "rootDirs",
836
- "customConditions",
837
- "module",
838
- "moduleResolution",
839
- "moduleSuffixes",
840
- "noResolve",
841
- "paths",
842
- "resolveJsonModule",
843
- "resolvePackageJsonExports",
844
- "resolvePackageJsonImports",
845
- "typeRoots",
846
- "types",
847
- "allowArbitraryExtensions",
848
- "allowImportingTsExtensions",
849
- "allowUmdGlobalAccess",
850
- /* JavaScript Support */
851
- "allowJs",
852
- "checkJs",
853
- "maxNodeModuleJsDepth",
854
- /* Type Checking */
855
- "strict",
856
- "strictBindCallApply",
857
- "strictFunctionTypes",
858
- "strictNullChecks",
859
- "strictPropertyInitialization",
860
- "allowUnreachableCode",
861
- "allowUnusedLabels",
862
- "alwaysStrict",
863
- "exactOptionalPropertyTypes",
864
- "noFallthroughCasesInSwitch",
865
- "noImplicitAny",
866
- "noImplicitOverride",
867
- "noImplicitReturns",
868
- "noImplicitThis",
869
- "noPropertyAccessFromIndexSignature",
870
- "noUncheckedIndexedAccess",
871
- "noUnusedLocals",
872
- "noUnusedParameters",
873
- "useUnknownInCatchVariables",
874
- /* Emit */
875
- "declaration",
876
- "declarationDir",
877
- "declarationMap",
878
- "downlevelIteration",
879
- "emitBOM",
880
- "emitDeclarationOnly",
881
- "importHelpers",
882
- "importsNotUsedAsValues",
883
- "inlineSourceMap",
884
- "inlineSources",
885
- "mapRoot",
886
- "newLine",
887
- "noEmit",
888
- "noEmitHelpers",
889
- "noEmitOnError",
890
- "outDir",
891
- "outFile",
892
- "preserveConstEnums",
893
- "preserveValueImports",
894
- "removeComments",
895
- "sourceMap",
896
- "sourceRoot",
897
- "stripInternal",
898
- /* Interop Constraints */
899
- "allowSyntheticDefaultImports",
900
- "esModuleInterop",
901
- "forceConsistentCasingInFileNames",
902
- "isolatedDeclarations",
903
- "isolatedModules",
904
- "preserveSymlinks",
905
- "verbatimModuleSyntax",
906
- /* Completeness */
907
- "skipDefaultLibCheck",
908
- "skipLibCheck"
909
- ],
910
- pathPattern: "^compilerOptions$"
927
+ internalPattern: ["~/**", "@/**", "#**"],
928
+ newlinesBetween: "ignore",
929
+ order: "asc",
930
+ type: "natural"
911
931
  }
932
+ ],
933
+ "perfectionist/sort-named-exports": [
934
+ "warn",
935
+ { groupKind: "values-first", order: "asc", type: "natural" }
936
+ ],
937
+ "perfectionist/sort-named-imports": [
938
+ "warn",
939
+ { groupKind: "values-first", order: "asc", type: "natural" }
912
940
  ]
913
941
  }
914
942
  }
915
943
  ];
916
944
  }
917
945
 
918
- // src/configs/stylistic.ts
919
- var StylisticConfigDefaults = {
920
- indent: 2,
921
- jsx: true,
922
- quotes: "single",
923
- semi: false
924
- };
925
- async function stylistic(options = {}) {
926
- const {
927
- indent,
928
- jsx: jsx2,
929
- overrides = {},
930
- quotes,
931
- semi
932
- } = {
933
- ...StylisticConfigDefaults,
934
- ...options
935
- };
936
- const pluginStylistic = await interopDefault(
937
- import("@stylistic/eslint-plugin")
938
- );
939
- const config = pluginStylistic.configs.customize({
940
- flat: true,
941
- indent,
942
- jsx: jsx2,
943
- pluginName: "style",
944
- quotes,
945
- semi
946
- });
947
- return [
948
- {
949
- name: "coderwyd/stylistic/rules",
950
- plugins: {
951
- antfu: import_eslint_plugin_antfu.default,
952
- style: pluginStylistic
953
- },
954
- rules: {
955
- ...config.rules,
956
- "antfu/consistent-list-newline": "error",
957
- "antfu/curly": "error",
958
- "antfu/if-newline": "warn",
959
- "antfu/top-level-function": "warn",
960
- ...overrides
961
- }
962
- }
963
- ];
964
- }
946
+ // src/configs/react.ts
947
+ var import_local_pkg3 = require("local-pkg");
965
948
 
966
- // src/configs/typescript.ts
949
+ // src/env.ts
967
950
  var import_node_process2 = __toESM(require("process"), 1);
968
- async function typescript(options = {}) {
969
- const { componentExts = [], overrides = {}, overridesTypeAware = {}, parserOptions = {} } = options;
970
- const files = options.files ?? [
971
- GLOB_TS,
972
- GLOB_TSX,
973
- ...componentExts.map((ext) => `**/*.${ext}`)
974
- ];
975
- const filesTypeAware = options.filesTypeAware ?? [GLOB_TS, GLOB_TSX];
976
- const ignoresTypeAware = options.ignoresTypeAware ?? [
977
- `${GLOB_MARKDOWN}/**`,
978
- GLOB_ASTRO_TS
979
- ];
980
- const tsconfigPath = options.tsconfigPath;
981
- const isTypeAware = !!tsconfigPath;
982
- const typeAwareRules = {
983
- "dot-notation": "off",
984
- "no-implied-eval": "off",
985
- "ts/await-thenable": "error",
986
- "ts/dot-notation": ["error", { allowKeywords: true }],
987
- "ts/no-floating-promises": "error",
988
- "ts/no-for-in-array": "error",
989
- "ts/no-implied-eval": "error",
990
- "ts/no-misused-promises": "error",
991
- "ts/no-unnecessary-type-assertion": "error",
992
- "ts/no-unsafe-argument": "error",
993
- "ts/no-unsafe-assignment": "error",
994
- "ts/no-unsafe-call": "error",
995
- "ts/no-unsafe-member-access": "error",
996
- "ts/no-unsafe-return": "error",
997
- "ts/promise-function-async": "error",
998
- "ts/restrict-plus-operands": "error",
999
- "ts/restrict-template-expressions": "error",
1000
- "ts/return-await": "error",
1001
- "ts/strict-boolean-expressions": "error",
1002
- "ts/switch-exhaustiveness-check": "error",
1003
- "ts/unbound-method": "error"
1004
- };
1005
- const [pluginTs, parserTs] = await Promise.all([
1006
- interopDefault(import("@typescript-eslint/eslint-plugin")),
1007
- interopDefault(import("@typescript-eslint/parser"))
1008
- ]);
1009
- function makeParser(typeAware, files2, ignores2) {
1010
- return {
1011
- files: files2,
1012
- ...ignores2 ? { ignores: ignores2 } : {},
1013
- languageOptions: {
1014
- parser: parserTs,
1015
- parserOptions: {
1016
- extraFileExtensions: componentExts.map((ext) => `.${ext}`),
1017
- sourceType: "module",
1018
- ...typeAware ? {
1019
- projectService: {
1020
- allowDefaultProject: ["./*.js"],
1021
- defaultProject: tsconfigPath
1022
- },
1023
- tsconfigRootDir: import_node_process2.default.cwd()
1024
- } : {},
1025
- ...parserOptions
1026
- }
1027
- },
1028
- name: `coderwyd/typescript/${typeAware ? "type-aware-parser" : "parser"}`
1029
- };
1030
- }
1031
- return [
1032
- {
1033
- // Install the plugins without globs, so they can be configured separately.
1034
- name: "coderwyd/typescript/setup",
1035
- plugins: {
1036
- antfu: import_eslint_plugin_antfu.default,
1037
- ts: pluginTs
1038
- }
1039
- },
1040
- // assign type-aware parser for type-aware files and type-unaware parser for the rest
1041
- ...isTypeAware ? [
1042
- makeParser(false, files),
1043
- makeParser(true, filesTypeAware, ignoresTypeAware)
1044
- ] : [makeParser(false, files)],
1045
- {
1046
- files,
1047
- name: "coderwyd/typescript/rules",
1048
- rules: {
1049
- ...renameRules(
1050
- pluginTs.configs["eslint-recommended"].overrides[0].rules,
1051
- { "@typescript-eslint": "ts" }
1052
- ),
1053
- ...renameRules(pluginTs.configs.strict.rules, {
1054
- "@typescript-eslint": "ts"
1055
- }),
1056
- "no-dupe-class-members": "off",
1057
- "no-loss-of-precision": "off",
1058
- "no-redeclare": "off",
1059
- "no-use-before-define": "off",
1060
- "no-useless-constructor": "off",
1061
- "ts/ban-ts-comment": [
1062
- "error",
1063
- { "ts-expect-error": "allow-with-description" }
1064
- ],
1065
- "ts/consistent-type-definitions": ["error", "interface"],
1066
- "ts/consistent-type-imports": [
1067
- "error",
1068
- { disallowTypeAnnotations: false, prefer: "type-imports" }
1069
- ],
1070
- "ts/method-signature-style": ["error", "property"],
1071
- // https://www.totaltypescript.com/method-shorthand-syntax-considered-harmful
1072
- "ts/no-dupe-class-members": "error",
1073
- "ts/no-dynamic-delete": "off",
1074
- "ts/no-empty-object-type": [
1075
- "error",
1076
- {
1077
- allowInterfaces: "with-single-extends",
1078
- // interface Derived extends Base {}
1079
- allowObjectTypes: "never",
1080
- allowWithName: "Props$"
1081
- }
1082
- ],
1083
- "ts/no-explicit-any": "off",
1084
- "ts/no-extraneous-class": "off",
1085
- "ts/no-import-type-side-effects": "error",
1086
- "ts/no-invalid-void-type": "off",
1087
- // this is deprecated
1088
- "ts/no-loss-of-precision": "off",
1089
- "ts/no-non-null-assertion": "off",
1090
- "ts/no-redeclare": "error",
1091
- "ts/no-require-imports": "error",
1092
- "ts/no-unused-vars": "off",
1093
- "ts/no-use-before-define": [
1094
- "error",
1095
- { classes: false, functions: false, variables: true }
1096
- ],
1097
- "ts/no-useless-constructor": "off",
1098
- "ts/no-wrapper-object-types": "error",
1099
- "ts/triple-slash-reference": "off",
1100
- "ts/unified-signatures": "off",
1101
- ...overrides
1102
- }
1103
- },
1104
- ...isTypeAware ? [
1105
- {
1106
- files: filesTypeAware,
1107
- ignores: ignoresTypeAware,
1108
- name: "coderwyd/typescript/rules-type-aware",
1109
- rules: {
1110
- ...typeAwareRules,
1111
- ...overridesTypeAware
1112
- }
1113
- }
1114
- ] : [],
1115
- {
1116
- files: [GLOB_DTS],
1117
- name: "coderwyd/typescript/disables/dts",
1118
- rules: {
1119
- "eslint-comments/no-unlimited-disable": "off",
1120
- "import/no-duplicates": "off",
1121
- "no-restricted-syntax": "off",
1122
- "unused-imports/no-unused-vars": "off"
1123
- }
1124
- },
1125
- {
1126
- files: ["**/*.{test,spec}.ts?(x)"],
1127
- name: "coderwyd/typescript/disables/test",
1128
- rules: {
1129
- "no-unused-expressions": "off"
1130
- }
1131
- },
1132
- {
1133
- files: ["**/*.js", "**/*.cjs"],
1134
- name: "coderwyd/typescript/disables/cjs",
1135
- rules: {
1136
- "ts/no-require-imports": "off",
1137
- "ts/no-var-requires": "off"
1138
- }
1139
- }
1140
- ];
1141
- }
1142
-
1143
- // src/configs/unicorn.ts
1144
- function unicorn() {
1145
- return [
1146
- {
1147
- name: "coderwyd/unicorn/rules",
1148
- plugins: {
1149
- unicorn: import_eslint_plugin_unicorn.default
1150
- },
1151
- rules: {
1152
- // 'unicorn/better-regex': 'error',
1153
- "unicorn/catch-error-name": "error",
1154
- "unicorn/consistent-empty-array-spread": "error",
1155
- "unicorn/custom-error-definition": "error",
1156
- "unicorn/error-message": "error",
1157
- // 'unicorn/explicit-length-check': 'error',
1158
- // 'unicorn/filename-case': [
1159
- // 'error',
1160
- // {
1161
- // cases: { kebabCase: true, pascalCase: true },
1162
- // ignore: [/^[A-Z]+\..*$/],
1163
- // },
1164
- "unicorn/escape-case": "error",
1165
- // ],
1166
- "unicorn/new-for-builtins": "error",
1167
- // 'unicorn/no-array-callback-reference': 'error',
1168
- "unicorn/no-array-method-this-argument": "error",
1169
- "unicorn/no-array-push-push": "error",
1170
- "unicorn/no-await-in-promise-methods": "error",
1171
- "unicorn/no-console-spaces": "error",
1172
- "unicorn/no-for-loop": "error",
1173
- "unicorn/no-hex-escape": "error",
1174
- "unicorn/no-instanceof-array": "error",
1175
- "unicorn/no-invalid-remove-event-listener": "error",
1176
- "unicorn/no-length-as-slice-end": "error",
1177
- "unicorn/no-lonely-if": "error",
1178
- "unicorn/no-new-array": "error",
1179
- "unicorn/no-new-buffer": "error",
1180
- "unicorn/no-single-promise-in-promise-methods": "error",
1181
- "unicorn/no-static-only-class": "error",
1182
- "unicorn/no-unnecessary-await": "error",
1183
- "unicorn/no-zero-fractions": `error`,
1184
- "unicorn/prefer-add-event-listener": "error",
1185
- "unicorn/prefer-array-find": "error",
1186
- "unicorn/prefer-array-flat-map": "error",
1187
- "unicorn/prefer-array-index-of": "error",
1188
- "unicorn/prefer-array-some": "error",
1189
- "unicorn/prefer-at": "error",
1190
- "unicorn/prefer-blob-reading-methods": "error",
1191
- "unicorn/prefer-date-now": "error",
1192
- "unicorn/prefer-dom-node-append": "error",
1193
- "unicorn/prefer-dom-node-dataset": "error",
1194
- "unicorn/prefer-dom-node-remove": "error",
1195
- "unicorn/prefer-dom-node-text-content": "error",
1196
- "unicorn/prefer-includes": "error",
1197
- "unicorn/prefer-keyboard-event-key": "error",
1198
- "unicorn/prefer-math-trunc": "error",
1199
- "unicorn/prefer-modern-dom-apis": "error",
1200
- "unicorn/prefer-modern-math-apis": "error",
1201
- "unicorn/prefer-negative-index": "error",
1202
- "unicorn/prefer-node-protocol": "error",
1203
- "unicorn/prefer-number-properties": "error",
1204
- "unicorn/prefer-optional-catch-binding": "error",
1205
- "unicorn/prefer-prototype-methods": "error",
1206
- "unicorn/prefer-query-selector": "error",
1207
- "unicorn/prefer-reflect-apply": "error",
1208
- // 'unicorn/prefer-regexp-test': 'error',
1209
- "unicorn/prefer-string-replace-all": "error",
1210
- "unicorn/prefer-string-slice": "error",
1211
- "unicorn/prefer-string-starts-ends-with": "error",
1212
- "unicorn/prefer-string-trim-start-end": "error",
1213
- // top level await is not supported in all environments
1214
- // 'unicorn/prefer-top-level-await': 'error',
1215
- "unicorn/prefer-type-error": "error",
1216
- "unicorn/throw-new-error": "error"
1217
- }
1218
- }
1219
- ];
951
+ var import_local_pkg2 = require("local-pkg");
952
+ var isInEditor = !!((import_node_process2.default.env.VSCODE_PID || import_node_process2.default.env.VSCODE_CWD || import_node_process2.default.env.JETBRAINS_IDE || import_node_process2.default.env.VIM || import_node_process2.default.env.NVIM) && !import_node_process2.default.env.CI);
953
+ var hasTypeScript = (0, import_local_pkg2.isPackageExists)("typescript");
954
+ var VueJsPackages = [
955
+ "vue",
956
+ "nuxt",
957
+ "vitepress",
958
+ "@slidev/cli"
959
+ ];
960
+ var hasVue = hasPackages(VueJsPackages);
961
+ var RemixPackages = [
962
+ "@remix-run/node",
963
+ "@remix-run/react",
964
+ "@remix-run/serve",
965
+ "@remix-run/dev"
966
+ ];
967
+ var NextJsPackages = ["next"];
968
+ var isUsingRemix = hasPackages(RemixPackages);
969
+ var isUsingNext = hasPackages(NextJsPackages);
970
+ function hasPackages(packages) {
971
+ return packages.some((name) => (0, import_local_pkg2.isPackageExists)(name));
1220
972
  }
1221
973
 
1222
- // src/configs/vue.ts
1223
- var import_eslint_merge_processors = require("eslint-merge-processors");
1224
- async function vue(options = {}) {
1225
- const { files = [GLOB_VUE], overrides = {}, stylistic: stylistic2 = true } = options;
1226
- const sfcBlocks = options.sfcBlocks === true ? {} : options.sfcBlocks ?? {};
1227
- const { indent = 2 } = typeof stylistic2 === "boolean" ? {} : stylistic2;
1228
- const [pluginVue, parserVue, processorVueBlocks] = await Promise.all([
1229
- interopDefault(import("eslint-plugin-vue")),
1230
- interopDefault(import("vue-eslint-parser")),
1231
- interopDefault(import("eslint-processor-vue-blocks"))
974
+ // src/configs/react.ts
975
+ var ReactRefreshAllowConstantExportPackages = ["vite"];
976
+ async function react(options = {}) {
977
+ const { files = [GLOB_SRC], overrides = {} } = options;
978
+ await ensurePackages([
979
+ "@eslint-react/eslint-plugin",
980
+ "eslint-plugin-react-hooks",
981
+ "eslint-plugin-react-refresh"
1232
982
  ]);
1233
- const isVue3 = getVueVersion() === 3;
1234
- const configKeys = isVue3 ? ["vue3-essential", "vue3-strongly-recommended", "vue3-recommended"] : ["essential", "strongly-recommended", "recommended"];
1235
- const vueRules = configKeys.reduce((preRules, key) => {
1236
- const config = pluginVue.configs[key];
1237
- return {
1238
- ...preRules,
1239
- ...config.rules
1240
- };
1241
- }, {});
983
+ const tsconfigPath = options?.tsconfigPath ? toArray(options.tsconfigPath) : void 0;
984
+ const isTypeAware = !!tsconfigPath;
985
+ const [pluginReact, pluginReactHooks, pluginReactRefresh, parserTs] = await Promise.all([
986
+ interopDefault(import("@eslint-react/eslint-plugin")),
987
+ interopDefault(import("eslint-plugin-react-hooks")),
988
+ interopDefault(import("eslint-plugin-react-refresh")),
989
+ interopDefault(import("@typescript-eslint/parser"))
990
+ ]);
991
+ const isAllowConstantExport = ReactRefreshAllowConstantExportPackages.some(
992
+ (i) => (0, import_local_pkg3.isPackageExists)(i)
993
+ );
994
+ const plugins = pluginReact.configs.all.plugins;
1242
995
  return [
1243
996
  {
1244
- // This allows Vue plugin to work with auto imports
1245
- // https://github.com/vuejs/eslint-plugin-vue/pull/2422
1246
- languageOptions: {
1247
- globals: {
1248
- computed: "readonly",
1249
- defineEmits: "readonly",
1250
- defineExpose: "readonly",
1251
- defineProps: "readonly",
1252
- onMounted: "readonly",
1253
- onUnmounted: "readonly",
1254
- reactive: "readonly",
1255
- ref: "readonly",
1256
- shallowReactive: "readonly",
1257
- shallowRef: "readonly",
1258
- toRef: "readonly",
1259
- toRefs: "readonly",
1260
- watch: "readonly",
1261
- watchEffect: "readonly"
1262
- }
1263
- },
1264
- name: "coderwyd/vue/setup",
997
+ name: "coderwyd/react/setup",
1265
998
  plugins: {
1266
- vue: pluginVue
999
+ "react": plugins["@eslint-react"],
1000
+ "react-dom": plugins["@eslint-react/dom"],
1001
+ "react-hooks": pluginReactHooks,
1002
+ "react-hooks-extra": plugins["@eslint-react/hooks-extra"],
1003
+ "react-naming-convention": plugins["@eslint-react/naming-convention"],
1004
+ "react-refresh": pluginReactRefresh
1267
1005
  }
1268
1006
  },
1269
1007
  {
1270
1008
  files,
1271
1009
  languageOptions: {
1272
- parser: parserVue,
1010
+ parser: parserTs,
1273
1011
  parserOptions: {
1274
1012
  ecmaFeatures: {
1275
1013
  jsx: true
1276
1014
  },
1277
- extraFileExtensions: [".vue"],
1278
- parser: options.typescript ? await interopDefault(
1279
- import("@typescript-eslint/parser")
1280
- ) : null,
1281
- sourceType: "module"
1282
- }
1015
+ ...isTypeAware ? { project: tsconfigPath } : {}
1016
+ },
1017
+ sourceType: "module"
1283
1018
  },
1284
- name: "coderwyd/vue/rules",
1285
- processor: sfcBlocks === false ? pluginVue.processors[".vue"] : (0, import_eslint_merge_processors.mergeProcessors)([
1286
- pluginVue.processors[".vue"],
1287
- processorVueBlocks({
1288
- ...sfcBlocks,
1289
- blocks: {
1290
- styles: true,
1291
- ...sfcBlocks.blocks
1292
- }
1293
- })
1294
- ]),
1295
- rules: {
1296
- ...pluginVue.configs.base.rules,
1297
- ...vueRules,
1298
- "node/prefer-global/process": "off",
1299
- "vue/block-order": [
1300
- "error",
1301
- {
1302
- order: isVue3 ? ["script", "template", "style"] : ["template", "script", "style"]
1303
- }
1304
- ],
1305
- // 'vue/component-api-style': ['warn', ['script-setup', 'composition']],
1306
- "vue/component-name-in-template-casing": ["error", "PascalCase"],
1307
- "vue/component-options-name-casing": ["error", "PascalCase"],
1308
- // this is deprecated
1309
- "vue/component-tags-order": "off",
1310
- "vue/custom-event-name-casing": ["error", "camelCase"],
1311
- // 'vue/define-emits-declaration': ['warn', 'type-based'],
1312
- "vue/define-macros-order": [
1313
- "error",
1314
- {
1315
- order: [
1316
- "defineOptions",
1317
- "defineProps",
1318
- "defineEmits",
1319
- "defineSlots"
1320
- ]
1321
- }
1322
- ],
1323
- // 'vue/define-props-declaration': ['warn', 'type-based'],
1324
- "vue/dot-location": ["error", "property"],
1325
- "vue/dot-notation": ["error", { allowKeywords: true }],
1326
- "vue/eqeqeq": ["error", "smart"],
1327
- "vue/html-indent": ["error", indent],
1328
- "vue/html-quotes": ["error", "double"],
1329
- "vue/html-self-closing": [
1330
- "error",
1331
- {
1332
- html: {
1333
- component: "always",
1334
- normal: "always",
1335
- void: "any"
1336
- },
1337
- math: "always",
1338
- svg: "always"
1339
- }
1340
- ],
1341
- "vue/max-attributes-per-line": "off",
1342
- "vue/multi-word-component-names": "off",
1343
- // 'vue/next-tick-style': ['warn', 'promise'],
1344
- "vue/no-constant-condition": "warn",
1345
- "vue/no-dupe-keys": "off",
1346
- "vue/no-duplicate-attr-inheritance": "warn",
1347
- "vue/no-empty-pattern": "error",
1348
- "vue/no-extra-parens": ["error", "functions"],
1349
- "vue/no-irregular-whitespace": "error",
1350
- "vue/no-loss-of-precision": "error",
1351
- "vue/no-required-prop-with-default": "warn",
1352
- "vue/no-restricted-syntax": [
1353
- "error",
1354
- "DebuggerStatement",
1355
- "LabeledStatement",
1356
- "WithStatement"
1357
- ],
1358
- "vue/no-restricted-v-bind": ["error", "/^v-/"],
1359
- "vue/no-setup-props-reactivity-loss": "off",
1360
- "vue/no-sparse-arrays": "error",
1361
- "vue/no-unsupported-features": "warn",
1362
- "vue/no-unused-emit-declarations": "warn",
1363
- "vue/no-unused-refs": "error",
1364
- "vue/no-use-v-else-with-v-for": "error",
1365
- "vue/no-useless-mustaches": "warn",
1366
- "vue/no-useless-v-bind": "error",
1367
- "vue/no-v-html": "off",
1368
- "vue/no-v-text": "warn",
1369
- "vue/object-shorthand": [
1370
- "error",
1371
- "always",
1372
- {
1373
- avoidQuotes: true,
1374
- ignoreConstructors: false
1375
- }
1376
- ],
1377
- "vue/prefer-define-options": "warn",
1378
- "vue/prefer-separate-static-class": "error",
1379
- "vue/prefer-template": "error",
1380
- "vue/prop-name-casing": ["error", "camelCase"],
1381
- "vue/require-default-prop": "off",
1382
- "vue/require-macro-variable-name": [
1383
- "warn",
1384
- {
1385
- defineEmits: "emit",
1386
- defineProps: "props",
1387
- defineSlots: "slots",
1388
- useAttrs: "attrs",
1389
- useSlots: "slots"
1390
- }
1391
- ],
1392
- "vue/require-prop-types": "off",
1393
- // 'vue/singleline-html-element-content-newline': 'off',
1394
- "vue/space-infix-ops": "error",
1395
- "vue/space-unary-ops": ["error", { nonwords: false, words: true }],
1396
- "vue/valid-define-options": "warn",
1397
- ...stylistic2 ? {
1398
- "vue/array-bracket-spacing": ["error", "never"],
1399
- "vue/arrow-spacing": ["error", { after: true, before: true }],
1400
- "vue/block-spacing": ["error", "always"],
1401
- "vue/block-tag-newline": [
1402
- "error",
1403
- {
1404
- multiline: "always",
1405
- singleline: "always"
1406
- }
1407
- ],
1408
- "vue/brace-style": [
1409
- "error",
1410
- "stroustrup",
1411
- { allowSingleLine: true }
1412
- ],
1413
- "vue/comma-dangle": ["error", "always-multiline"],
1414
- "vue/comma-spacing": ["error", { after: true, before: false }],
1415
- "vue/comma-style": ["error", "last"],
1416
- "vue/html-comment-content-newline": "warn",
1417
- "vue/html-comment-content-spacing": [
1418
- "error",
1419
- "always",
1420
- {
1421
- exceptions: ["-"]
1422
- }
1423
- ],
1424
- "vue/key-spacing": [
1425
- "error",
1426
- { afterColon: true, beforeColon: false }
1427
- ],
1428
- "vue/keyword-spacing": ["error", { after: true, before: true }],
1429
- "vue/object-curly-newline": "off",
1430
- "vue/object-curly-spacing": ["error", "always"],
1431
- "vue/object-property-newline": [
1432
- "error",
1433
- { allowMultiplePropertiesPerLine: true }
1434
- ],
1435
- "vue/operator-linebreak": ["error", "before"],
1436
- "vue/padding-line-between-blocks": ["error", "always"],
1437
- "vue/quote-props": ["error", "consistent-as-needed"],
1438
- "vue/space-in-parens": ["error", "never"],
1439
- "vue/template-curly-spacing": "error"
1019
+ name: "coderwyd/react/rules",
1020
+ rules: {
1021
+ // recommended rules from @eslint-react/dom
1022
+ "react-dom/no-children-in-void-dom-elements": "warn",
1023
+ "react-dom/no-dangerously-set-innerhtml": "warn",
1024
+ "react-dom/no-dangerously-set-innerhtml-with-children": "error",
1025
+ "react-dom/no-find-dom-node": "error",
1026
+ "react-dom/no-missing-button-type": "warn",
1027
+ "react-dom/no-missing-iframe-sandbox": "warn",
1028
+ "react-dom/no-namespace": "error",
1029
+ "react-dom/no-render-return-value": "error",
1030
+ "react-dom/no-script-url": "warn",
1031
+ "react-dom/no-unsafe-iframe-sandbox": "warn",
1032
+ "react-dom/no-unsafe-target-blank": "warn",
1033
+ // recommended rules react-hooks
1034
+ "react-hooks/exhaustive-deps": "warn",
1035
+ "react-hooks/rules-of-hooks": "error",
1036
+ // react refresh
1037
+ "react-refresh/only-export-components": [
1038
+ "warn",
1039
+ {
1040
+ allowConstantExport: isAllowConstantExport,
1041
+ allowExportNames: [
1042
+ ...isUsingNext ? [
1043
+ "config",
1044
+ "generateStaticParams",
1045
+ "metadata",
1046
+ "generateMetadata",
1047
+ "viewport",
1048
+ "generateViewport"
1049
+ ] : [],
1050
+ ...isUsingRemix ? ["meta", "links", "headers", "loader", "action"] : []
1051
+ ]
1052
+ }
1053
+ ],
1054
+ // recommended rules from @eslint-react
1055
+ "react/ensure-forward-ref-using-ref": "warn",
1056
+ "react/no-access-state-in-setstate": "error",
1057
+ "react/no-array-index-key": "warn",
1058
+ "react/no-children-count": "warn",
1059
+ "react/no-children-for-each": "warn",
1060
+ "react/no-children-map": "warn",
1061
+ "react/no-children-only": "warn",
1062
+ "react/no-children-prop": "warn",
1063
+ "react/no-children-to-array": "warn",
1064
+ "react/no-clone-element": "warn",
1065
+ "react/no-comment-textnodes": "warn",
1066
+ "react/no-component-will-mount": "error",
1067
+ "react/no-component-will-receive-props": "error",
1068
+ "react/no-component-will-update": "error",
1069
+ "react/no-create-ref": "error",
1070
+ "react/no-direct-mutation-state": "error",
1071
+ "react/no-duplicate-key": "error",
1072
+ "react/no-implicit-key": "error",
1073
+ "react/no-missing-key": "error",
1074
+ "react/no-nested-components": "warn",
1075
+ "react/no-redundant-should-component-update": "error",
1076
+ "react/no-set-state-in-component-did-mount": "warn",
1077
+ "react/no-set-state-in-component-did-update": "warn",
1078
+ "react/no-set-state-in-component-will-update": "warn",
1079
+ "react/no-string-refs": "error",
1080
+ "react/no-unsafe-component-will-mount": "warn",
1081
+ "react/no-unsafe-component-will-receive-props": "warn",
1082
+ "react/no-unsafe-component-will-update": "warn",
1083
+ "react/no-unstable-context-value": "error",
1084
+ "react/no-unstable-default-props": "error",
1085
+ "react/no-unused-class-component-members": "warn",
1086
+ "react/no-unused-state": "warn",
1087
+ "react/no-useless-fragment": "warn",
1088
+ "react/prefer-destructuring-assignment": "warn",
1089
+ "react/prefer-shorthand-boolean": "warn",
1090
+ "react/prefer-shorthand-fragment": "warn",
1091
+ ...isTypeAware ? {
1092
+ "react/no-leaked-conditional-rendering": "warn"
1440
1093
  } : {},
1094
+ // overrides
1441
1095
  ...overrides
1442
1096
  }
1443
1097
  }
1444
1098
  ];
1445
1099
  }
1446
1100
 
1447
- // src/configs/test.ts
1448
- var _pluginTest;
1449
- async function test(options = {}) {
1450
- const { files = GLOB_TESTS, isInEditor: isInEditor2 = false, overrides = {} } = options;
1451
- const [pluginVitest, pluginNoOnlyTests] = await Promise.all([
1452
- interopDefault(import("@vitest/eslint-plugin")),
1453
- // @ts-expect-error missing types
1454
- interopDefault(import("eslint-plugin-no-only-tests"))
1455
- ]);
1456
- _pluginTest = _pluginTest || {
1457
- ...pluginVitest,
1458
- rules: {
1459
- ...pluginVitest.rules,
1460
- // extend `test/no-only-tests` rule
1461
- ...pluginNoOnlyTests.rules
1462
- }
1101
+ // src/configs/regexp.ts
1102
+ var import_eslint_plugin_regexp = require("eslint-plugin-regexp");
1103
+ function regexp(options = {}) {
1104
+ const config = import_eslint_plugin_regexp.configs["flat/recommended"];
1105
+ const rules = {
1106
+ ...config.rules
1463
1107
  };
1108
+ if (options.level === "warn") {
1109
+ Object.keys(rules).forEach((key) => {
1110
+ if (rules[key] === "error")
1111
+ rules[key] = "warn";
1112
+ });
1113
+ }
1464
1114
  return [
1465
1115
  {
1466
- name: "coderwyd/test/setup",
1467
- plugins: {
1468
- test: _pluginTest
1116
+ ...config,
1117
+ name: "coderwyd/regexp/rules",
1118
+ rules: {
1119
+ ...rules,
1120
+ ...options.overrides
1469
1121
  }
1470
- },
1122
+ }
1123
+ ];
1124
+ }
1125
+
1126
+ // src/configs/sort.ts
1127
+ function sortPackageJson() {
1128
+ return [
1471
1129
  {
1472
- files,
1473
- name: "coderwyd/test/rules",
1130
+ files: ["**/package.json"],
1131
+ name: "coderwyd/sort/package-json",
1474
1132
  rules: {
1475
- "node/prefer-global/process": "off",
1476
- "test/consistent-test-it": [
1133
+ "jsonc/sort-array-values": [
1477
1134
  "error",
1478
- { fn: "it", withinDescribe: "it" }
1135
+ {
1136
+ order: { type: "asc" },
1137
+ pathPattern: "^files$"
1138
+ }
1479
1139
  ],
1480
- "test/no-identical-title": "error",
1481
- "test/no-import-node-test": "error",
1482
- "test/no-only-tests": isInEditor2 ? "off" : "error",
1483
- "test/prefer-hooks-in-order": "error",
1484
- "test/prefer-lowercase-title": "error",
1485
- "ts/explicit-function-return-type": "off",
1486
- ...overrides
1140
+ "jsonc/sort-keys": [
1141
+ "error",
1142
+ {
1143
+ order: [
1144
+ "publisher",
1145
+ "name",
1146
+ "displayName",
1147
+ "type",
1148
+ "version",
1149
+ "private",
1150
+ "packageManager",
1151
+ "description",
1152
+ "author",
1153
+ "license",
1154
+ "funding",
1155
+ "homepage",
1156
+ "repository",
1157
+ "bugs",
1158
+ "keywords",
1159
+ "categories",
1160
+ "sideEffects",
1161
+ "exports",
1162
+ "main",
1163
+ "module",
1164
+ "unpkg",
1165
+ "jsdelivr",
1166
+ "types",
1167
+ "typesVersions",
1168
+ "bin",
1169
+ "icon",
1170
+ "files",
1171
+ "engines",
1172
+ "activationEvents",
1173
+ "contributes",
1174
+ "scripts",
1175
+ "peerDependencies",
1176
+ "peerDependenciesMeta",
1177
+ "dependencies",
1178
+ "optionalDependencies",
1179
+ "devDependencies",
1180
+ "pnpm",
1181
+ "overrides",
1182
+ "resolutions",
1183
+ "husky",
1184
+ "simple-git-hooks",
1185
+ "lint-staged",
1186
+ "eslintConfig"
1187
+ ],
1188
+ pathPattern: "^$"
1189
+ },
1190
+ {
1191
+ order: { type: "asc" },
1192
+ pathPattern: "^(?:dev|peer|optional|bundled)?[Dd]ependencies(Meta)?$"
1193
+ },
1194
+ {
1195
+ order: { type: "asc" },
1196
+ pathPattern: "^(?:resolutions|overrides|pnpm.overrides)$"
1197
+ },
1198
+ {
1199
+ order: ["types", "import", "require", "default"],
1200
+ pathPattern: "^exports.*$"
1201
+ },
1202
+ {
1203
+ order: [
1204
+ // client hooks only
1205
+ "pre-commit",
1206
+ "prepare-commit-msg",
1207
+ "commit-msg",
1208
+ "post-commit",
1209
+ "pre-rebase",
1210
+ "post-rewrite",
1211
+ "post-checkout",
1212
+ "post-merge",
1213
+ "pre-push",
1214
+ "pre-auto-gc"
1215
+ ],
1216
+ pathPattern: "^(?:gitHooks|husky|simple-git-hooks)$"
1217
+ }
1218
+ ]
1487
1219
  }
1488
1220
  }
1489
1221
  ];
1490
1222
  }
1491
-
1492
- // src/configs/perfectionist.ts
1493
- function perfectionist() {
1223
+ function sortTsconfig() {
1494
1224
  return [
1495
1225
  {
1496
- name: "coderwyd/perfectionist/rules",
1497
- plugins: {
1498
- perfectionist: import_eslint_plugin_perfectionist.default
1499
- },
1226
+ files: ["**/tsconfig.json", "**/tsconfig.*.json"],
1227
+ name: "coderwyd/sort/tsconfig-json",
1500
1228
  rules: {
1501
- "perfectionist/sort-imports": [
1502
- "warn",
1229
+ "jsonc/sort-keys": [
1230
+ "error",
1503
1231
  {
1504
- groups: [
1505
- "builtin",
1506
- "external",
1507
- "internal",
1508
- "internal-type",
1509
- "parent",
1510
- "parent-type",
1511
- "sibling",
1512
- "sibling-type",
1513
- "index",
1514
- "index-type",
1515
- "object",
1516
- "type",
1517
- "side-effect",
1518
- "side-effect-style"
1232
+ order: [
1233
+ "extends",
1234
+ "compilerOptions",
1235
+ "references",
1236
+ "files",
1237
+ "include",
1238
+ "exclude"
1239
+ ],
1240
+ pathPattern: "^$"
1241
+ },
1242
+ {
1243
+ order: [
1244
+ /* Projects */
1245
+ "incremental",
1246
+ "composite",
1247
+ "tsBuildInfoFile",
1248
+ "disableSourceOfProjectReferenceRedirect",
1249
+ "disableSolutionSearching",
1250
+ "disableReferencedProjectLoad",
1251
+ /* Language and Environment */
1252
+ "target",
1253
+ "jsx",
1254
+ "jsxFactory",
1255
+ "jsxFragmentFactory",
1256
+ "jsxImportSource",
1257
+ "lib",
1258
+ "moduleDetection",
1259
+ "noLib",
1260
+ "reactNamespace",
1261
+ "useDefineForClassFields",
1262
+ "emitDecoratorMetadata",
1263
+ "experimentalDecorators",
1264
+ /* Modules */
1265
+ "baseUrl",
1266
+ "rootDir",
1267
+ "rootDirs",
1268
+ "customConditions",
1269
+ "module",
1270
+ "moduleResolution",
1271
+ "moduleSuffixes",
1272
+ "noResolve",
1273
+ "paths",
1274
+ "resolveJsonModule",
1275
+ "resolvePackageJsonExports",
1276
+ "resolvePackageJsonImports",
1277
+ "typeRoots",
1278
+ "types",
1279
+ "allowArbitraryExtensions",
1280
+ "allowImportingTsExtensions",
1281
+ "allowUmdGlobalAccess",
1282
+ /* JavaScript Support */
1283
+ "allowJs",
1284
+ "checkJs",
1285
+ "maxNodeModuleJsDepth",
1286
+ /* Type Checking */
1287
+ "strict",
1288
+ "strictBindCallApply",
1289
+ "strictFunctionTypes",
1290
+ "strictNullChecks",
1291
+ "strictPropertyInitialization",
1292
+ "allowUnreachableCode",
1293
+ "allowUnusedLabels",
1294
+ "alwaysStrict",
1295
+ "exactOptionalPropertyTypes",
1296
+ "noFallthroughCasesInSwitch",
1297
+ "noImplicitAny",
1298
+ "noImplicitOverride",
1299
+ "noImplicitReturns",
1300
+ "noImplicitThis",
1301
+ "noPropertyAccessFromIndexSignature",
1302
+ "noUncheckedIndexedAccess",
1303
+ "noUnusedLocals",
1304
+ "noUnusedParameters",
1305
+ "useUnknownInCatchVariables",
1306
+ /* Emit */
1307
+ "declaration",
1308
+ "declarationDir",
1309
+ "declarationMap",
1310
+ "downlevelIteration",
1311
+ "emitBOM",
1312
+ "emitDeclarationOnly",
1313
+ "importHelpers",
1314
+ "importsNotUsedAsValues",
1315
+ "inlineSourceMap",
1316
+ "inlineSources",
1317
+ "mapRoot",
1318
+ "newLine",
1319
+ "noEmit",
1320
+ "noEmitHelpers",
1321
+ "noEmitOnError",
1322
+ "outDir",
1323
+ "outFile",
1324
+ "preserveConstEnums",
1325
+ "preserveValueImports",
1326
+ "removeComments",
1327
+ "sourceMap",
1328
+ "sourceRoot",
1329
+ "stripInternal",
1330
+ /* Interop Constraints */
1331
+ "allowSyntheticDefaultImports",
1332
+ "esModuleInterop",
1333
+ "forceConsistentCasingInFileNames",
1334
+ "isolatedDeclarations",
1335
+ "isolatedModules",
1336
+ "preserveSymlinks",
1337
+ "verbatimModuleSyntax",
1338
+ /* Completeness */
1339
+ "skipDefaultLibCheck",
1340
+ "skipLibCheck"
1519
1341
  ],
1520
- internalPattern: ["~/**", "@/**", "#**"],
1521
- newlinesBetween: "ignore"
1342
+ pathPattern: "^compilerOptions$"
1522
1343
  }
1523
- ],
1524
- "perfectionist/sort-named-exports": [
1525
- "warn",
1526
- { groupKind: "values-first" }
1527
- ],
1528
- "perfectionist/sort-named-imports": [
1529
- "warn",
1530
- { groupKind: "values-first" }
1531
1344
  ]
1532
1345
  }
1533
1346
  }
1534
1347
  ];
1535
1348
  }
1536
1349
 
1537
- // src/configs/react.ts
1538
- var import_local_pkg3 = require("local-pkg");
1539
-
1540
- // src/env.ts
1541
- var import_node_process3 = __toESM(require("process"), 1);
1542
- var import_local_pkg2 = require("local-pkg");
1543
- var isInEditor = !!((import_node_process3.default.env.VSCODE_PID || import_node_process3.default.env.VSCODE_CWD || import_node_process3.default.env.JETBRAINS_IDE || import_node_process3.default.env.VIM || import_node_process3.default.env.NVIM) && !import_node_process3.default.env.CI);
1544
- var hasTypeScript = (0, import_local_pkg2.isPackageExists)("typescript");
1545
- var VueJsPackages = [
1546
- "vue",
1547
- "nuxt",
1548
- "vitepress",
1549
- "@slidev/cli"
1550
- ];
1551
- var hasVue = hasPackages(VueJsPackages);
1552
- var RemixPackages = [
1553
- "@remix-run/node",
1554
- "@remix-run/react",
1555
- "@remix-run/serve",
1556
- "@remix-run/dev"
1557
- ];
1558
- var NextJsPackages = ["next"];
1559
- var isUsingRemix = hasPackages(RemixPackages);
1560
- var isUsingNext = hasPackages(NextJsPackages);
1561
- function hasPackages(packages) {
1562
- return packages.some((name) => (0, import_local_pkg2.isPackageExists)(name));
1563
- }
1564
-
1565
- // src/configs/react.ts
1566
- var ReactRefreshAllowConstantExportPackages = ["vite"];
1567
- async function react(options = {}) {
1568
- const { files = [GLOB_SRC], overrides = {} } = options;
1569
- await ensurePackages([
1570
- "@eslint-react/eslint-plugin",
1571
- "eslint-plugin-react-hooks",
1572
- "eslint-plugin-react-refresh"
1573
- ]);
1574
- const tsconfigPath = options?.tsconfigPath ? toArray(options.tsconfigPath) : void 0;
1575
- const isTypeAware = !!tsconfigPath;
1576
- const [pluginReact, pluginReactHooks, pluginReactRefresh, parserTs] = await Promise.all([
1577
- interopDefault(import("@eslint-react/eslint-plugin")),
1578
- interopDefault(import("eslint-plugin-react-hooks")),
1579
- interopDefault(import("eslint-plugin-react-refresh")),
1580
- interopDefault(import("@typescript-eslint/parser"))
1350
+ // src/configs/svelte.ts
1351
+ async function svelte(options = {}) {
1352
+ const { files = [GLOB_SVELTE], overrides = {}, stylistic: stylistic2 = true } = options;
1353
+ const {
1354
+ indent = 2,
1355
+ quotes = "single"
1356
+ } = typeof stylistic2 === "boolean" ? {} : stylistic2;
1357
+ await ensurePackages(["eslint-plugin-svelte"]);
1358
+ const [pluginSvelte, parserSvelte] = await Promise.all([
1359
+ interopDefault(import("eslint-plugin-svelte")),
1360
+ interopDefault(import("svelte-eslint-parser"))
1581
1361
  ]);
1582
- const isAllowConstantExport = ReactRefreshAllowConstantExportPackages.some(
1583
- (i) => (0, import_local_pkg3.isPackageExists)(i)
1584
- );
1585
- const plugins = pluginReact.configs.all.plugins;
1586
1362
  return [
1587
1363
  {
1588
- name: "coderwyd/react/setup",
1364
+ name: "coderwyd/svelte/setup",
1589
1365
  plugins: {
1590
- "react": plugins["@eslint-react"],
1591
- "react-dom": plugins["@eslint-react/dom"],
1592
- "react-hooks": pluginReactHooks,
1593
- "react-hooks-extra": plugins["@eslint-react/hooks-extra"],
1594
- "react-naming-convention": plugins["@eslint-react/naming-convention"],
1595
- "react-refresh": pluginReactRefresh
1366
+ svelte: pluginSvelte
1596
1367
  }
1597
1368
  },
1598
1369
  {
1599
1370
  files,
1600
1371
  languageOptions: {
1601
- parser: parserTs,
1372
+ parser: parserSvelte,
1602
1373
  parserOptions: {
1603
- ecmaFeatures: {
1604
- jsx: true
1605
- },
1606
- ...isTypeAware ? { project: tsconfigPath } : {}
1607
- },
1608
- sourceType: "module"
1374
+ extraFileExtensions: [".svelte"],
1375
+ parser: options.typescript ? await interopDefault(
1376
+ import("@typescript-eslint/parser")
1377
+ ) : null
1378
+ }
1609
1379
  },
1610
- name: "coderwyd/react/rules",
1380
+ name: "coderwyd/svelte/rules",
1381
+ processor: pluginSvelte.processors[".svelte"],
1611
1382
  rules: {
1612
- // recommended rules from @eslint-react/dom
1613
- "react-dom/no-children-in-void-dom-elements": "warn",
1614
- "react-dom/no-dangerously-set-innerhtml": "warn",
1615
- "react-dom/no-dangerously-set-innerhtml-with-children": "error",
1616
- "react-dom/no-find-dom-node": "error",
1617
- "react-dom/no-missing-button-type": "warn",
1618
- "react-dom/no-missing-iframe-sandbox": "warn",
1619
- "react-dom/no-namespace": "error",
1620
- "react-dom/no-render-return-value": "error",
1621
- "react-dom/no-script-url": "warn",
1622
- "react-dom/no-unsafe-iframe-sandbox": "warn",
1623
- "react-dom/no-unsafe-target-blank": "warn",
1624
- // recommended rules react-hooks
1625
- "react-hooks/exhaustive-deps": "warn",
1626
- "react-hooks/rules-of-hooks": "error",
1627
- // react refresh
1628
- "react-refresh/only-export-components": [
1629
- "warn",
1383
+ "import/no-mutable-exports": "off",
1384
+ "no-undef": "off",
1385
+ // incompatible with most recent (attribute-form) generic types RFC
1386
+ "no-unused-vars": [
1387
+ "error",
1630
1388
  {
1631
- allowConstantExport: isAllowConstantExport,
1632
- allowExportNames: [
1633
- ...isUsingNext ? [
1634
- "config",
1635
- "generateStaticParams",
1636
- "metadata",
1637
- "generateMetadata",
1638
- "viewport",
1639
- "generateViewport"
1640
- ] : [],
1641
- ...isUsingRemix ? ["meta", "links", "headers", "loader", "action"] : []
1642
- ]
1643
- }
1644
- ],
1645
- // recommended rules from @eslint-react
1646
- "react/ensure-forward-ref-using-ref": "warn",
1647
- "react/no-access-state-in-setstate": "error",
1648
- "react/no-array-index-key": "warn",
1649
- "react/no-children-count": "warn",
1650
- "react/no-children-for-each": "warn",
1651
- "react/no-children-map": "warn",
1652
- "react/no-children-only": "warn",
1653
- "react/no-children-prop": "warn",
1654
- "react/no-children-to-array": "warn",
1655
- "react/no-clone-element": "warn",
1656
- "react/no-comment-textnodes": "warn",
1657
- "react/no-component-will-mount": "error",
1658
- "react/no-component-will-receive-props": "error",
1659
- "react/no-component-will-update": "error",
1660
- "react/no-create-ref": "error",
1661
- "react/no-direct-mutation-state": "error",
1662
- "react/no-duplicate-key": "error",
1663
- "react/no-implicit-key": "error",
1664
- "react/no-missing-key": "error",
1665
- "react/no-nested-components": "warn",
1666
- "react/no-redundant-should-component-update": "error",
1667
- "react/no-set-state-in-component-did-mount": "warn",
1668
- "react/no-set-state-in-component-did-update": "warn",
1669
- "react/no-set-state-in-component-will-update": "warn",
1670
- "react/no-string-refs": "error",
1671
- "react/no-unsafe-component-will-mount": "warn",
1672
- "react/no-unsafe-component-will-receive-props": "warn",
1673
- "react/no-unsafe-component-will-update": "warn",
1674
- "react/no-unstable-context-value": "error",
1675
- "react/no-unstable-default-props": "error",
1676
- "react/no-unused-class-component-members": "warn",
1677
- "react/no-unused-state": "warn",
1678
- "react/no-useless-fragment": "warn",
1679
- "react/prefer-destructuring-assignment": "warn",
1680
- "react/prefer-shorthand-boolean": "warn",
1681
- "react/prefer-shorthand-fragment": "warn",
1682
- ...isTypeAware ? {
1683
- "react/no-leaked-conditional-rendering": "warn"
1389
+ args: "none",
1390
+ caughtErrors: "none",
1391
+ ignoreRestSiblings: true,
1392
+ vars: "all",
1393
+ varsIgnorePattern: "^(\\$\\$Props$|\\$\\$Events$|\\$\\$Slots$)"
1394
+ }
1395
+ ],
1396
+ "svelte/comment-directive": "error",
1397
+ "svelte/no-at-debug-tags": "warn",
1398
+ "svelte/no-at-html-tags": "error",
1399
+ "svelte/no-dupe-else-if-blocks": "error",
1400
+ "svelte/no-dupe-style-properties": "error",
1401
+ "svelte/no-dupe-use-directives": "error",
1402
+ "svelte/no-dynamic-slot-name": "error",
1403
+ "svelte/no-export-load-in-svelte-module-in-kit-pages": "error",
1404
+ "svelte/no-inner-declarations": "error",
1405
+ "svelte/no-not-function-handler": "error",
1406
+ "svelte/no-object-in-text-mustaches": "error",
1407
+ "svelte/no-reactive-functions": "error",
1408
+ "svelte/no-reactive-literals": "error",
1409
+ "svelte/no-shorthand-style-property-overrides": "error",
1410
+ "svelte/no-unknown-style-directive-property": "error",
1411
+ "svelte/no-unused-svelte-ignore": "error",
1412
+ "svelte/no-useless-mustaches": "error",
1413
+ "svelte/require-store-callbacks-use-set-param": "error",
1414
+ "svelte/system": "error",
1415
+ "svelte/valid-each-key": "error",
1416
+ "unused-imports/no-unused-vars": [
1417
+ "error",
1418
+ {
1419
+ args: "after-used",
1420
+ argsIgnorePattern: "^_",
1421
+ vars: "all",
1422
+ varsIgnorePattern: "^(_|\\$\\$Props$|\\$\\$Events$|\\$\\$Slots$)"
1423
+ }
1424
+ ],
1425
+ ...stylistic2 ? {
1426
+ "style/indent": "off",
1427
+ // superseded by svelte/indent
1428
+ "style/no-trailing-spaces": "off",
1429
+ // superseded by svelte/no-trailing-spaces
1430
+ "svelte/derived-has-same-inputs-outputs": "error",
1431
+ "svelte/html-closing-bracket-spacing": "error",
1432
+ "svelte/html-quotes": ["error", { prefer: quotes }],
1433
+ "svelte/indent": [
1434
+ "error",
1435
+ { alignAttributesVertically: true, indent }
1436
+ ],
1437
+ "svelte/mustache-spacing": "error",
1438
+ "svelte/no-spaces-around-equal-signs-in-attribute": "error",
1439
+ "svelte/no-trailing-spaces": "error",
1440
+ "svelte/spaced-html-comment": "error"
1684
1441
  } : {},
1685
- // overrides
1686
1442
  ...overrides
1687
1443
  }
1688
1444
  }
1689
1445
  ];
1690
1446
  }
1691
1447
 
1692
- // src/configs/unocss.ts
1693
- async function unocss(options = {}) {
1694
- const { attributify = true, strict = false } = options;
1695
- await ensurePackages(["@unocss/eslint-plugin"]);
1696
- const [pluginUnoCSS] = await Promise.all([
1697
- interopDefault(import("@unocss/eslint-plugin"))
1698
- ]);
1448
+ // src/configs/tailwindcss.ts
1449
+ async function tailwindcss(options = {}) {
1450
+ const { overrides } = options;
1451
+ await ensurePackages(["eslint-plugin-tailwindcss"]);
1452
+ const pluginTailwindcss = await interopDefault(
1453
+ import("eslint-plugin-tailwindcss")
1454
+ );
1699
1455
  return [
1700
1456
  {
1701
- name: "coderwyd/unocss/rules",
1457
+ name: "coderwyd/tailwindcss/rules",
1702
1458
  plugins: {
1703
- unocss: pluginUnoCSS
1459
+ tailwindcss: pluginTailwindcss
1704
1460
  },
1705
1461
  rules: {
1706
- "unocss/order": "warn",
1707
- ...attributify ? {
1708
- "unocss/order-attributify": "warn"
1709
- } : {},
1710
- ...strict ? {
1711
- "unocss/blocklist": "error"
1712
- } : {}
1462
+ "tailwindcss/classnames-order": "warn",
1463
+ "tailwindcss/enforces-negative-arbitrary-values": "warn",
1464
+ "tailwindcss/enforces-shorthand": "warn",
1465
+ "tailwindcss/migration-from-tailwind-2": "warn",
1466
+ "tailwindcss/no-arbitrary-value": "off",
1467
+ "tailwindcss/no-contradicting-classname": "warn",
1468
+ "tailwindcss/no-custom-classname": "off",
1469
+ "tailwindcss/no-unnecessary-arbitrary-value": "warn",
1470
+ ...overrides
1713
1471
  }
1714
1472
  }
1715
1473
  ];
1716
1474
  }
1717
1475
 
1718
- // src/configs/formatter.ts
1719
- async function formatter(options = {}, stylistic2 = {}) {
1720
- const { css, graphql, html, markdown, toml, yaml } = options === true ? {
1721
- css: true,
1722
- graphql: true,
1723
- html: true,
1724
- markdown: true,
1725
- toml: true,
1726
- yaml: true
1727
- } : options;
1728
- const { indent, quotes, semi } = {
1729
- ...StylisticConfigDefaults,
1730
- ...stylistic2
1476
+ // src/configs/test.ts
1477
+ var _pluginTest;
1478
+ async function test(options = {}) {
1479
+ const { files = GLOB_TESTS, isInEditor: isInEditor2 = false, overrides = {} } = options;
1480
+ const [pluginVitest, pluginNoOnlyTests] = await Promise.all([
1481
+ interopDefault(import("@vitest/eslint-plugin")),
1482
+ // @ts-expect-error missing types
1483
+ interopDefault(import("eslint-plugin-no-only-tests"))
1484
+ ]);
1485
+ _pluginTest = _pluginTest || {
1486
+ ...pluginVitest,
1487
+ rules: {
1488
+ ...pluginVitest.rules,
1489
+ // extend `test/no-only-tests` rule
1490
+ ...pluginNoOnlyTests.rules
1491
+ }
1731
1492
  };
1732
- const prettierOptions = Object.assign(
1493
+ return [
1733
1494
  {
1734
- endOfLine: "auto",
1735
- printWidth: 80,
1736
- semi,
1737
- singleQuote: quotes === "single",
1738
- tabWidth: typeof indent === "number" ? indent : 2,
1739
- trailingComma: "all",
1740
- useTabs: indent === "tab"
1741
- },
1742
- typeof options === "boolean" ? {} : options.prettierOptions || {}
1743
- );
1744
- await ensurePackages(["eslint-plugin-format"]);
1745
- const pluginFormat = await interopDefault(import("eslint-plugin-format"));
1746
- function createPrettierFormatter(files, parser, plugins) {
1747
- const rules = {
1748
- ...prettierOptions,
1749
- parser
1750
- };
1751
- const markdownRules = {
1752
- printWidth: 120,
1753
- ...rules,
1754
- embeddedLanguageFormatting: "off"
1755
- };
1756
- if (plugins?.length)
1757
- rules.plugins = [...rules.plugins || [], ...plugins];
1758
- const config = {
1759
- files,
1760
- languageOptions: {
1761
- parser: parserPlain
1762
- },
1763
- name: `coderwyd/formatter/${parser}`,
1495
+ name: "coderwyd/test/setup",
1764
1496
  plugins: {
1765
- format: pluginFormat
1766
- },
1767
- rules: {
1768
- "format/prettier": [
1769
- "warn",
1770
- parser === "markdown" ? markdownRules : rules
1771
- ]
1497
+ test: _pluginTest
1772
1498
  }
1773
- };
1774
- return config;
1775
- }
1776
- const configs2 = [
1499
+ },
1777
1500
  {
1778
- name: "coderwyd/formatter/setup",
1779
- plugins: {
1780
- format: pluginFormat
1501
+ files,
1502
+ name: "coderwyd/test/rules",
1503
+ rules: {
1504
+ "node/prefer-global/process": "off",
1505
+ "test/consistent-test-it": [
1506
+ "error",
1507
+ { fn: "it", withinDescribe: "it" }
1508
+ ],
1509
+ "test/no-identical-title": "error",
1510
+ "test/no-import-node-test": "error",
1511
+ "test/no-only-tests": isInEditor2 ? "off" : "error",
1512
+ "test/prefer-hooks-in-order": "error",
1513
+ "test/prefer-lowercase-title": "error",
1514
+ "ts/explicit-function-return-type": "off",
1515
+ "unicorn/consistent-function-scoping": "off",
1516
+ ...overrides
1781
1517
  }
1782
1518
  }
1783
1519
  ];
1784
- if (html) {
1785
- const htmlConfig = createPrettierFormatter([GLOB_HTML], "html");
1786
- configs2.push(htmlConfig);
1787
- }
1788
- if (css) {
1789
- const cssConfig = createPrettierFormatter([GLOB_CSS, GLOB_POSTCSS], "css");
1790
- const scssConfig = createPrettierFormatter([GLOB_SCSS], "scss");
1791
- const lessConfig = createPrettierFormatter([GLOB_LESS], "less");
1792
- configs2.push(cssConfig, scssConfig, lessConfig);
1793
- }
1794
- if (markdown) {
1795
- const markdownConfig = createPrettierFormatter([GLOB_MARKDOWN], "markdown");
1796
- configs2.push(markdownConfig);
1797
- }
1798
- if (graphql) {
1799
- const graphqlConfig = createPrettierFormatter([GLOB_GRAPHQL], "graphql");
1800
- configs2.push(graphqlConfig);
1801
- }
1802
- if (yaml) {
1803
- const yamlConfig = createPrettierFormatter([GLOB_YAML], "yaml");
1804
- configs2.push(yamlConfig);
1805
- }
1806
- if (toml) {
1807
- await ensurePackages(["@toml-tools/parser", "prettier-plugin-toml"]);
1808
- const tomlConfig = createPrettierFormatter([GLOB_TOML], "toml", [
1809
- "prettier-plugin-toml"
1810
- ]);
1811
- configs2.push(tomlConfig);
1812
- }
1813
- return configs2;
1814
1520
  }
1815
1521
 
1816
- // src/configs/svelte.ts
1817
- async function svelte(options = {}) {
1818
- const { files = [GLOB_SVELTE], overrides = {}, stylistic: stylistic2 = true } = options;
1819
- const {
1820
- indent = 2,
1821
- quotes = "single"
1822
- } = typeof stylistic2 === "boolean" ? {} : stylistic2;
1823
- await ensurePackages(["eslint-plugin-svelte"]);
1824
- const [pluginSvelte, parserSvelte] = await Promise.all([
1825
- interopDefault(import("eslint-plugin-svelte")),
1826
- interopDefault(import("svelte-eslint-parser"))
1522
+ // src/configs/typescript.ts
1523
+ var import_node_process3 = __toESM(require("process"), 1);
1524
+ async function typescript(options = {}) {
1525
+ const { componentExts = [], overrides = {}, overridesTypeAware = {}, parserOptions = {} } = options;
1526
+ const files = options.files ?? [
1527
+ GLOB_TS,
1528
+ GLOB_TSX,
1529
+ ...componentExts.map((ext) => `**/*.${ext}`)
1530
+ ];
1531
+ const filesTypeAware = options.filesTypeAware ?? [GLOB_TS, GLOB_TSX];
1532
+ const ignoresTypeAware = options.ignoresTypeAware ?? [
1533
+ `${GLOB_MARKDOWN}/**`,
1534
+ GLOB_ASTRO_TS
1535
+ ];
1536
+ const tsconfigPath = options.tsconfigPath;
1537
+ const isTypeAware = !!tsconfigPath;
1538
+ const typeAwareRules = {
1539
+ "dot-notation": "off",
1540
+ "no-implied-eval": "off",
1541
+ "ts/await-thenable": "error",
1542
+ "ts/dot-notation": ["error", { allowKeywords: true }],
1543
+ "ts/no-floating-promises": "error",
1544
+ "ts/no-for-in-array": "error",
1545
+ "ts/no-implied-eval": "error",
1546
+ "ts/no-misused-promises": "error",
1547
+ "ts/no-unnecessary-type-assertion": "error",
1548
+ "ts/no-unsafe-argument": "error",
1549
+ "ts/no-unsafe-assignment": "error",
1550
+ "ts/no-unsafe-call": "error",
1551
+ "ts/no-unsafe-member-access": "error",
1552
+ "ts/no-unsafe-return": "error",
1553
+ "ts/promise-function-async": "error",
1554
+ "ts/restrict-plus-operands": "error",
1555
+ "ts/restrict-template-expressions": "error",
1556
+ "ts/return-await": "error",
1557
+ "ts/strict-boolean-expressions": "error",
1558
+ "ts/switch-exhaustiveness-check": "error",
1559
+ "ts/unbound-method": "error"
1560
+ };
1561
+ const [pluginTs, parserTs] = await Promise.all([
1562
+ interopDefault(import("@typescript-eslint/eslint-plugin")),
1563
+ interopDefault(import("@typescript-eslint/parser"))
1827
1564
  ]);
1565
+ function makeParser(typeAware, files2, ignores2) {
1566
+ return {
1567
+ files: files2,
1568
+ ...ignores2 ? { ignores: ignores2 } : {},
1569
+ languageOptions: {
1570
+ parser: parserTs,
1571
+ parserOptions: {
1572
+ extraFileExtensions: componentExts.map((ext) => `.${ext}`),
1573
+ sourceType: "module",
1574
+ ...typeAware ? {
1575
+ projectService: {
1576
+ allowDefaultProject: ["./*.js"],
1577
+ defaultProject: tsconfigPath
1578
+ },
1579
+ tsconfigRootDir: import_node_process3.default.cwd()
1580
+ } : {},
1581
+ ...parserOptions
1582
+ }
1583
+ },
1584
+ name: `coderwyd/typescript/${typeAware ? "type-aware-parser" : "parser"}`
1585
+ };
1586
+ }
1828
1587
  return [
1829
1588
  {
1830
- name: "coderwyd/svelte/setup",
1589
+ // Install the plugins without globs, so they can be configured separately.
1590
+ name: "coderwyd/typescript/setup",
1831
1591
  plugins: {
1832
- svelte: pluginSvelte
1592
+ antfu: import_eslint_plugin_antfu.default,
1593
+ ts: pluginTs
1833
1594
  }
1834
1595
  },
1596
+ // assign type-aware parser for type-aware files and type-unaware parser for the rest
1597
+ ...isTypeAware ? [
1598
+ makeParser(false, files),
1599
+ makeParser(true, filesTypeAware, ignoresTypeAware)
1600
+ ] : [makeParser(false, files)],
1835
1601
  {
1836
1602
  files,
1837
- languageOptions: {
1838
- parser: parserSvelte,
1839
- parserOptions: {
1840
- extraFileExtensions: [".svelte"],
1841
- parser: options.typescript ? await interopDefault(
1842
- import("@typescript-eslint/parser")
1843
- ) : null
1844
- }
1845
- },
1846
- name: "coderwyd/svelte/rules",
1847
- processor: pluginSvelte.processors[".svelte"],
1603
+ name: "coderwyd/typescript/rules",
1848
1604
  rules: {
1849
- "import/no-mutable-exports": "off",
1850
- "no-undef": "off",
1851
- // incompatible with most recent (attribute-form) generic types RFC
1852
- "no-unused-vars": [
1605
+ ...renameRules(
1606
+ pluginTs.configs["eslint-recommended"].overrides[0].rules,
1607
+ { "@typescript-eslint": "ts" }
1608
+ ),
1609
+ ...renameRules(pluginTs.configs.strict.rules, {
1610
+ "@typescript-eslint": "ts"
1611
+ }),
1612
+ "no-dupe-class-members": "off",
1613
+ "no-redeclare": "off",
1614
+ "no-use-before-define": "off",
1615
+ "no-useless-constructor": "off",
1616
+ "ts/ban-ts-comment": [
1853
1617
  "error",
1854
- {
1855
- args: "none",
1856
- caughtErrors: "none",
1857
- ignoreRestSiblings: true,
1858
- vars: "all",
1859
- varsIgnorePattern: "^(\\$\\$Props$|\\$\\$Events$|\\$\\$Slots$)"
1860
- }
1618
+ { "ts-expect-error": "allow-with-description" }
1861
1619
  ],
1862
- "svelte/comment-directive": "error",
1863
- "svelte/no-at-debug-tags": "warn",
1864
- "svelte/no-at-html-tags": "error",
1865
- "svelte/no-dupe-else-if-blocks": "error",
1866
- "svelte/no-dupe-style-properties": "error",
1867
- "svelte/no-dupe-use-directives": "error",
1868
- "svelte/no-dynamic-slot-name": "error",
1869
- "svelte/no-export-load-in-svelte-module-in-kit-pages": "error",
1870
- "svelte/no-inner-declarations": "error",
1871
- "svelte/no-not-function-handler": "error",
1872
- "svelte/no-object-in-text-mustaches": "error",
1873
- "svelte/no-reactive-functions": "error",
1874
- "svelte/no-reactive-literals": "error",
1875
- "svelte/no-shorthand-style-property-overrides": "error",
1876
- "svelte/no-unknown-style-directive-property": "error",
1877
- "svelte/no-unused-svelte-ignore": "error",
1878
- "svelte/no-useless-mustaches": "error",
1879
- "svelte/require-store-callbacks-use-set-param": "error",
1880
- "svelte/system": "error",
1881
- "svelte/valid-each-key": "error",
1882
- "unused-imports/no-unused-vars": [
1620
+ "ts/consistent-type-definitions": ["error", "interface"],
1621
+ "ts/consistent-type-imports": [
1622
+ "error",
1623
+ { disallowTypeAnnotations: false, prefer: "type-imports" }
1624
+ ],
1625
+ "ts/method-signature-style": ["error", "property"],
1626
+ // https://www.totaltypescript.com/method-shorthand-syntax-considered-harmful
1627
+ "ts/no-dupe-class-members": "error",
1628
+ "ts/no-dynamic-delete": "off",
1629
+ "ts/no-empty-object-type": [
1883
1630
  "error",
1884
1631
  {
1885
- args: "after-used",
1886
- argsIgnorePattern: "^_",
1887
- vars: "all",
1888
- varsIgnorePattern: "^(_|\\$\\$Props$|\\$\\$Events$|\\$\\$Slots$)"
1632
+ allowInterfaces: "with-single-extends",
1633
+ // interface Derived extends Base {}
1634
+ allowObjectTypes: "never",
1635
+ allowWithName: "Props$"
1889
1636
  }
1890
1637
  ],
1891
- ...stylistic2 ? {
1892
- "style/indent": "off",
1893
- // superseded by svelte/indent
1894
- "style/no-trailing-spaces": "off",
1895
- // superseded by svelte/no-trailing-spaces
1896
- "svelte/derived-has-same-inputs-outputs": "error",
1897
- "svelte/html-closing-bracket-spacing": "error",
1898
- "svelte/html-quotes": ["error", { prefer: quotes }],
1899
- "svelte/indent": [
1900
- "error",
1901
- { alignAttributesVertically: true, indent }
1902
- ],
1903
- "svelte/mustache-spacing": "error",
1904
- "svelte/no-spaces-around-equal-signs-in-attribute": "error",
1905
- "svelte/no-trailing-spaces": "error",
1906
- "svelte/spaced-html-comment": "error"
1907
- } : {},
1638
+ "ts/no-explicit-any": "off",
1639
+ "ts/no-extraneous-class": "off",
1640
+ "ts/no-import-type-side-effects": "error",
1641
+ "ts/no-invalid-void-type": "off",
1642
+ "ts/no-non-null-assertion": "off",
1643
+ "ts/no-redeclare": "error",
1644
+ "ts/no-require-imports": "error",
1645
+ "ts/no-unused-vars": "off",
1646
+ "ts/no-use-before-define": [
1647
+ "error",
1648
+ { classes: false, functions: false, variables: true }
1649
+ ],
1650
+ "ts/no-useless-constructor": "off",
1651
+ "ts/no-wrapper-object-types": "error",
1652
+ "ts/triple-slash-reference": "off",
1653
+ "ts/unified-signatures": "off",
1908
1654
  ...overrides
1909
1655
  }
1910
- }
1656
+ },
1657
+ ...isTypeAware ? [
1658
+ {
1659
+ files: filesTypeAware,
1660
+ ignores: ignoresTypeAware,
1661
+ name: "coderwyd/typescript/rules-type-aware",
1662
+ rules: {
1663
+ ...typeAwareRules,
1664
+ ...overridesTypeAware
1665
+ }
1666
+ }
1667
+ ] : []
1911
1668
  ];
1912
1669
  }
1913
1670
 
1914
- // src/configs/tailwindcss.ts
1915
- async function tailwindcss(options = {}) {
1916
- const { overrides } = options;
1917
- await ensurePackages(["eslint-plugin-tailwindcss"]);
1918
- const pluginTailwindcss = await interopDefault(
1919
- import("eslint-plugin-tailwindcss")
1920
- );
1671
+ // src/configs/unicorn.ts
1672
+ function unicorn() {
1921
1673
  return [
1922
1674
  {
1923
- name: "coderwyd/tailwindcss/rules",
1675
+ name: "coderwyd/unicorn/rules",
1924
1676
  plugins: {
1925
- tailwindcss: pluginTailwindcss
1677
+ unicorn: import_eslint_plugin_unicorn.default
1926
1678
  },
1927
1679
  rules: {
1928
- "tailwindcss/classnames-order": "warn",
1929
- "tailwindcss/enforces-negative-arbitrary-values": "warn",
1930
- "tailwindcss/enforces-shorthand": "warn",
1931
- "tailwindcss/migration-from-tailwind-2": "warn",
1932
- "tailwindcss/no-arbitrary-value": "off",
1933
- "tailwindcss/no-contradicting-classname": "warn",
1934
- "tailwindcss/no-custom-classname": "off",
1935
- "tailwindcss/no-unnecessary-arbitrary-value": "warn",
1936
- ...overrides
1937
- }
1938
- }
1939
- ];
1940
- }
1941
-
1942
- // src/configs/command.ts
1943
- var import_config = __toESM(require("eslint-plugin-command/config"), 1);
1944
- function command() {
1945
- return [
1946
- {
1947
- ...(0, import_config.default)(),
1948
- name: "coderwyd/command/rules"
1680
+ // 'unicorn/better-regex': 'error',
1681
+ "unicorn/catch-error-name": "error",
1682
+ "unicorn/consistent-empty-array-spread": "error",
1683
+ "unicorn/consistent-function-scoping": ["error", { checkArrowFunctions: false }],
1684
+ "unicorn/custom-error-definition": "error",
1685
+ "unicorn/error-message": "error",
1686
+ // 'unicorn/explicit-length-check': 'error',
1687
+ // 'unicorn/filename-case': [
1688
+ // 'error',
1689
+ // {
1690
+ // cases: { kebabCase: true, pascalCase: true },
1691
+ // ignore: [/^[A-Z]+\..*$/],
1692
+ // },
1693
+ "unicorn/escape-case": "error",
1694
+ // ],
1695
+ "unicorn/new-for-builtins": "error",
1696
+ // 'unicorn/no-array-callback-reference': 'error',
1697
+ "unicorn/no-array-method-this-argument": "error",
1698
+ "unicorn/no-array-push-push": "error",
1699
+ "unicorn/no-await-in-promise-methods": "error",
1700
+ "unicorn/no-console-spaces": "error",
1701
+ "unicorn/no-for-loop": "error",
1702
+ "unicorn/no-hex-escape": "error",
1703
+ "unicorn/no-instanceof-array": "error",
1704
+ "unicorn/no-invalid-remove-event-listener": "error",
1705
+ "unicorn/no-length-as-slice-end": "error",
1706
+ "unicorn/no-lonely-if": "error",
1707
+ "unicorn/no-new-array": "error",
1708
+ "unicorn/no-new-buffer": "error",
1709
+ "unicorn/no-single-promise-in-promise-methods": "error",
1710
+ "unicorn/no-static-only-class": "error",
1711
+ "unicorn/no-unnecessary-await": "error",
1712
+ "unicorn/no-zero-fractions": `error`,
1713
+ "unicorn/prefer-add-event-listener": "error",
1714
+ "unicorn/prefer-array-find": "error",
1715
+ "unicorn/prefer-array-flat-map": "error",
1716
+ "unicorn/prefer-array-index-of": "error",
1717
+ "unicorn/prefer-array-some": "error",
1718
+ "unicorn/prefer-at": "error",
1719
+ "unicorn/prefer-blob-reading-methods": "error",
1720
+ "unicorn/prefer-date-now": "error",
1721
+ "unicorn/prefer-dom-node-append": "error",
1722
+ "unicorn/prefer-dom-node-dataset": "error",
1723
+ "unicorn/prefer-dom-node-remove": "error",
1724
+ "unicorn/prefer-dom-node-text-content": "error",
1725
+ "unicorn/prefer-includes": "error",
1726
+ "unicorn/prefer-keyboard-event-key": "error",
1727
+ "unicorn/prefer-math-trunc": "error",
1728
+ "unicorn/prefer-modern-dom-apis": "error",
1729
+ "unicorn/prefer-modern-math-apis": "error",
1730
+ "unicorn/prefer-negative-index": "error",
1731
+ "unicorn/prefer-node-protocol": "error",
1732
+ "unicorn/prefer-number-properties": "error",
1733
+ "unicorn/prefer-optional-catch-binding": "error",
1734
+ "unicorn/prefer-prototype-methods": "error",
1735
+ "unicorn/prefer-query-selector": "error",
1736
+ "unicorn/prefer-reflect-apply": "error",
1737
+ // 'unicorn/prefer-regexp-test': 'error',
1738
+ "unicorn/prefer-string-replace-all": "error",
1739
+ "unicorn/prefer-string-slice": "error",
1740
+ "unicorn/prefer-string-starts-ends-with": "error",
1741
+ "unicorn/prefer-string-trim-start-end": "error",
1742
+ // top level await is not supported in all environments
1743
+ // 'unicorn/prefer-top-level-await': 'error',
1744
+ "unicorn/prefer-type-error": "error",
1745
+ "unicorn/throw-new-error": "error"
1746
+ }
1949
1747
  }
1950
1748
  ];
1951
1749
  }
1952
1750
 
1953
- // src/configs/regexp.ts
1954
- var import_eslint_plugin_regexp = require("eslint-plugin-regexp");
1955
- function regexp(options = {}) {
1956
- const config = import_eslint_plugin_regexp.configs["flat/recommended"];
1957
- const rules = {
1958
- ...config.rules
1959
- };
1960
- if (options.level === "warn") {
1961
- Object.keys(rules).forEach((key) => {
1962
- if (rules[key] === "error")
1963
- rules[key] = "warn";
1964
- });
1965
- }
1751
+ // src/configs/unocss.ts
1752
+ async function unocss(options = {}) {
1753
+ const { attributify = true, strict = false } = options;
1754
+ await ensurePackages(["@unocss/eslint-plugin"]);
1755
+ const [pluginUnoCSS] = await Promise.all([
1756
+ interopDefault(import("@unocss/eslint-plugin"))
1757
+ ]);
1966
1758
  return [
1967
1759
  {
1968
- ...config,
1969
- name: "coderwyd/regexp/rules",
1760
+ name: "coderwyd/unocss/rules",
1761
+ plugins: {
1762
+ unocss: pluginUnoCSS
1763
+ },
1970
1764
  rules: {
1971
- ...rules,
1972
- ...options.overrides
1765
+ "unocss/order": "warn",
1766
+ ...attributify ? {
1767
+ "unocss/order-attributify": "warn"
1768
+ } : {},
1769
+ ...strict ? {
1770
+ "unocss/blocklist": "error"
1771
+ } : {}
1973
1772
  }
1974
1773
  }
1975
1774
  ];
1976
1775
  }
1977
1776
 
1978
- // src/configs/jsx.ts
1979
- function jsx() {
1777
+ // src/configs/vue.ts
1778
+ var import_eslint_merge_processors = require("eslint-merge-processors");
1779
+ async function vue(options = {}) {
1780
+ const { files = [GLOB_VUE], overrides = {}, stylistic: stylistic2 = true } = options;
1781
+ const sfcBlocks = options.sfcBlocks === true ? {} : options.sfcBlocks ?? {};
1782
+ const { indent = 2 } = typeof stylistic2 === "boolean" ? {} : stylistic2;
1783
+ const [pluginVue, parserVue, processorVueBlocks] = await Promise.all([
1784
+ interopDefault(import("eslint-plugin-vue")),
1785
+ interopDefault(import("vue-eslint-parser")),
1786
+ interopDefault(import("eslint-processor-vue-blocks"))
1787
+ ]);
1788
+ const isVue3 = getVueVersion() === 3;
1789
+ const configKeys = isVue3 ? ["vue3-essential", "vue3-strongly-recommended", "vue3-recommended"] : ["essential", "strongly-recommended", "recommended"];
1790
+ const vueRules = configKeys.reduce((preRules, key) => {
1791
+ const config = pluginVue.configs[key];
1792
+ return {
1793
+ ...preRules,
1794
+ ...config.rules
1795
+ };
1796
+ }, {});
1980
1797
  return [
1981
1798
  {
1982
- files: [GLOB_JSX, GLOB_TSX],
1799
+ // This allows Vue plugin to work with auto imports
1800
+ // https://github.com/vuejs/eslint-plugin-vue/pull/2422
1801
+ languageOptions: {
1802
+ globals: {
1803
+ computed: "readonly",
1804
+ defineEmits: "readonly",
1805
+ defineExpose: "readonly",
1806
+ defineProps: "readonly",
1807
+ onMounted: "readonly",
1808
+ onUnmounted: "readonly",
1809
+ reactive: "readonly",
1810
+ ref: "readonly",
1811
+ shallowReactive: "readonly",
1812
+ shallowRef: "readonly",
1813
+ toRef: "readonly",
1814
+ toRefs: "readonly",
1815
+ watch: "readonly",
1816
+ watchEffect: "readonly"
1817
+ }
1818
+ },
1819
+ name: "coderwyd/vue/setup",
1820
+ plugins: {
1821
+ vue: pluginVue
1822
+ }
1823
+ },
1824
+ {
1825
+ files,
1983
1826
  languageOptions: {
1827
+ parser: parserVue,
1984
1828
  parserOptions: {
1985
1829
  ecmaFeatures: {
1986
1830
  jsx: true
1987
- }
1831
+ },
1832
+ extraFileExtensions: [".vue"],
1833
+ parser: options.typescript ? await interopDefault(
1834
+ import("@typescript-eslint/parser")
1835
+ ) : null,
1836
+ sourceType: "module"
1988
1837
  }
1989
1838
  },
1990
- name: "coderwyd/jsx/setup"
1839
+ name: "coderwyd/vue/rules",
1840
+ processor: sfcBlocks === false ? pluginVue.processors[".vue"] : (0, import_eslint_merge_processors.mergeProcessors)([
1841
+ pluginVue.processors[".vue"],
1842
+ processorVueBlocks({
1843
+ ...sfcBlocks,
1844
+ blocks: {
1845
+ styles: true,
1846
+ ...sfcBlocks.blocks
1847
+ }
1848
+ })
1849
+ ]),
1850
+ rules: {
1851
+ ...pluginVue.configs.base.rules,
1852
+ ...vueRules,
1853
+ "node/prefer-global/process": "off",
1854
+ "vue/block-order": [
1855
+ "error",
1856
+ {
1857
+ order: isVue3 ? ["script", "template", "style"] : ["template", "script", "style"]
1858
+ }
1859
+ ],
1860
+ // 'vue/component-api-style': ['warn', ['script-setup', 'composition']],
1861
+ "vue/component-name-in-template-casing": ["error", "PascalCase"],
1862
+ "vue/component-options-name-casing": ["error", "PascalCase"],
1863
+ // this is deprecated
1864
+ "vue/component-tags-order": "off",
1865
+ "vue/custom-event-name-casing": ["error", "camelCase"],
1866
+ // 'vue/define-emits-declaration': ['warn', 'type-based'],
1867
+ "vue/define-macros-order": [
1868
+ "error",
1869
+ {
1870
+ order: [
1871
+ "defineOptions",
1872
+ "defineProps",
1873
+ "defineEmits",
1874
+ "defineSlots"
1875
+ ]
1876
+ }
1877
+ ],
1878
+ // 'vue/define-props-declaration': ['warn', 'type-based'],
1879
+ "vue/dot-location": ["error", "property"],
1880
+ "vue/dot-notation": ["error", { allowKeywords: true }],
1881
+ "vue/eqeqeq": ["error", "smart"],
1882
+ "vue/html-indent": ["error", indent],
1883
+ "vue/html-quotes": ["error", "double"],
1884
+ "vue/html-self-closing": [
1885
+ "error",
1886
+ {
1887
+ html: {
1888
+ component: "always",
1889
+ normal: "always",
1890
+ void: "any"
1891
+ },
1892
+ math: "always",
1893
+ svg: "always"
1894
+ }
1895
+ ],
1896
+ "vue/max-attributes-per-line": "off",
1897
+ "vue/multi-word-component-names": "off",
1898
+ // 'vue/next-tick-style': ['warn', 'promise'],
1899
+ "vue/no-constant-condition": "warn",
1900
+ "vue/no-dupe-keys": "off",
1901
+ "vue/no-duplicate-attr-inheritance": "warn",
1902
+ "vue/no-empty-pattern": "error",
1903
+ "vue/no-extra-parens": ["error", "functions"],
1904
+ "vue/no-irregular-whitespace": "error",
1905
+ "vue/no-loss-of-precision": "error",
1906
+ "vue/no-required-prop-with-default": "warn",
1907
+ "vue/no-restricted-syntax": [
1908
+ "error",
1909
+ "DebuggerStatement",
1910
+ "LabeledStatement",
1911
+ "WithStatement"
1912
+ ],
1913
+ "vue/no-restricted-v-bind": ["error", "/^v-/"],
1914
+ "vue/no-setup-props-reactivity-loss": "off",
1915
+ "vue/no-sparse-arrays": "error",
1916
+ "vue/no-unsupported-features": "warn",
1917
+ "vue/no-unused-emit-declarations": "warn",
1918
+ "vue/no-unused-refs": "error",
1919
+ "vue/no-use-v-else-with-v-for": "error",
1920
+ "vue/no-useless-mustaches": "warn",
1921
+ "vue/no-useless-v-bind": "error",
1922
+ "vue/no-v-html": "off",
1923
+ "vue/no-v-text": "warn",
1924
+ "vue/object-shorthand": [
1925
+ "error",
1926
+ "always",
1927
+ {
1928
+ avoidQuotes: true,
1929
+ ignoreConstructors: false
1930
+ }
1931
+ ],
1932
+ "vue/prefer-define-options": "warn",
1933
+ "vue/prefer-separate-static-class": "error",
1934
+ "vue/prefer-template": "error",
1935
+ "vue/prop-name-casing": ["error", "camelCase"],
1936
+ "vue/require-default-prop": "off",
1937
+ "vue/require-macro-variable-name": [
1938
+ "warn",
1939
+ {
1940
+ defineEmits: "emit",
1941
+ defineProps: "props",
1942
+ defineSlots: "slots",
1943
+ useAttrs: "attrs",
1944
+ useSlots: "slots"
1945
+ }
1946
+ ],
1947
+ "vue/require-prop-types": "off",
1948
+ // 'vue/singleline-html-element-content-newline': 'off',
1949
+ "vue/space-infix-ops": "error",
1950
+ "vue/space-unary-ops": ["error", { nonwords: false, words: true }],
1951
+ "vue/valid-define-options": "warn",
1952
+ ...stylistic2 ? {
1953
+ "vue/array-bracket-spacing": ["error", "never"],
1954
+ "vue/arrow-spacing": ["error", { after: true, before: true }],
1955
+ "vue/block-spacing": ["error", "always"],
1956
+ "vue/block-tag-newline": [
1957
+ "error",
1958
+ {
1959
+ multiline: "always",
1960
+ singleline: "always"
1961
+ }
1962
+ ],
1963
+ "vue/brace-style": [
1964
+ "error",
1965
+ "stroustrup",
1966
+ { allowSingleLine: true }
1967
+ ],
1968
+ "vue/comma-dangle": ["error", "always-multiline"],
1969
+ "vue/comma-spacing": ["error", { after: true, before: false }],
1970
+ "vue/comma-style": ["error", "last"],
1971
+ "vue/html-comment-content-newline": "warn",
1972
+ "vue/html-comment-content-spacing": [
1973
+ "error",
1974
+ "always",
1975
+ {
1976
+ exceptions: ["-"]
1977
+ }
1978
+ ],
1979
+ "vue/key-spacing": [
1980
+ "error",
1981
+ { afterColon: true, beforeColon: false }
1982
+ ],
1983
+ "vue/keyword-spacing": ["error", { after: true, before: true }],
1984
+ "vue/object-curly-newline": "off",
1985
+ "vue/object-curly-spacing": ["error", "always"],
1986
+ "vue/object-property-newline": [
1987
+ "error",
1988
+ { allowMultiplePropertiesPerLine: true }
1989
+ ],
1990
+ "vue/operator-linebreak": ["error", "before"],
1991
+ "vue/padding-line-between-blocks": ["error", "always"],
1992
+ "vue/quote-props": ["error", "consistent-as-needed"],
1993
+ "vue/space-in-parens": ["error", "never"],
1994
+ "vue/template-curly-spacing": "error"
1995
+ } : {},
1996
+ ...overrides
1997
+ }
1991
1998
  }
1992
1999
  ];
1993
2000
  }
@@ -2170,6 +2177,7 @@ async function defineConfig(options = {}, ...userConfigs) {
2170
2177
  )
2171
2178
  );
2172
2179
  }
2180
+ configs2.push(disables());
2173
2181
  if ("files" in options) {
2174
2182
  throw new Error('[@coderwyd/eslint-config] The first argument should not contain the "files" property as the options are supposed to be global. Place it in the second or later config instead.');
2175
2183
  }