From 8fc344f3eaa899e66089b343b35efa8761b92a01 Mon Sep 17 00:00:00 2001 From: Ferdinand Thiessen Date: Tue, 14 Jan 2025 09:50:19 +0100 Subject: [PATCH 1/7] feat!: Migrate config to ESLint v9 implementing all code style rules Signed-off-by: Ferdinand Thiessen --- .gitignore | 6 +- .npmignore | 6 -- README.md | 60 +++++------- REUSE.toml | 6 ++ index.js | 25 ----- lib/configs/codeStyle.ts | 173 +++++++++++++++++++++++++++++++++++ lib/configs/documentation.ts | 90 ++++++++++++++++++ lib/configs/filesystem.ts | 21 +++++ lib/configs/javascript.ts | 98 ++++++++++++++++++++ lib/configs/json.ts | 37 ++++++++ lib/configs/node.ts | 30 ++++++ lib/configs/typescript.ts | 62 +++++++++++++ lib/configs/vue.ts | 126 +++++++++++++++++++++++++ lib/configs/vue2.ts | 47 ++++++++++ lib/configs/vue3.ts | 37 ++++++++ lib/globals.d.ts | 10 ++ lib/globs.ts | 35 +++++++ lib/index.ts | 65 +++++++++++++ lib/types.d.ts | 8 ++ lib/utils.ts | 22 +++++ package.json | 107 ++++++++++------------ parts/base.js | 117 ----------------------- parts/typescript.js | 49 ---------- parts/vue.js | 45 --------- parts/vue3.js | 43 --------- tsconfig.json | 24 +++++ typescript.js | 45 --------- vite.config.ts | 17 ++++ vue3.js | 45 --------- 29 files changed, 982 insertions(+), 474 deletions(-) delete mode 100644 .npmignore delete mode 100644 index.js create mode 100644 lib/configs/codeStyle.ts create mode 100644 lib/configs/documentation.ts create mode 100644 lib/configs/filesystem.ts create mode 100644 lib/configs/javascript.ts create mode 100644 lib/configs/json.ts create mode 100644 lib/configs/node.ts create mode 100644 lib/configs/typescript.ts create mode 100644 lib/configs/vue.ts create mode 100644 lib/configs/vue2.ts create mode 100644 lib/configs/vue3.ts create mode 100644 lib/globals.d.ts create mode 100644 lib/globs.ts create mode 100644 lib/index.ts create mode 100644 lib/types.d.ts create mode 100644 lib/utils.ts delete mode 100644 parts/base.js delete mode 100644 parts/typescript.js delete mode 100644 parts/vue.js delete mode 100644 parts/vue3.js create mode 100644 tsconfig.json delete mode 100644 typescript.js create mode 100644 vite.config.ts delete mode 100644 vue3.js diff --git a/.gitignore b/.gitignore index a9cc883..bffa5a2 100644 --- a/.gitignore +++ b/.gitignore @@ -1,5 +1,6 @@ # SPDX-FileCopyrightText: 2019 Nextcloud GmbH and Nextcloud contributors # SPDX-License-Identifier: AGPL-3.0-or-later + # Logs logs *.log @@ -36,10 +37,9 @@ build/Release # Dependency directories node_modules/ -jspm_packages/ -# TypeScript v1 declaration files -typings/ +# Output +dist/ # Optional npm cache directory .npm diff --git a/.npmignore b/.npmignore deleted file mode 100644 index d8c336e..0000000 --- a/.npmignore +++ /dev/null @@ -1,6 +0,0 @@ -# SPDX-FileCopyrightText: 2019 Nextcloud GmbH and Nextcloud contributors -# SPDX-License-Identifier: AGPL-3.0-or-later -.travis.yml -test/ -.github -tests diff --git a/README.md b/README.md index 60844db..fd580fa 100644 --- a/README.md +++ b/README.md @@ -10,11 +10,10 @@ [![Dependabot status](https://img.shields.io/badge/Dependabot-enabled-brightgreen.svg?longCache=true&style=flat-square&logo=dependabot)](https://dependabot.com) -This is a package containing the unified global eslint config used by all nextcloud apps. +This is a package containing the unified global eslint config used by all nextcloud apps and libraries. It contains the necessary dependencies and peerDependencies so that other apps cannot update if this config does not support it. Please always use dependabot to update your apps, OR pay attention to the peer dependencies error messages! - ## Installation ```bash @@ -23,45 +22,36 @@ npm install @nextcloud/eslint-config --save-dev ## Usage -Add a file `.eslintrc.js` in the root directory of your app repository with the following content: - -```js -module.exports = { - extends: [ - '@nextcloud', - ], -} -``` - -### Usage with Typescript projects - -If your projects uses Typescript for vue files, like ` diff --git a/tests/fixtures/typescript-vue-overrides.vue b/tests/fixtures/typescript-vue-overrides.vue index 7fe0d70..1312bda 100644 --- a/tests/fixtures/typescript-vue-overrides.vue +++ b/tests/fixtures/typescript-vue-overrides.vue @@ -1,17 +1,18 @@ +--> diff --git a/tests/setup-jest.ts b/tests/setup.ts similarity index 73% rename from tests/setup-jest.ts rename to tests/setup.ts index fd75f0f..7cf8f9c 100644 --- a/tests/setup-jest.ts +++ b/tests/setup.ts @@ -3,15 +3,7 @@ * SPDX-License-Identifier: AGPL-3.0-or-later */ import { ESLint, Linter } from 'eslint' - -/** - * Add some custom matchers for ESLint to jest - */ -expect.extend({ - toPass: assertLintingPassed, - toHaveIssueCount: assertHavingNIssues, - toHaveIssue: assertHavingIssue, -}) +import { expect } from 'vitest' /** * Check if linting a file did not throw any errors or warnings @@ -20,7 +12,9 @@ expect.extend({ */ function hasNoIssues(received: ESLint.LintResult) { // dirty type check - if (received?.errorCount === undefined) throw new Error('Expected ESLintResult') + if (received?.errorCount === undefined) { + throw new Error('Expected ESLintResult') + } return received.errorCount === 0 && received.warningCount === 0 } @@ -28,8 +22,7 @@ function hasNoIssues(received: ESLint.LintResult) { /** * Check if linting of multiple fils * - * @param received - * @return {} + * @param received The result of the linting */ function assertLintingPassed(received: ESLint.LintResult | ESLint.LintResult[]) { // allow single ESLintResult @@ -37,10 +30,16 @@ function assertLintingPassed(received: ESLint.LintResult | ESLint.LintResult[]) received = [received] } - const errors = [] as {file: string, errors: Linter.LintMessage[]}[] + const errors = [] as { + file: string + errors: Linter.LintMessage[] + }[] const pass = received.every((result) => { // save issues - errors.push({ file: result.filePath, errors: result.messages }) + errors.push({ + file: result.filePath, + errors: result.messages, + }) return hasNoIssues(result) }) @@ -50,10 +49,8 @@ function assertLintingPassed(received: ESLint.LintResult | ESLint.LintResult[]) if (pass) { return 'Expected file to not pass eslint, but got no issues' } else { - const errorMessages = errors.map((m) => - `file: ${m.file}\n` + m.errors.map((e) => 'line: ' + e.line + ': ' + (e.ruleId || e.message)), - ) - return 'Expected file to pass eslint, got issues:\n' + errorMessages.join('\n') + const errorMessages = errors.map((m) => `file: ${m.file}\n${m.errors.map((e) => `line: ${e.line}: ${e.ruleId || e.message}`)}`) + return `Expected file to pass eslint, got issues:\n${errorMessages.join('\n')}` } }, } @@ -63,7 +60,7 @@ function assertLintingPassed(received: ESLint.LintResult | ESLint.LintResult[]) * Count the total amount of issues * * @param received lint result - * @return total amount of issues + * @returns total amount of issues */ function countIssues(received: ESLint.LintResult) { return received.errorCount + received.warningCount @@ -74,10 +71,12 @@ function countIssues(received: ESLint.LintResult) { * * @param received the lint result * @param expected number of expected issues - * @return jest matcher result + * @returns jest matcher result */ function assertHavingNIssues(received: ESLint.LintResult | ESLint.LintResult[], expected: number) { - if (!(typeof expected === 'number')) throw new Error('Expected a number as expected value') + if (!(typeof expected === 'number')) { + throw new Error('Expected a number as expected value') + } if (!Array.isArray(received)) { received = [received] @@ -97,9 +96,12 @@ function assertHavingNIssues(received: ESLint.LintResult | ESLint.LintResult[], * * @param received the lint result * @param issue the expected issue - * @return jest matcher result + * @returns jest matcher result */ -function assertHavingIssue(received: ESLint.LintResult | ESLint.LintResult[], issue: string | {ruleId: string, line?: number}) { +function assertHavingIssue(received: ESLint.LintResult | ESLint.LintResult[], issue: string | { + ruleId: string + line?: number +}) { if (!Array.isArray(received)) { received = [received] } @@ -113,12 +115,16 @@ function assertHavingIssue(received: ESLint.LintResult | ESLint.LintResult[], is } const name = typeof issue === 'string' ? issue : issue.ruleId - const result = received.some((result) => { - return result.messages.some((message) => { + const result = received.some((data) => { + return data.messages.some((message) => { // ensure name matches - if (message.ruleId !== name) return false + if (message.ruleId !== name) { + return false + } // if line is requested ignore not matching ones - if (typeof issue === 'object' && issue.line !== undefined && issue.line !== message.line) return false + if (typeof issue === 'object' && issue.line !== undefined && issue.line !== message.line) { + return false + } // otherwise matched return true }) @@ -130,3 +136,12 @@ function assertHavingIssue(received: ESLint.LintResult | ESLint.LintResult[], is message: () => result ? `Unexpected error '${name}'${onLine} found.` : `Expected error '${name}'${onLine} not found.`, } } + +/** + * Add some custom matchers for ESLint to jest + */ +expect.extend({ + toPass: assertLintingPassed, + toHaveIssueCount: assertHavingNIssues, + toHaveIssue: assertHavingIssue, +}) diff --git a/tests/tsconfig.json b/tests/tsconfig.json new file mode 100644 index 0000000..8cccc9d --- /dev/null +++ b/tests/tsconfig.json @@ -0,0 +1,7 @@ +{ + "extends":"../tsconfig.json", + "compilerOptions": { + "rootDir": ".." + }, + "include": ["./vitest.d.ts", ".", "../lib"] +} \ No newline at end of file diff --git a/tests/vitest.d.ts b/tests/vitest.d.ts new file mode 100644 index 0000000..c3d8659 --- /dev/null +++ b/tests/vitest.d.ts @@ -0,0 +1,22 @@ +/** + * SPDX-FileCopyrightText: 2023 Nextcloud GmbH and Nextcloud contributors + * SPDX-License-Identifier: AGPL-3.0-or-later + */ + +import 'vitest' + +interface CustomMatchers { + toPass(): R + toHaveIssueCount(n: number): R + toHaveIssue(issue: string | { + ruleId: string + line?: number + }): R +} + +declare module 'vitest' { + // eslint-disable-next-line @typescript-eslint/no-empty-object-type + interface Assertion extends CustomMatchers {} + // eslint-disable-next-line @typescript-eslint/no-empty-object-type + interface AsymmetricMatchersContaining extends CustomMatchers {} +} diff --git a/vite.config.ts b/vite.config.ts index 6b8105f..688a1b3 100644 --- a/vite.config.ts +++ b/vite.config.ts @@ -3,6 +3,7 @@ * SPDX-License-Identifier: CC0-1.0 */ +import type { UserConfig } from 'vite' import { createLibConfig } from '@nextcloud/vite-config' export default createLibConfig({ @@ -14,4 +15,10 @@ export default createLibConfig({ replace: { __PACKAGE_VERSION__: JSON.stringify(process.env.npm_package_version), }, + + config: { + test: { + setupFiles: ['tests/setup.ts'], + }, + } as UserConfig, })