@mlaursen/eslint-config 12.0.6 → 12.0.8

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.
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sources":["../src/constants.ts","../src/base.ts","../src/jsxA11y.ts","../src/react.ts","../src/scripts.ts","../src/testing.ts","../src/typescript.ts","../src/unicorn.ts","../src/recommended.ts","../src/mui.ts","../src/testing-library.ts","../src/recommendedFrontend.ts","../src/gitignore.ts","../src/index.ts"],"sourcesContent":["export const DEV_WARNING_PROD_ERROR =\n process.env[\"NODE_ENV\"] === \"production\" ? \"error\" : \"warn\";\n\n/**\n * This is a \"temporary\" workaround until autofixable rules can be disabled with\n * a config option because of the \"autofix + format(+ save)?\" behavior. It\n * should be something closer to `DEV_WARN_PROD_ERROR_AND_FIX`\n */\nexport const DEV_OFF_PROD_ERROR =\n process.env[\"NODE_ENV\"] === \"production\" ? \"error\" : \"off\";\n\nexport const BASE_NAME = \"@mlaursen/eslint-config\";\n\nexport const TS_FILES = [\"**/*.{ts,tsx,mts,mtsx}\"];\n\nexport const TEST_FILES = [\n \"**/__tests__/**\",\n \"**/*.{spec,test}.{ts,tsx,js,jsx}\",\n];\n\nexport const JSX_FILES = [\"**/*.{js,mjs,cjs,jsx,mjsx,ts,tsx,mtsx}\"];\n\nexport const VITE_MAIN_FILES = [\"**/main.tsx\"];\n","import eslint from \"@eslint/js\";\nimport { type Linter } from \"eslint\";\nimport { BASE_NAME, DEV_WARNING_PROD_ERROR } from \"./constants.js\";\n\n/**\n * @example\n * ```js\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.base);\n * ```\n */\nexport const base: Linter.Config[] = [\n eslint.configs.recommended,\n {\n name: `${BASE_NAME}/base`,\n rules: {\n // I use typescript instead\n \"no-undef\": \"off\",\n\n // You normally do not want `console.{whatever}` in prod but is fine for\n // development in debugging\n \"no-console\": DEV_WARNING_PROD_ERROR,\n\n \"no-var\": \"error\",\n \"no-use-before-define\": \"warn\",\n\n // I want to enforce all statements to require curly braces even if it\n // could be omitted for consistency\n curly: \"error\",\n\n // Since this is auto-fixable, I like `{ someproperty }` instead of\n // `{ someproperty: someproperty }`\n \"object-shorthand\": [\"error\", \"always\"],\n\n // This is about the same as `object-shorthand`. Only rename if it has to\n // be renamed\n \"no-useless-rename\": [\"error\"],\n\n \"no-eval\": \"error\",\n \"no-alert\": \"error\",\n \"no-lonely-if\": \"error\",\n \"no-else-return\": \"error\",\n eqeqeq: \"error\",\n\n // 100% stylistic, but do not allow `a = b = c = \"whatever\"` / `let a = whatever, b = whatever, c = whatever;`\n // these should be different statements\n \"no-multi-assign\": \"error\",\n \"no-sequences\": \"error\",\n\n // use template strings instead\n \"no-multi-str\": \"error\",\n\n // better to use new variables most of the time\n \"no-param-reassign\": \"error\",\n\n // i'd never hit these, but who trusts other people and AI?\n \"no-return-assign\": \"error\",\n \"no-script-url\": \"error\",\n },\n },\n];\n","import { type Linter } from \"eslint\";\nimport jsxA11yPlugin from \"eslint-plugin-jsx-a11y\";\nimport { BASE_NAME, JSX_FILES, TEST_FILES } from \"./constants.js\";\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.jsxA11y);\n * ```\n */\nexport const jsxA11y: Linter.Config[] = [\n {\n name: `${BASE_NAME}/jsx-a11y`,\n files: JSX_FILES,\n ...jsxA11yPlugin.flatConfigs.recommended,\n rules: {\n ...jsxA11yPlugin.flatConfigs.recommended.rules,\n // I **only** use autoFocus within dialogs which provide the correct\n // context for screen readers.\n \"jsx-a11y/no-autofocus\": \"off\",\n },\n },\n {\n name: `${BASE_NAME}/jsx-a11y/testing`,\n files: TEST_FILES,\n rules: {\n \"jsx-a11y/anchor-has-content\": \"off\",\n \"jsx-a11y/click-events-have-key-events\": \"off\",\n \"jsx-a11y/no-static-element-interactions\": \"off\",\n },\n },\n];\n","import { type Linter } from \"eslint\";\nimport reactPlugin from \"eslint-plugin-react\";\nimport reactHooksPlugin from \"eslint-plugin-react-hooks\";\nimport reactRefreshPlugin from \"eslint-plugin-react-refresh\";\nimport { BASE_NAME, JSX_FILES } from \"./constants.js\";\n\nexport type ReactRefreshConfig = keyof typeof reactRefreshPlugin.configs;\n\nexport interface ReactOptions {\n /**\n * Set to one of the `eslint-plugin-react-refresh` config names to enable.\n *\n * @example Vite\n * ```js\n * configs.react({\n * reactRefresh: \"vite\",\n * })\n * ```\n *\n * @example Next.js\n * ```js\n * configs.react({\n * reactRefresh: \"next\",\n * })\n * ```\n *\n * @example Recommended\n * ```js\n * configs.react({\n * reactRefresh: \"recommended\",\n * })\n * ```\n */\n reactRefresh?: ReactRefreshConfig;\n\n /**\n * Set to `true` to enable the react compiler eslint rules.\n *\n * @defaultValue `false`\n */\n reactCompiler?: boolean;\n}\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.react());\n *\n * // or with react compiler rules enabled\n * export default defineConfig(configs.react(true));\n * ```\n *\n * Enables:\n * - `eslint-plugin-react` with:\n * - flat.recommended\n * - flat['jsx-runtime']\n * - `eslint-plugin-react-hooks` with:\n * - recommended rules\n * - compiler rules (if `true` is provided)\n */\nexport const react = (options: ReactOptions = {}): Linter.Config[] => {\n const { reactRefresh, reactCompiler } = options;\n\n return [\n {\n ...reactPlugin.configs.flat[\"recommended\"],\n name: `${BASE_NAME}/react`,\n files: JSX_FILES,\n settings: {\n react: {\n version: \"detect\",\n },\n },\n rules: {\n ...reactPlugin.configs.flat[\"recommended\"]?.rules,\n ...reactPlugin.configs.flat[\"jsx-runtime\"]?.rules,\n },\n },\n {\n ...reactHooksPlugin.configs.flat.recommended,\n name: `${BASE_NAME}/react-hooks`,\n rules: {\n ...(reactCompiler && reactHooksPlugin.configs.flat.recommended.rules),\n \"react-hooks/rules-of-hooks\": \"error\",\n \"react-hooks/exhaustive-deps\": [\n \"error\",\n {\n additionalHooks: \"(useIsomorphicLayoutEffect)\",\n },\n ],\n },\n },\n ...(reactRefresh\n ? [\n {\n ...reactRefreshPlugin.configs[reactRefresh],\n name: `${BASE_NAME}/react-refresh`,\n ignores: [\"**/test-utils*\", \"**/test-utils/**\"],\n },\n ]\n : []),\n ];\n};\n","import { type Linter } from \"eslint\";\nimport { BASE_NAME } from \"./constants.js\";\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.scripts);\n * ```\n */\nexport const scripts: Linter.Config[] = [\n {\n name: `${BASE_NAME}/scripts`,\n files: [\"scripts/**\"],\n rules: {\n \"no-console\": \"off\",\n },\n },\n];\n","import vitestPlugin from \"@vitest/eslint-plugin\";\nimport { type Linter } from \"eslint\";\nimport jestPlugin from \"eslint-plugin-jest\";\nimport jestDomPlugin from \"eslint-plugin-jest-dom\";\nimport { BASE_NAME, DEV_OFF_PROD_ERROR, TEST_FILES } from \"./constants.js\";\n\nexport type TestFramework = \"jest\" | \"vitest\";\n\nexport interface TestOptions {\n /**\n * @defaultValue `\"vitest\"`\n */\n testFramework?: TestFramework;\n}\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.vitest);\n * ```\n */\nexport const vitest: Linter.Config[] = [\n {\n name: `${BASE_NAME}/vitest`,\n files: TEST_FILES,\n plugins: {\n vitest: vitestPlugin,\n },\n rules: {\n ...vitestPlugin.configs.recommended.rules,\n \"vitest/no-alias-methods\": \"error\",\n \"vitest/no-focused-tests\": DEV_OFF_PROD_ERROR,\n \"vitest/no-disabled-tests\": DEV_OFF_PROD_ERROR,\n \"vitest/no-duplicate-hooks\": \"error\",\n \"vitest/no-standalone-expect\": \"error\",\n \"vitest/prefer-expect-resolves\": \"error\",\n \"vitest/prefer-spy-on\": \"error\",\n \"vitest/prefer-vi-mocked\": \"error\",\n },\n },\n];\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.jest);\n * ```\n */\nexport const jest: Linter.Config[] = [\n {\n name: `${BASE_NAME}/jest`,\n files: TEST_FILES,\n ...jestPlugin.configs[\"flat/recommended\"],\n },\n];\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([\n * ...configs.jest,\n * ...configs.jestDom,\n * ]);\n * ```\n */\nexport const jestDom: Linter.Config[] = [\n {\n name: `${BASE_NAME}/jest-dom`,\n files: TEST_FILES,\n ...jestDomPlugin.configs[\"flat/recommended\"],\n },\n];\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig(configs.testing({ testFramework: \"jest\" }));\n *\n * // or\n * export default defineConfig(configs.testing({ testFramework: \"vitest\" }));\n * ```\n */\nexport const testing = (options: TestOptions = {}): Linter.Config[] => {\n const { testFramework = \"vitest\" } = options;\n\n let config: Linter.Config[];\n switch (testFramework) {\n case \"jest\":\n config = jest;\n break;\n case \"vitest\":\n config = vitest;\n break;\n }\n\n return [...config, ...jestDom];\n};\n","import { type Linter } from \"eslint\";\nimport tseslint from \"typescript-eslint\";\nimport { base } from \"./base.js\";\nimport {\n BASE_NAME,\n TEST_FILES,\n TS_FILES,\n VITE_MAIN_FILES,\n} from \"./constants.js\";\n\nexport interface TypescriptOptions {\n /**\n * This is required when working in monorepos or when the\n * {@link strictTypeChecked} rules are enabled.\n *\n * @example\n * ```js\n * configs.recommended({\n * tsconfigRootDir: import.meta.dirname,\n * })\n * ```\n */\n tsconfigRootDir?: string;\n\n /**\n * The {@link tsconfigRootDir} must be set if this is `true`.\n *\n * @example\n * ```js\n * configs.recommended({\n * tsconfigRootDir: import.meta.dirname,\n * strictTypeChecked: process.env.STRICT_TYPING === \"true\",\n * })\n *\n * @defaultValue `false`\n */\n strictTypeChecked?: boolean;\n}\n\n/**\n * @example\n * ```ts\n * import { configs, gitignore } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([\n * gitignore(import.meta.url),\n * ...configs.typescript(),\n * ]);\n * ```\n */\nexport const typescript = (\n options: TypescriptOptions = {},\n): Linter.Config[] => {\n const { tsconfigRootDir, strictTypeChecked } = options;\n\n const configs: Linter.Config[] = [\n ...base,\n ...tseslint.configs.strict,\n {\n name: `${BASE_NAME}/typescript`,\n files: TS_FILES,\n rules: {\n // I normally do not want unified signatures since it helps improve type\n // inference with function overloading\n \"@typescript-eslint/unified-signatures\": \"off\",\n\n // I prefer specifying when something is used only as a type\n \"@typescript-eslint/consistent-type-imports\": [\n \"error\",\n { fixStyle: \"inline-type-imports\" },\n ],\n\n // I prefer shorthand syntax\n \"@typescript-eslint/array-type\": [\"error\", { default: \"array\" }],\n\n // I prefer using `interface` over `type = {}`\n \"@typescript-eslint/consistent-type-definitions\": [\n \"error\",\n \"interface\",\n ],\n\n // Allow expressions to work with react hooks. Annoying to have to\n // typedef each arrow function in a `useEffect` or `useCallback` when\n // it can be derived.\n \"@typescript-eslint/explicit-function-return-type\": [\n \"error\",\n {\n allowExpressions: true,\n // allow FC definitions for React\n allowTypedFunctionExpressions: true,\n },\n ],\n\n \"@typescript-eslint/no-unused-vars\": [\n \"error\",\n {\n argsIgnorePattern: \"^_\",\n varsIgnorePattern: \"^_\",\n },\n ],\n\n \"no-use-before-define\": \"off\",\n \"@typescript-eslint/no-use-before-define\": [\n \"warn\",\n { ignoreTypeReferences: true },\n ],\n },\n },\n {\n name: `${BASE_NAME}/typescript/tests`,\n files: TEST_FILES,\n rules: {\n // allow tests to be less strict\n \"@typescript-eslint/ban-ts-comment\": \"off\",\n \"@typescript-eslint/explicit-function-return-type\": \"off\",\n \"@typescript-eslint/no-empty-function\": \"off\",\n \"@typescript-eslint/no-explicit-any\": \"off\",\n \"@typescript-eslint/no-object-literal-type-assertion\": \"off\",\n \"@typescript-eslint/no-var-requires\": \"off\",\n },\n },\n {\n name: `${BASE_NAME}/typescript/vite`,\n files: VITE_MAIN_FILES,\n rules: {\n // allow `createRoot(document.getElementById(\"root\")).render(...)` for\n // `vite` without disabling eslint\n \"@typescript-eslint/no-non-null-assertion\": \"off\",\n },\n },\n ];\n\n if (tsconfigRootDir) {\n configs.push({\n name: `${BASE_NAME}/typescript-type-checking-language-options`,\n languageOptions: {\n parserOptions: {\n projectService: strictTypeChecked,\n tsconfigRootDir,\n },\n },\n });\n }\n\n if (strictTypeChecked) {\n configs.push(\n ...tseslint.configs.strictTypeCheckedOnly,\n {\n name: `${BASE_NAME}/typescript-type-checking`,\n files: TS_FILES,\n rules: {\n // I do not enable the `noUncheckedIndexedAccess` tsconfig option, so I\n // still need to verify that stuff exists. There are other cases where I\n // know it exists, so I can ignore those as well\n \"@typescript-eslint/no-unnecessary-condition\": \"off\",\n\n // I never use `this`\n \"@typescript-eslint/unbound-method\": \"off\",\n\n \"@typescript-eslint/restrict-template-expressions\": [\n \"error\",\n {\n allowNumber: true,\n },\n ],\n\n // I want to allow `onClick={async (event) => { ... }}`\n \"@typescript-eslint/no-misused-promises\": [\n \"error\",\n {\n checksVoidReturn: false,\n },\n ],\n },\n },\n {\n name: `${BASE_NAME}/typescript-type-checking/tests`,\n files: TEST_FILES,\n rules: {\n // like base typescript, can be less strict in tests\n \"@typescript-eslint/no-unsafe-return\": \"off\",\n \"@typescript-eslint/no-unsafe-assignment\": \"off\",\n \"@typescript-eslint/restrict-template-expressions\": \"off\",\n },\n },\n );\n }\n\n return configs;\n};\n","import { type Linter } from \"eslint\";\nimport { BASE_NAME, TEST_FILES, VITE_MAIN_FILES } from \"./constants.js\";\nimport eslintPluiginUnicorn from \"eslint-plugin-unicorn\";\n\nexport const unicorn: Linter.Config[] = [\n {\n ...eslintPluiginUnicorn.configs.recommended,\n name: `${BASE_NAME}/unicorn`,\n rules: {\n ...eslintPluiginUnicorn.configs.recommended.rules,\n\n // this flags `dist` and `dest` which is annoying\n \"unicorn/prevent-abbreviations\": \"off\",\n\n // I do not like using the default exports from `node:path`, `node:fs`,\n // etc\n \"unicorn/import-style\": \"off\",\n\n // I want PascalCase for React components/classes, camelCase for others.\n // Don't care enough to enforce through a rule and don't think it's\n // possible.\n \"unicorn/filename-case\": \"off\",\n\n // prettier instead\n \"unicorn/empty-brace-spaces\": \"off\",\n\n // I like `null`\n \"unicorn/no-null\": \"off\",\n\n // the description is incorrect since it attempts converting multi-line\n // statements to ternary which is awful:\n //\n // > This rule enforces the use of ternary expressions over 'simple'\n // > if-else statements, where 'simple' means the consequent and alternate\n // > are each one line and have the same basic type and form.\n \"unicorn/prefer-ternary\": \"off\",\n\n // I don't care about adding braces to switch cases. I'd prefer\n // `[\"error\", \"avoid\"]` more though since it only adds them when needed.\n \"unicorn/switch-case-braces\": \"off\",\n },\n },\n {\n name: `${BASE_NAME}/unicorn/vite`,\n files: VITE_MAIN_FILES,\n rules: {\n // allow `createRoot(document.getElementById(\"root\")).render(...)` for\n // `vite` without disabling eslint\n \"unicorn/prefer-query-selector\": \"off\",\n },\n },\n {\n name: `${BASE_NAME}/unicorn/testing`,\n files: TEST_FILES,\n rules: {\n // allow functions to be scoped to tests\n \"unicorn/consistent-function-scoping\": \"off\",\n },\n },\n];\n","import { type Linter } from \"eslint\";\nimport { scripts } from \"./scripts.js\";\nimport { testing, type TestOptions } from \"./testing.js\";\nimport { typescript, type TypescriptOptions } from \"./typescript.js\";\nimport { unicorn } from \"./unicorn.js\";\n\nexport interface RecommendedOptions extends TypescriptOptions, TestOptions {}\n\n/**\n * @example\n * ```ts\n * import { configs, gitignore } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([\n * gitignore(import.meta.url),\n * ...configs.recommended(),\n * ]);\n * ```\n */\nexport const recommended = (\n options: RecommendedOptions = {},\n): readonly Linter.Config[] => {\n return [...typescript(options), ...scripts, ...testing(options), ...unicorn];\n};\n","import { type Linter } from \"eslint\";\nimport { BASE_NAME, JSX_FILES } from \"./constants.js\";\n\nexport const mui: Linter.Config[] = [\n {\n name: `${BASE_NAME}/material-ui`,\n files: JSX_FILES,\n rules: {\n \"no-restricted-imports\": [\n \"error\",\n {\n // https://mui.com/material-ui/guides/minimizing-bundle-size/#enforce-best-practices-with-eslint\n patterns: [{ regex: \"^@mui/(?!(x-|utils))[^/]+$\" }],\n },\n ],\n },\n },\n];\n","import { type Linter } from \"eslint\";\nimport testingLibraryPlugin from \"eslint-plugin-testing-library\";\nimport { BASE_NAME, TEST_FILES } from \"./constants.js\";\n\n/**\n * @example\n * ```ts\n * import { configs } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([\n * ...configs.react,\n * ...configs.jest,\n * ...configs.jestDom,\n * ...configs.testingLibraryReact\n * ]);\n * ```\n *\n * NOTE: Only choose this or the {@link testingLibraryDom}. Do not use\n * both.\n */\nexport const testingLibraryReact: Linter.Config[] = [\n {\n name: `${BASE_NAME}/testing-library/react`,\n files: TEST_FILES,\n ...testingLibraryPlugin.configs[\"flat/react\"],\n rules: {\n ...testingLibraryPlugin.configs[\"flat/react\"].rules,\n // it can be useful to reassign screen.* queries without reusing to\n // verify it still exists\n \"no-useless-assignment\": \"off\",\n },\n },\n];\n\n/**\n * @example\n * ```ts\n * import { configs, defineConfig } from \"@mlaursen/eslint-config\";\n *\n * export default defineConfig([\n * ...configs.jest,\n * ...configs.jestDom,\n * ...configs.testingLibraryDom\n * ]);\n * ```\n *\n * NOTE: Only choose this or the {@link testingLibraryReact}. Do not use\n * both.\n */\nexport const testingLibraryDom: Linter.Config[] = [\n {\n name: `${BASE_NAME}/testing-library/dom`,\n files: TEST_FILES,\n ...testingLibraryPlugin.configs[\"flat/dom\"],\n rules: {\n ...testingLibraryPlugin.configs[\"flat/dom\"].rules,\n // it can be useful to reassign screen.* queries without reusing to\n // verify it still exists\n \"no-useless-assignment\": \"off\",\n },\n },\n];\n","import { type Linter } from \"eslint\";\nimport { jsxA11y } from \"./jsxA11y.js\";\nimport { mui } from \"./mui.js\";\nimport { react, type ReactOptions } from \"./react.js\";\nimport { recommended, type RecommendedOptions } from \"./recommended.js\";\nimport { testingLibraryReact } from \"./testing-library.js\";\n\nexport interface RecommendedFrontendOptions\n extends RecommendedOptions, ReactOptions {}\n\n/**\n * @example\n * ```ts\n * import { configs, gitignore } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([\n * gitignore(import.meta.url),\n * ...configs.recommendedFrontend(),\n * ]);\n * ```\n */\nexport const recommendedFrontend = (\n options: RecommendedFrontendOptions = {},\n): readonly Linter.Config[] => {\n return [\n ...recommended(options),\n ...mui,\n ...react(options),\n ...jsxA11y,\n ...testingLibraryReact,\n ];\n};\n","import { includeIgnoreFile } from \"@eslint/compat\";\nimport { type Linter } from \"eslint\";\nimport { fileURLToPath } from \"node:url\";\n\n/**\n * @example\n * ```ts\n * import { configs, gitignore } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n *\n * export default defineConfig([gitignore(import.meta.url), ...configs.typescript]);\n * ```\n *\n * @example .gitignore in a different folder\n * ```ts\n * import { configs, gitignore } from \"@mlaursen/eslint-config\";\n * import { defineConfig } from \"eslint/config\";\n * import { join } from \"node:path\";\n *\n * export default defineConfig([\n * gitignore(join(import.meta.url, \"..\", \"..\")),\n * ...configs.typescript,\n * ]);\n * ```\n */\nexport function gitignore(importMetaUrl: string): Linter.Config {\n return includeIgnoreFile(fileURLToPath(new URL(\".gitignore\", importMetaUrl)));\n}\n","import { base } from \"./base.js\";\n\nimport { jsxA11y } from \"./jsxA11y.js\";\nimport { react } from \"./react.js\";\nimport { recommended } from \"./recommended.js\";\nimport { recommendedFrontend } from \"./recommendedFrontend.js\";\nimport { scripts } from \"./scripts.js\";\nimport { testingLibraryDom, testingLibraryReact } from \"./testing-library.js\";\nimport { jest, jestDom, testing, vitest } from \"./testing.js\";\nimport { typescript } from \"./typescript.js\";\nimport { unicorn } from \"./unicorn.js\";\n\nexport * from \"./constants.js\";\n\ninterface EslintConfigs {\n recommended: typeof recommended;\n recommendedFrontend: typeof recommendedFrontend;\n\n base: typeof base;\n jest: typeof jest;\n jestDom: typeof jestDom;\n jsxA11y: typeof jsxA11y;\n react: typeof react;\n scripts: typeof scripts;\n testing: typeof testing;\n testingLibraryDom: typeof testingLibraryDom;\n testingLibraryReact: typeof testingLibraryReact;\n typescript: typeof typescript;\n unicorn: typeof unicorn;\n vitest: typeof vitest;\n}\n\nexport const configs: Readonly<EslintConfigs> = {\n recommended,\n recommendedFrontend,\n\n base,\n jest,\n jestDom,\n react,\n typescript,\n testingLibraryDom,\n testingLibraryReact,\n scripts,\n jsxA11y,\n testing,\n vitest,\n unicorn,\n};\n\nexport { gitignore } from \"./gitignore.js\";\n"],"names":["DEV_WARNING_PROD_ERROR","process","env","DEV_OFF_PROD_ERROR","BASE_NAME","TS_FILES","TEST_FILES","JSX_FILES","VITE_MAIN_FILES","base","eslint","configs","recommended","name","rules","curly","eqeqeq","jsxA11y","files","jsxA11yPlugin","flatConfigs","react","options","reactRefresh","reactCompiler","reactPlugin","flat","settings","version","reactHooksPlugin","additionalHooks","reactRefreshPlugin","ignores","scripts","vitest","plugins","vitestPlugin","jest","jestPlugin","jestDom","jestDomPlugin","testing","testFramework","config","typescript","tsconfigRootDir","strictTypeChecked","tseslint","strict","fixStyle","default","allowExpressions","allowTypedFunctionExpressions","argsIgnorePattern","varsIgnorePattern","ignoreTypeReferences","push","languageOptions","parserOptions","projectService","strictTypeCheckedOnly","allowNumber","checksVoidReturn","unicorn","eslintPluiginUnicorn","mui","patterns","regex","testingLibraryReact","testingLibraryPlugin","testingLibraryDom","recommendedFrontend","gitignore","importMetaUrl","includeIgnoreFile","fileURLToPath","URL"],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@mlaursen/eslint-config",
3
- "version": "12.0.6",
3
+ "version": "12.0.8",
4
4
  "description": "An eslint config used by mlaursen for most projects.",
