|
| 1 | +const { builtinModules } = require('node:module') |
1 | 2 | const DOMGlobals = ['window', 'document']
|
2 | 3 | const NodeGlobals = ['module', 'require']
|
3 | 4 |
|
| 5 | +const banConstEnum = { |
| 6 | + selector: 'TSEnumDeclaration[const=true]', |
| 7 | + message: |
| 8 | + 'Please use non-const enums. This project automatically inlines enums.', |
| 9 | +} |
| 10 | + |
| 11 | +/** |
| 12 | + * @type {import('eslint-define-config').ESLintConfig} |
| 13 | + */ |
4 | 14 | module.exports = {
|
5 | 15 | parser: '@typescript-eslint/parser',
|
6 | 16 | parserOptions: {
|
7 |
| - sourceType: 'module' |
| 17 | + sourceType: 'module', |
8 | 18 | },
|
9 |
| - plugins: ['jest'], |
| 19 | + plugins: ['jest', 'import', '@typescript-eslint'], |
10 | 20 | rules: {
|
11 | 21 | 'no-debugger': 'error',
|
12 |
| - 'no-unused-vars': [ |
13 |
| - 'error', |
14 |
| - // we are only using this rule to check for unused arguments since TS |
15 |
| - // catches unused variables but not args. |
16 |
| - { varsIgnorePattern: '.*', args: 'none' } |
17 |
| - ], |
| 22 | + 'no-console': ['error', { allow: ['warn', 'error', 'info'] }], |
18 | 23 | // most of the codebase are expected to be env agnostic
|
19 | 24 | 'no-restricted-globals': ['error', ...DOMGlobals, ...NodeGlobals],
|
20 | 25 |
|
21 | 26 | 'no-restricted-syntax': [
|
22 | 27 | 'error',
|
| 28 | + banConstEnum, |
23 | 29 | // since we target ES2015 for baseline support, we need to forbid object
|
24 | 30 | // rest spread usage in destructure as it compiles into a verbose helper.
|
25 | 31 | 'ObjectPattern > RestElement',
|
26 | 32 | // tsc compiles assignment spread into Object.assign() calls, but esbuild
|
27 | 33 | // still generates verbose helpers, so spread assignment is also prohiboted
|
28 | 34 | 'ObjectExpression > SpreadElement',
|
29 |
| - 'AwaitExpression' |
30 |
| - ] |
| 35 | + 'AwaitExpression', |
| 36 | + ], |
| 37 | + 'sort-imports': ['error', { ignoreDeclarationSort: true }], |
| 38 | + |
| 39 | + 'import/no-nodejs-modules': [ |
| 40 | + 'error', |
| 41 | + { allow: builtinModules.map(mod => `node:${mod}`) }, |
| 42 | + ], |
| 43 | + // This rule enforces the preference for using '@ts-expect-error' comments in TypeScript |
| 44 | + // code to indicate intentional type errors, improving code clarity and maintainability. |
| 45 | + '@typescript-eslint/prefer-ts-expect-error': 'error', |
| 46 | + // Enforce the use of 'import type' for importing types |
| 47 | + '@typescript-eslint/consistent-type-imports': [ |
| 48 | + 'error', |
| 49 | + { |
| 50 | + fixStyle: 'inline-type-imports', |
| 51 | + disallowTypeAnnotations: false, |
| 52 | + }, |
| 53 | + ], |
| 54 | + // Enforce the use of top-level import type qualifier when an import only has specifiers with inline type qualifiers |
| 55 | + '@typescript-eslint/no-import-type-side-effects': 'error', |
31 | 56 | },
|
32 | 57 | overrides: [
|
33 | 58 | // tests, no restrictions (runs in Node / jest with jsdom)
|
34 | 59 | {
|
35 | 60 | files: ['**/__tests__/**', 'packages/dts-test/**'],
|
36 | 61 | rules: {
|
| 62 | + 'no-console': 'off', |
37 | 63 | 'no-restricted-globals': 'off',
|
38 | 64 | 'no-restricted-syntax': 'off',
|
39 | 65 | 'jest/no-disabled-tests': 'error',
|
40 |
| - 'jest/no-focused-tests': 'error' |
41 |
| - } |
| 66 | + 'jest/no-focused-tests': 'error', |
| 67 | + }, |
42 | 68 | },
|
43 | 69 | // shared, may be used in any env
|
44 | 70 | {
|
45 |
| - files: ['packages/shared/**'], |
| 71 | + files: ['packages/shared/**', '.eslintrc.cjs'], |
46 | 72 | rules: {
|
47 |
| - 'no-restricted-globals': 'off' |
48 |
| - } |
| 73 | + 'no-restricted-globals': 'off', |
| 74 | + }, |
49 | 75 | },
|
50 | 76 | // Packages targeting DOM
|
51 | 77 | {
|
52 | 78 | files: ['packages/{vue,vue-compat,runtime-dom}/**'],
|
53 | 79 | rules: {
|
54 |
| - 'no-restricted-globals': ['error', ...NodeGlobals] |
55 |
| - } |
| 80 | + 'no-restricted-globals': ['error', ...NodeGlobals], |
| 81 | + }, |
56 | 82 | },
|
57 | 83 | // Packages targeting Node
|
58 | 84 | {
|
59 |
| - files: [ |
60 |
| - 'packages/{compiler-sfc,compiler-ssr,server-renderer,reactivity-transform}/**' |
61 |
| - ], |
| 85 | + files: ['packages/{compiler-sfc,compiler-ssr,server-renderer}/**'], |
62 | 86 | rules: {
|
63 | 87 | 'no-restricted-globals': ['error', ...DOMGlobals],
|
64 |
| - 'no-restricted-syntax': 'off' |
65 |
| - } |
| 88 | + 'no-restricted-syntax': ['error', banConstEnum], |
| 89 | + }, |
66 | 90 | },
|
67 | 91 | // Private package, browser only + no syntax restrictions
|
68 | 92 | {
|
69 | 93 | files: ['packages/template-explorer/**', 'packages/sfc-playground/**'],
|
70 | 94 | rules: {
|
71 | 95 | 'no-restricted-globals': ['error', ...NodeGlobals],
|
72 |
| - 'no-restricted-syntax': 'off' |
73 |
| - } |
| 96 | + 'no-restricted-syntax': ['error', banConstEnum], |
| 97 | + 'no-console': 'off', |
| 98 | + }, |
| 99 | + }, |
| 100 | + // JavaScript files |
| 101 | + { |
| 102 | + files: ['*.js', '*.cjs'], |
| 103 | + rules: { |
| 104 | + // We only do `no-unused-vars` checks for js files, TS files are checked by TypeScript itself. |
| 105 | + 'no-unused-vars': ['error', { vars: 'all', args: 'none' }], |
| 106 | + }, |
74 | 107 | },
|
75 | 108 | // Node scripts
|
76 | 109 | {
|
77 |
| - files: ['scripts/**', '*.{js,ts}', 'packages/**/index.js'], |
| 110 | + files: [ |
| 111 | + 'scripts/**', |
| 112 | + './*.{js,ts}', |
| 113 | + 'packages/*/*.js', |
| 114 | + 'packages/vue/*/*.js', |
| 115 | + ], |
78 | 116 | rules: {
|
79 | 117 | 'no-restricted-globals': 'off',
|
80 |
| - 'no-restricted-syntax': 'off' |
81 |
| - } |
82 |
| - } |
83 |
| - ] |
| 118 | + 'no-restricted-syntax': ['error', banConstEnum], |
| 119 | + 'no-console': 'off', |
| 120 | + }, |
| 121 | + }, |
| 122 | + // Import nodejs modules in compiler-sfc |
| 123 | + { |
| 124 | + files: ['packages/compiler-sfc/src/**'], |
| 125 | + rules: { |
| 126 | + 'import/no-nodejs-modules': ['error', { allow: builtinModules }], |
| 127 | + }, |
| 128 | + }, |
| 129 | + ], |
84 | 130 | }
|
0 commit comments