diff --git a/.github/workflows/checks.yaml b/.github/workflows/checks.yaml index 9851aeb2..02b4e164 100644 --- a/.github/workflows/checks.yaml +++ b/.github/workflows/checks.yaml @@ -75,20 +75,21 @@ jobs: - run: npm ci # prettier-ignore - - run: npm install eslint@${{ matrix.eslint }} @types/eslint@${{ matrix.eslint }} @eslint/js@${{ matrix.eslint }} @typescript-eslint/parser@${{ matrix.typescript-eslint }} @typescript-eslint/eslint-plugin@${{ matrix.typescript-eslint }} --no-fund - - if: matrix.eslint == 8 - run: npm i -D @types/eslint__js@${{ matrix.eslint }} - - if: matrix.eslint != 8 # v9+ provides its own types - run: npm un @types/eslint @types/eslint__js + - run: tools/install-eslint-dependencies.sh ${{ matrix.eslint }} ${{ matrix.typescript-eslint }} - run: npm run lint test: permissions: contents: read # to fetch code (actions/checkout) - name: Test on ${{ matrix.os }} using Node.js LTS + name: Test on ${{ matrix.os }} with eslint v${{ matrix.eslint }}, @typescript-eslint v${{ matrix.typescript-eslint }}, and using Node.js LTS strategy: fail-fast: false matrix: + eslint: [8, 9] + typescript-eslint: [7, 8] os: [ubuntu-latest, macOS-latest] + exclude: + - eslint: 9 + typescript-eslint: 7 runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v4 @@ -100,17 +101,23 @@ jobs: cache: npm - run: npm ci + # prettier-ignore + - run: tools/install-eslint-dependencies.sh ${{ matrix.eslint }} ${{ matrix.typescript-eslint }} - run: npm run test typecheck: permissions: contents: read # to fetch code (actions/checkout) # prettier-ignore - name: Typecheck on ${{ matrix.os }} using Node.js LTS and ESLint v${{ matrix.eslint }} types + name: Typecheck on ${{ matrix.os }} with eslint v${{ matrix.eslint }}, @typescript-eslint v${{ matrix.typescript-eslint }}, and using Node.js LTS strategy: fail-fast: false matrix: eslint: [8, 9] + typescript-eslint: [7, 8] os: [ubuntu-latest, macOS-latest] + exclude: + - eslint: 9 + typescript-eslint: 7 runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v4 @@ -123,9 +130,5 @@ jobs: - run: npm ci # prettier-ignore - - run: npm i -D eslint@${{ matrix.eslint }} @types/eslint@${{ matrix.eslint }} @eslint/js@${{ matrix.eslint }} - - if: matrix.eslint == 8 - run: npm i -D @types/eslint__js@${{ matrix.eslint }} - - if: matrix.eslint != 8 # v9+ provides its own types - run: npm un @types/eslint @types/eslint__js + - run: tools/install-eslint-dependencies.sh ${{ matrix.eslint }} ${{ matrix.typescript-eslint }} - run: npm run typecheck diff --git a/tools/install-eslint-dependencies.sh b/tools/install-eslint-dependencies.sh new file mode 100755 index 00000000..ab1a250f --- /dev/null +++ b/tools/install-eslint-dependencies.sh @@ -0,0 +1,20 @@ +#!/usr/bin/env bash + +set -e + +esv=${1?'must be eslint major version'} +tsv=${2?'must be typescript eslint major version'} + +npm install -D \ + "eslint@$esv" \ + "@types/eslint@$esv" \ + "@eslint/js@$esv" \ + "@typescript-eslint/parser@$tsv" \ + "@typescript-eslint/eslint-plugin@$tsv" + +# ESLint v9+ ships with its own types +if [ "$esv" -eq 8 ]; then + npm install -D "@types/eslint__js@$esv" +else + npm uninstall -D @types/eslint @types/eslint__js +fi diff --git a/types.d.ts b/types.d.ts index e2f940e1..2e402945 100644 --- a/types.d.ts +++ b/types.d.ts @@ -113,11 +113,20 @@ declare module '@typescript-eslint/eslint-plugin' { export = plugin; } -// todo: doesn't get its own types until v8 +// todo: we need to specify our own types to ensure compatibility with both ESLint v8 and v9 declare module '@typescript-eslint/parser' { import * as ESLint from 'eslint'; - const parser: ESLint.Linter.ParserModule; + const parser: ESLint.ESLint.ObjectMetaProperties & + ( + | { + parseForESLint( + text: string, + options?: unknown + ): ESLint.Linter.ESLintParseResult; + } + | { parse(text: string, options?: unknown): ESLint.AST.Program } + ); export = parser; }