5
5
  "type": "module",
6
6
  "exports": {
@@ -22,28 +22,32 @@
22
22
  ],
23
23
  "license": "MIT",
24
24
  "dependencies": {
25
- "@eslint/compat": "^2.0.3",
26
- "@eslint/core": "^1.1.1",
25
+ "@eslint/compat": "^2.0.5",
26
+ "@eslint/core": "^1.2.1",
27
27
  "@eslint/js": "^9.39.4",
28
28
  "@types/eslint-plugin-jsx-a11y": "^6.10.1",
29
- "@typescript-eslint/utils": "^8.57.1",
30
- "@vitest/eslint-plugin": "^1.6.12",
31
- "eslint": "^9.39.3",
32
- "eslint-plugin-jest": "^29.15.0",
29
+ "@typescript-eslint/utils": "^8.58.2",
30
+ "@vitest/eslint-plugin": "^1.6.16",
31
+ "eslint": "^9.39.4",
32
+ "eslint-plugin-jest": "^29.15.2",
33
33
  "eslint-plugin-jest-dom": "^5.5.0",
34
34
  "eslint-plugin-jsx-a11y": "^6.10.2",
35
35
  "eslint-plugin-react": "^7.37.5",
36
36
  "eslint-plugin-react-hooks": "^7.0.1",
37
37
  "eslint-plugin-react-refresh": "^0.5.2",
38
- "eslint-plugin-testing-library": "^7.16.0",
39
- "eslint-plugin-unicorn": "^63.0.0",
40
- "typescript-eslint": "^8.57.1"
38
+ "eslint-plugin-testing-library": "^7.16.2",
39
+ "eslint-plugin-unicorn": "^64.0.0",
40
+ "typescript-eslint": "^8.58.2"
41
41
  },
42
42
  "devDependencies": {
43
- "@types/node": "^25.5.0",
43
+ "@rollup/plugin-node-resolve": "^16.0.3",
44
+ "@types/node": "^24.12.2",
44
45
  "concurrently": "^9.2.1",
45
- "prettier": "^3.8.1",
46
- "typescript": "^5.9.3"
46
+ "prettier": "^3.8.3",
47
+ "rollup": "^4.60.1",
48
+ "rollup-plugin-dts": "^6.4.1",
49
+ "rollup-plugin-swc3": "^0.12.1",
50
+ "typescript": "^6.0.2"
47
51
  },
48
52
  "peerDependencies": {
49
53
  "eslint": ">= 9.0.0",
@@ -61,18 +65,24 @@
61
65
  "access": "public"
62
66
  },
63
67
  "volta": {
64
- "node": "24.13.1",
65
- "pnpm": "10.29.3"
68
+ "node": "24.14.1",
69
+ "pnpm": "10.33.0"
66
70
  },
67
71
  "scripts": {
68
- "clean-dist": "rm -rf dist",
69
- "clean-cache": "rm -rf .turbo node_modules",
72
+ "clean-dist": "rm -rf dist types",
73
+ "clean-cache": "rm -rf .turbo node_modules",
70
74
  "clean": "concurrently 'pnpm clean-dist' 'pnpm clean-cache'",
75
+ "check-format": "prettier --check .",
76
+ "format": "prettier --write .",
71
77
  "lint": "eslint .",
78
+ "lint-fix": "pnpm lint --fix",
72
79
  "typecheck": "tsc --noEmit",
73
80
  "typecheck-watch": "pnpm typecheck --watch",
74
- "check-format": "prettier --check .",
75
- "format": "prettier --write .",
76
- "build": "tsc -p tsconfig.build.json"
81
+ "build-dist": "rollup -c rollup.config.ts",
82
+ "build-dist-watch": "pnpm build-dist --watch",
83
+ "build-types": "tsc -p tsconfig.types.json",
84
+ "build-types-watch": "pnpm build-types --watch",
85
+ "build": "pnpm build-types && pnpm build-dist",
86
+ "dev": "concurrently 'pnpm build-types-watch' 'pnpm build-dist-watch'"
77
87
  }
78
88
  }
package/src/constants.ts CHANGED
@@ -1,5 +1,5 @@
1
1
  export const DEV_WARNING_PROD_ERROR =
2
- process.env.NODE_ENV === "production" ? "error" : "warn";
2
+ process.env["NODE_ENV"] === "production" ? "error" : "warn";
3
3
 
4
4
  /**
5
5
  * This is a "temporary" workaround until autofixable rules can be disabled with
@@ -7,7 +7,7 @@ export const DEV_WARNING_PROD_ERROR =
7
7
  * should be something closer to `DEV_WARN_PROD_ERROR_AND_FIX`
8
8
  */
9
9
  export const DEV_OFF_PROD_ERROR =
10
- process.env.NODE_ENV === "production" ? "error" : "off";
10
+ process.env["NODE_ENV"] === "production" ? "error" : "off";
11
11
 
12
12
  export const BASE_NAME = "@mlaursen/eslint-config";
13
13
 
package/src/react.ts CHANGED
@@ -66,7 +66,7 @@ export const react = (options: ReactOptions = {}): Linter.Config[] => {
66
66
 
67
67
  return [
68
68
  {
69
- ...reactPlugin.configs.flat.recommended,
69
+ ...reactPlugin.configs.flat["recommended"],
70
70
  name: `${BASE_NAME}/react`,
71
71
  files: JSX_FILES,
72
72
  settings: {
@@ -75,7 +75,7 @@ export const react = (options: ReactOptions = {}): Linter.Config[] => {
75
75
  },
76
76
  },
77
77
  rules: {
78
- ...reactPlugin.configs.flat.recommended?.rules,
78
+ ...reactPlugin.configs.flat["recommended"]?.rules,
79
79
  ...reactPlugin.configs.flat["jsx-runtime"]?.rules,
80
80
  },
81
81
  },
@@ -19,7 +19,7 @@ export interface RecommendedOptions extends TypescriptOptions, TestOptions {}
19
19
  * ```
20
20
  */
21
21
  export const recommended = (
22
- options: RecommendedOptions = {}
22
+ options: RecommendedOptions = {},
23
23
  ): readonly Linter.Config[] => {
24
24
  return [...typescript(options), ...scripts, ...testing(options), ...unicorn];
25
25
  };
@@ -21,7 +21,7 @@ export interface RecommendedFrontendOptions
21
21
  * ```
22
22
  */
23
23
  export const recommendedFrontend = (
24
- options: RecommendedFrontendOptions = {}
24
+ options: RecommendedFrontendOptions = {},
25
25
  ): readonly Linter.Config[] => {
26
26
  return [
27
27
  ...recommended(options),
package/src/typescript.ts CHANGED
@@ -50,7 +50,7 @@ export interface TypescriptOptions {
50
50
  * ```
51
51
  */
52
52
  export const typescript = (
53
- options: TypescriptOptions = {}
53
+ options: TypescriptOptions = {},
54
54
  ): Linter.Config[] => {
55
55
  const { tsconfigRootDir, strictTypeChecked } = options;
56
56
 
@@ -183,7 +183,7 @@ export const typescript = (
183
183
  "@typescript-eslint/no-unsafe-assignment": "off",
184
184
  "@typescript-eslint/restrict-template-expressions": "off",
185
185
  },
186
- }
186
+ },
187
187
  );
188
188
  }
189
189
 
package/dist/base.d.ts DELETED
@@ -1,11 +0,0 @@
1
- import { type Linter } from "eslint";
2
- /**
3
- * @example
4
- * ```js
5
- * import { configs } from "@mlaursen/eslint-config";
6
- * import { defineConfig } from "eslint/config";
7
- *
8
- * export default defineConfig(configs.base);
9
- * ```
10
- */
11
- export declare const base: Linter.Config[];
package/dist/base.js DELETED
@@ -1,51 +0,0 @@
1
- import eslint from "@eslint/js";
2
- import { BASE_NAME, DEV_WARNING_PROD_ERROR } from "./constants.js";
3
- /**
4
- * @example
5
- * ```js
6
- * import { configs } from "@mlaursen/eslint-config";
7
- * import { defineConfig } from "eslint/config";
8
- *
9
- * export default defineConfig(configs.base);
10
- * ```
11
- */
12
- export var base = [
13
- eslint.configs.recommended,
14
- {
15
- name: "".concat(BASE_NAME, "/base"),
16
- rules: {
17
- // I use typescript instead
18
- "no-undef": "off",
19
- // You normally do not want `console.{whatever}` in prod but is fine for
20
- // development in debugging
21
- "no-console": DEV_WARNING_PROD_ERROR,
22
- "no-var": "error",
23
- "no-use-before-define": "warn",
24
- // I want to enforce all statements to require curly braces even if it
25
- // could be omitted for consistency
26
- curly: "error",
27
- // Since this is auto-fixable, I like `{ someproperty }` instead of
28
- // `{ someproperty: someproperty }`
29
- "object-shorthand": ["error", "always"],
30
- // This is about the same as `object-shorthand`. Only rename if it has to
31
- // be renamed
32
- "no-useless-rename": ["error"],
33
- "no-eval": "error",
34
- "no-alert": "error",
35
- "no-lonely-if": "error",
36
- "no-else-return": "error",
37
- eqeqeq: "error",
38
- // 100% stylistic, but do not allow `a = b = c = "whatever"` / `let a = whatever, b = whatever, c = whatever;`
39
- // these should be different statements
40
- "no-multi-assign": "error",
41
- "no-sequences": "error",
42
- // use template strings instead
43
- "no-multi-str": "error",
44
- // better to use new variables most of the time
45
- "no-param-reassign": "error",
46
- // i'd never hit these, but who trusts other people and AI?
47
- "no-return-assign": "error",
48
- "no-script-url": "error",
49
- },
50
- },
51
- ];
@@ -1,12 +0,0 @@
1
- export declare const DEV_WARNING_PROD_ERROR: string;
2
- /**
3
- * This is a "temporary" workaround until autofixable rules can be disabled with
4
- * a config option because of the "autofix + format(+ save)?" behavior. It
5
- * should be something closer to `DEV_WARN_PROD_ERROR_AND_FIX`
6
- */
7
- export declare const DEV_OFF_PROD_ERROR: string;
8
- export declare const BASE_NAME = "@mlaursen/eslint-config";
9
- export declare const TS_FILES: string[];
10
- export declare const TEST_FILES: string[];
11
- export declare const JSX_FILES: string[];
12
- export declare const VITE_MAIN_FILES: string[];
package/dist/constants.js DELETED
@@ -1,15 +0,0 @@
1
- export var DEV_WARNING_PROD_ERROR = process.env.NODE_ENV === "production" ? "error" : "warn";
2
- /**
3
- * This is a "temporary" workaround until autofixable rules can be disabled with
4
- * a config option because of the "autofix + format(+ save)?" behavior. It
5
- * should be something closer to `DEV_WARN_PROD_ERROR_AND_FIX`
6
- */
7
- export var DEV_OFF_PROD_ERROR = process.env.NODE_ENV === "production" ? "error" : "off";
8
- export var BASE_NAME = "@mlaursen/eslint-config";
9
- export var TS_FILES = ["**/*.{ts,tsx,mts,mtsx}"];
10
- export var TEST_FILES = [
11
- "**/__tests__/**",
12
- "**/*.{spec,test}.{ts,tsx,js,jsx}",
13
- ];
14
- export var JSX_FILES = ["**/*.{js,mjs,cjs,jsx,mjsx,ts,tsx,mtsx}"];
15
- export var VITE_MAIN_FILES = ["**/main.tsx"];
@@ -1,23 +0,0 @@
1
- import { type Linter } from "eslint";
2
- /**
3
- * @example
4
- * ```ts
5
- * import { configs, gitignore } from "@mlaursen/eslint-config";
6
- * import { defineConfig } from "eslint/config";
7
- *
8
- * export default defineConfig([gitignore(import.meta.url), ...configs.typescript]);
9
- * ```
10
- *
11
- * @example .gitignore in a different folder
12
- * ```ts
13
- * import { configs, gitignore } from "@mlaursen/eslint-config";
14
- * import { defineConfig } from "eslint/config";
15
- * import { join } from "node:path";
16
- *
17
- * export default defineConfig([
18
- * gitignore(join(import.meta.url, "..", "..")),
19
- * ...configs.typescript,
20
- * ]);
21
- * ```
22
- */
23
- export declare function gitignore(importMetaUrl: string): Linter.Config;
package/dist/gitignore.js DELETED
@@ -1,26 +0,0 @@
1
- import { includeIgnoreFile } from "@eslint/compat";
2
- import { fileURLToPath } from "node:url";
3
- /**
4
- * @example
5
- * ```ts
6
- * import { configs, gitignore } from "@mlaursen/eslint-config";
7
- * import { defineConfig } from "eslint/config";
8
- *
9
- * export default defineConfig([gitignore(import.meta.url), ...configs.typescript]);
10
- * ```
11
- *
12
- * @example .gitignore in a different folder
13
- * ```ts
14
- * import { configs, gitignore } from "@mlaursen/eslint-config";
15
- * import { defineConfig } from "eslint/config";
16
- * import { join } from "node:path";
17
- *
18
- * export default defineConfig([
19
- * gitignore(join(import.meta.url, "..", "..")),
20
- * ...configs.typescript,
21
- * ]);
22
- * ```
23
- */
24
- export function gitignore(importMetaUrl) {
25
- return includeIgnoreFile(fileURLToPath(new URL(".gitignore", importMetaUrl)));
26
- }
package/dist/jsxA11y.d.ts DELETED
@@ -1,11 +0,0 @@
1
- import { type Linter } from "eslint";
2
- /**
3
- * @example
4
- * ```ts
5
- * import { configs } from "@mlaursen/eslint-config";
6
- * import { defineConfig } from "eslint/config";
7
- *
8
- * export default defineConfig(configs.jsxA11y);
9
- * ```
10
- */
11
- export declare const jsxA11y: Linter.Config[];
package/dist/jsxA11y.js DELETED
@@ -1,37 +0,0 @@
1
- var __assign = (this && this.__assign) || function () {
2
- __assign = Object.assign || function(t) {
3
- for (var s, i = 1, n = arguments.length; i < n; i++) {
4
- s = arguments[i];
5
- for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
6
- t[p] = s[p];
7
- }
8
- return t;
9
- };
10
- return __assign.apply(this, arguments);
11
- };
12
- import jsxA11yPlugin from "eslint-plugin-jsx-a11y";
13
- import { BASE_NAME, JSX_FILES, TEST_FILES } from "./constants.js";
14
- /**
15
- * @example
16
- * ```ts
17
- * import { configs } from "@mlaursen/eslint-config";
18
- * import { defineConfig } from "eslint/config";
19
- *
20
- * export default defineConfig(configs.jsxA11y);
21
- * ```
22
- */
23
- export var jsxA11y = [
24
- __assign(__assign({ name: "".concat(BASE_NAME, "/jsx-a11y"), files: JSX_FILES }, jsxA11yPlugin.flatConfigs.recommended), { rules: __assign(__assign({}, jsxA11yPlugin.flatConfigs.recommended.rules), {
25
- // I **only** use autoFocus within dialogs which provide the correct
26
- // context for screen readers.
27
- "jsx-a11y/no-autofocus": "off" }) }),
28
- {
29
- name: "".concat(BASE_NAME, "/jsx-a11y/testing"),
30
- files: TEST_FILES,
31
- rules: {
32
- "jsx-a11y/anchor-has-content": "off",
33
- "jsx-a11y/click-events-have-key-events": "off",
34
- "jsx-a11y/no-static-element-interactions": "off",
35
- },
36
- },
37
- ];
package/dist/mui.d.ts DELETED
@@ -1,2 +0,0 @@
1
- import { type Linter } from "eslint";
2
- export declare const mui: Linter.Config[];
package/dist/mui.js DELETED
@@ -1,16 +0,0 @@
1
- import { BASE_NAME, JSX_FILES } from "./constants.js";
2
- export var mui = [
3
- {
4
- name: "".concat(BASE_NAME, "/material-ui"),
5
- files: JSX_FILES,
6
- rules: {
7
- "no-restricted-imports": [
8
- "error",
9
- {
10
- // https://mui.com/material-ui/guides/minimizing-bundle-size/#enforce-best-practices-with-eslint
11
- patterns: [{ regex: "^@mui/(?!(x-|utils))[^/]+$" }],
12
- },
13
- ],
14
- },
15
- },
16
- ];
package/dist/react.d.ts DELETED
@@ -1,57 +0,0 @@
1
- import { type Linter } from "eslint";
2
- import reactRefreshPlugin from "eslint-plugin-react-refresh";
3
- export type ReactRefreshConfig = keyof typeof reactRefreshPlugin.configs;
4
- export interface ReactOptions {
5
- /**
6
- * Set to one of the `eslint-plugin-react-refresh` config names to enable.
7
- *
8
- * @example Vite
9
- * ```js
10
- * configs.react({
11
- * reactRefresh: "vite",
12
- * })
13
- * ```
14
- *
15
- * @example Next.js
16
- * ```js
17
- * configs.react({
18
- * reactRefresh: "next",
19
- * })
20
- * ```
21
- *
22
- * @example Recommended
23
- * ```js
24
- * configs.react({
25
- * reactRefresh: "recommended",
26
- * })
27
- * ```
28
- */
29
- reactRefresh?: ReactRefreshConfig;
30
- /**
31
- * Set to `true` to enable the react compiler eslint rules.
32
- *
33
- * @defaultValue `false`
34
- */
35
- reactCompiler?: boolean;
36
- }
37
- /**
38
- * @example
39
- * ```ts
40
- * import { configs } from "@mlaursen/eslint-config";
41
- * import { defineConfig } from "eslint/config";
42
- *
43
- * export default defineConfig(configs.react());
44
- *
45
- * // or with react compiler rules enabled
46
- * export default defineConfig(configs.react(true));
47
- * ```
48
- *
49
- * Enables:
50
- * - `eslint-plugin-react` with:
51
- * - flat.recommended
52
- * - flat['jsx-runtime']
53
- * - `eslint-plugin-react-hooks` with:
54
- * - recommended rules
55
- * - compiler rules (if `true` is provided)
56
- */
57
- export declare const react: (options?: ReactOptions) => Linter.Config[];
package/dist/react.js DELETED
@@ -1,82 +0,0 @@
1
- var __assign = (this && this.__assign) || function () {
2
- __assign = Object.assign || function(t) {
3
- for (var s, i = 1, n = arguments.length; i < n; i++) {
4
- s = arguments[i];
5
- for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
6
- t[p] = s[p];
7
- }
8
- return t;
9
- };
10
- return __assign.apply(this, arguments);
11
- };
12
- var __read = (this && this.__read) || function (o, n) {
13
- var m = typeof Symbol === "function" && o[Symbol.iterator];
14
- if (!m) return o;
15
- var i = m.call(o), r, ar = [], e;
16
- try {
17
- while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);
18
- }
19
- catch (error) { e = { error: error }; }
20
- finally {
21
- try {
22
- if (r && !r.done && (m = i["return"])) m.call(i);
23
- }
24
- finally { if (e) throw e.error; }
25
- }
26
- return ar;
27
- };
28
- var __spreadArray = (this && this.__spreadArray) || function (to, from, pack) {
29
- if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {
30
- if (ar || !(i in from)) {
31
- if (!ar) ar = Array.prototype.slice.call(from, 0, i);
32
- ar[i] = from[i];
33
- }
34
- }
35
- return to.concat(ar || Array.prototype.slice.call(from));
36
- };
37
- import reactPlugin from "eslint-plugin-react";
38
- import reactHooksPlugin from "eslint-plugin-react-hooks";
39
- import reactRefreshPlugin from "eslint-plugin-react-refresh";
40
- import { BASE_NAME, JSX_FILES } from "./constants.js";
41
- /**
42
- * @example
43
- * ```ts
44
- * import { configs } from "@mlaursen/eslint-config";
45
- * import { defineConfig } from "eslint/config";
46
- *
47
- * export default defineConfig(configs.react());
48
- *
49
- * // or with react compiler rules enabled
50
- * export default defineConfig(configs.react(true));
51
- * ```
52
- *
53
- * Enables:
54
- * - `eslint-plugin-react` with:
55
- * - flat.recommended
56
- * - flat['jsx-runtime']
57
- * - `eslint-plugin-react-hooks` with:
58
- * - recommended rules
59
- * - compiler rules (if `true` is provided)
60
- */
61
- export var react = function (options) {
62
- var _a, _b;
63
- if (options === void 0) { options = {}; }
64
- var reactRefresh = options.reactRefresh, reactCompiler = options.reactCompiler;
65
- return __spreadArray([
66
- __assign(__assign({}, reactPlugin.configs.flat.recommended), { name: "".concat(BASE_NAME, "/react"), files: JSX_FILES, settings: {
67
- react: {
68
- version: "detect",
69
- },
70
- }, rules: __assign(__assign({}, (_a = reactPlugin.configs.flat.recommended) === null || _a === void 0 ? void 0 : _a.rules), (_b = reactPlugin.configs.flat["jsx-runtime"]) === null || _b === void 0 ? void 0 : _b.rules) }),
71
- __assign(__assign({}, reactHooksPlugin.configs.flat.recommended), { name: "".concat(BASE_NAME, "/react-hooks"), rules: __assign(__assign({}, (reactCompiler && reactHooksPlugin.configs.flat.recommended.rules)), { "react-hooks/rules-of-hooks": "error", "react-hooks/exhaustive-deps": [
72
- "error",
73
- {
74
- additionalHooks: "(useIsomorphicLayoutEffect)",
75
- },
76
- ] }) })
77
- ], __read((reactRefresh
78
- ? [
79
- __assign(__assign({}, reactRefreshPlugin.configs[reactRefresh]), { name: "".concat(BASE_NAME, "/react-refresh"), ignores: ["**/test-utils*", "**/test-utils/**"] }),
80
- ]
81
- : [])), false);
82
- };
@@ -1,18 +0,0 @@
1
- import { type Linter } from "eslint";
2
- import { type TestOptions } from "./testing.js";
3
- import { type TypescriptOptions } from "./typescript.js";
4
- export interface RecommendedOptions extends TypescriptOptions, TestOptions {
5
- }
6
- /**
7
- * @example
8
- * ```ts
9
- * import { configs, gitignore } from "@mlaursen/eslint-config";
10
- * import { defineConfig } from "eslint/config";
11
- *
12
- * export default defineConfig([
13
- * gitignore(import.meta.url),
14
- * ...configs.recommended(),
15
- * ]);
16
- * ```
17
- */
18
- export declare const recommended: (options?: RecommendedOptions) => readonly Linter.Config[];