From f9942cb7f319396ebd69e76c11511bf478b3648e Mon Sep 17 00:00:00 2001 From: Mark Wubben Date: Sun, 5 May 2024 22:04:49 +0200 Subject: [PATCH 1/6] Target same Node.js versions as AVA 6 --- .github/workflows/ci.yml | 5 +---- package.json | 2 +- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 536a931..c8dbb78 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -13,16 +13,13 @@ jobs: strategy: fail-fast: false matrix: - node-version: [^14.19, ^16.15, ^18, ^20, ^21] + node-version: [^18.18, ^20.8, ^21] os: [ubuntu-latest, windows-latest] steps: - uses: actions/checkout@v3 - uses: actions/setup-node@v3 with: node-version: ${{ matrix.node-version }} - - name: Install npm@8 for Node.js 14 - if: matrix.node-version == '^14.19' - run: npm install --global npm@^8 - run: npm install --no-audit - run: npm test - uses: codecov/codecov-action@v2 diff --git a/package.json b/package.json index e97a007..a414772 100644 --- a/package.json +++ b/package.json @@ -3,7 +3,7 @@ "version": "4.1.0", "description": "TypeScript provider for AVA", "engines": { - "node": "^14.19 || ^16.15 || ^18 || ^20 || ^21" + "node": "^18.18 || ^20.8 || ^21" }, "files": [ "index.js" From 4811f7424af9aab426230af01085a2f276198dff Mon Sep 17 00:00:00 2001 From: Silas Rech Date: Sun, 5 May 2024 22:05:48 +0200 Subject: [PATCH 2/6] Upgrade actions --- .github/workflows/ci.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index c8dbb78..99193b6 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -16,13 +16,13 @@ jobs: node-version: [^18.18, ^20.8, ^21] os: [ubuntu-latest, windows-latest] steps: - - uses: actions/checkout@v3 - - uses: actions/setup-node@v3 + - uses: actions/checkout@v4 + - uses: actions/setup-node@v4 with: node-version: ${{ matrix.node-version }} - run: npm install --no-audit - run: npm test - - uses: codecov/codecov-action@v2 + - uses: codecov/codecov-action@v4 with: files: coverage/lcov.info name: ${{ matrix.os }}/${{ matrix.node-version }} From 547fb42fb353481df6aba82909afc5223ab320e7 Mon Sep 17 00:00:00 2001 From: Mark Wubben Date: Sun, 5 May 2024 22:09:51 +0200 Subject: [PATCH 3/6] Restrict compatibility to AVA 6 --- index.js | 183 ++++++++++-------------- test/compilation.js | 4 +- test/fixtures/install-and-load.js | 2 +- test/load.js | 2 +- test/protocol-ava-3.2.js | 91 ------------ test/snapshots/protocol-ava-3.2.js.md | 117 --------------- test/snapshots/protocol-ava-3.2.js.snap | Bin 782 -> 0 bytes 7 files changed, 80 insertions(+), 319 deletions(-) delete mode 100644 test/protocol-ava-3.2.js delete mode 100644 test/snapshots/protocol-ava-3.2.js.md delete mode 100644 test/snapshots/protocol-ava-3.2.js.snap diff --git a/index.js b/index.js index fb5b165..48fc16b 100644 --- a/index.js +++ b/index.js @@ -75,7 +75,7 @@ const changeInterpretations = Object.freeze(Object.assign(Object.create(null), { })); export default function typescriptProvider({negotiateProtocol}) { - const protocol = negotiateProtocol(['ava-6', 'ava-3.2'], {version: pkg.version}); + const protocol = negotiateProtocol(['ava-6'], {version: pkg.version}); if (protocol === null) { return; } @@ -100,141 +100,110 @@ export default function typescriptProvider({negotiateProtocol}) { ]); const testFileExtension = new RegExp(`\\.(${extensions.map(ext => escapeStringRegexp(ext)).join('|')})$`); - const watchMode = protocol.identifier === 'ava-3.2' - ? { - ignoreChange(filePath) { - if (!testFileExtension.test(filePath)) { - return false; - } - - return rewritePaths.some(([from]) => filePath.startsWith(from)); - }, - - resolveTestFile(testfile) { // Used under AVA 3.2 protocol by legacy watcher implementation. - if (!testFileExtension.test(testfile)) { - return testfile; - } - - const rewrite = rewritePaths.find(([from]) => testfile.startsWith(from)); - if (rewrite === undefined) { - return testfile; - } - - const [from, to] = rewrite; - let newExtension = '.js'; - if (testfile.endsWith('.cts')) { - newExtension = '.cjs'; - } else if (testfile.endsWith('.mts')) { - newExtension = '.mjs'; - } - - return `${to}${testfile.slice(from.length)}`.replace(testFileExtension, newExtension); - }, - } - : { - changeInterpretations, - interpretChange(filePath) { - if (config.compile === false) { - for (const [from] of rewritePaths) { - if (testFileExtension.test(filePath) && filePath.startsWith(from)) { - return changeInterpretations.waitForOutOfBandCompilation; - } + const watchMode = { + changeInterpretations, + interpretChange(filePath) { + if (config.compile === false) { + for (const [from] of rewritePaths) { + if (testFileExtension.test(filePath) && filePath.startsWith(from)) { + return changeInterpretations.waitForOutOfBandCompilation; } } + } - if (config.compile === 'tsc') { - for (const [, to] of rewritePaths) { - if (filePath.startsWith(to)) { - return changeInterpretations.ignoreCompiled; - } + if (config.compile === 'tsc') { + for (const [, to] of rewritePaths) { + if (filePath.startsWith(to)) { + return changeInterpretations.ignoreCompiled; } } + } - return changeInterpretations.unspecified; - }, - - resolvePossibleOutOfBandCompilationSources(filePath) { - if (config.compile !== false) { - return null; - } + return changeInterpretations.unspecified; + }, - // Only recognize .cjs, .mjs and .js files. - if (!/\.(c|m)?js$/.test(filePath)) { - return null; - } + resolvePossibleOutOfBandCompilationSources(filePath) { + if (config.compile !== false) { + return null; + } - for (const [from, to] of rewritePaths) { - if (!filePath.startsWith(to)) { - continue; - } + // Only recognize .cjs, .mjs and .js files. + if (!/\.(c|m)?js$/.test(filePath)) { + return null; + } - const rewritten = `${from}${filePath.slice(to.length)}`; - const possibleExtensions = []; + for (const [from, to] of rewritePaths) { + if (!filePath.startsWith(to)) { + continue; + } - if (filePath.endsWith('.cjs')) { - if (extensions.includes('cjs')) { - possibleExtensions.push({replace: /\.cjs$/, extension: 'cjs'}); - } + const rewritten = `${from}${filePath.slice(to.length)}`; + const possibleExtensions = []; - if (extensions.includes('cts')) { - possibleExtensions.push({replace: /\.cjs$/, extension: 'cts'}); - } + if (filePath.endsWith('.cjs')) { + if (extensions.includes('cjs')) { + possibleExtensions.push({replace: /\.cjs$/, extension: 'cjs'}); + } - if (possibleExtensions.length === 0) { - return null; - } + if (extensions.includes('cts')) { + possibleExtensions.push({replace: /\.cjs$/, extension: 'cts'}); } - if (filePath.endsWith('.mjs')) { - if (extensions.includes('mjs')) { - possibleExtensions.push({replace: /\.mjs$/, extension: 'mjs'}); - } + if (possibleExtensions.length === 0) { + return null; + } + } - if (extensions.includes('mts')) { - possibleExtensions.push({replace: /\.mjs$/, extension: 'mts'}); - } + if (filePath.endsWith('.mjs')) { + if (extensions.includes('mjs')) { + possibleExtensions.push({replace: /\.mjs$/, extension: 'mjs'}); + } - if (possibleExtensions.length === 0) { - return null; - } + if (extensions.includes('mts')) { + possibleExtensions.push({replace: /\.mjs$/, extension: 'mts'}); } - if (filePath.endsWith('.js')) { - if (extensions.includes('js')) { - possibleExtensions.push({replace: /\.js$/, extension: 'js'}); - } + if (possibleExtensions.length === 0) { + return null; + } + } - if (extensions.includes('ts')) { - possibleExtensions.push({replace: /\.js$/, extension: 'ts'}); - } + if (filePath.endsWith('.js')) { + if (extensions.includes('js')) { + possibleExtensions.push({replace: /\.js$/, extension: 'js'}); + } - if (extensions.includes('tsx')) { - possibleExtensions.push({replace: /\.js$/, extension: 'tsx'}); - } + if (extensions.includes('ts')) { + possibleExtensions.push({replace: /\.js$/, extension: 'ts'}); + } - if (possibleExtensions.length === 0) { - return null; - } + if (extensions.includes('tsx')) { + possibleExtensions.push({replace: /\.js$/, extension: 'tsx'}); } - const possibleDeletedFiles = []; - for (const {replace, extension} of possibleExtensions) { - const possibleFilePath = rewritten.replace(replace, `.${extension}`); + if (possibleExtensions.length === 0) { + return null; + } + } - // Pick the first file path that exists. - if (fs.existsSync(possibleFilePath)) { - return [possibleFilePath]; - } + const possibleDeletedFiles = []; + for (const {replace, extension} of possibleExtensions) { + const possibleFilePath = rewritten.replace(replace, `.${extension}`); - possibleDeletedFiles.push(possibleFilePath); + // Pick the first file path that exists. + if (fs.existsSync(possibleFilePath)) { + return [possibleFilePath]; } - return possibleDeletedFiles; + possibleDeletedFiles.push(possibleFilePath); } - return null; - }, - }; + return possibleDeletedFiles; + } + + return null; + }, + }; return { ...watchMode, diff --git a/test/compilation.js b/test/compilation.js index 4f06b74..34698f2 100644 --- a/test/compilation.js +++ b/test/compilation.js @@ -6,8 +6,8 @@ import {execaNode} from 'execa'; import createProviderMacro from './_with-provider.js'; const __dirname = path.dirname(fileURLToPath(import.meta.url)); -const withProvider = createProviderMacro('ava-3.2', '3.2.0', path.join(__dirname, 'fixtures')); -const withAltProvider = createProviderMacro('ava-3.2', '3.2.0', path.join(__dirname, 'broken-fixtures')); +const withProvider = createProviderMacro('ava-6', '6.0.0', path.join(__dirname, 'fixtures')); +const withAltProvider = createProviderMacro('ava-6', '6.0.0', path.join(__dirname, 'broken-fixtures')); test.before('deleting compiled files', async t => { t.log(await deleteAsync('test/fixtures/typescript/compiled')); diff --git a/test/fixtures/install-and-load.js b/test/fixtures/install-and-load.js index c92a633..4a5fc40 100644 --- a/test/fixtures/install-and-load.js +++ b/test/fixtures/install-and-load.js @@ -8,7 +8,7 @@ const __dirname = path.dirname(fileURLToPath(import.meta.url)); const provider = makeProvider({ negotiateProtocol() { - return {identifier: 'ava-3.2', ava: {version: '3.15.0'}, projectDir: __dirname}; + return {identifier: 'ava-6', ava: {version: '6.0.0'}, projectDir: __dirname}; }, }); diff --git a/test/load.js b/test/load.js index 35d55b2..292aa20 100644 --- a/test/load.js +++ b/test/load.js @@ -5,7 +5,7 @@ import {execaNode} from 'execa'; import createProviderMacro from './_with-provider.js'; const __dirname = path.dirname(fileURLToPath(import.meta.url)); -const withProvider = createProviderMacro('ava-3.2', '3.2.0', path.join(__dirname, 'fixtures')); +const withProvider = createProviderMacro('ava-6', '6.0.0', path.join(__dirname, 'fixtures')); const setup = async provider => ({ state: await provider.main({ diff --git a/test/protocol-ava-3.2.js b/test/protocol-ava-3.2.js deleted file mode 100644 index a19ee45..0000000 --- a/test/protocol-ava-3.2.js +++ /dev/null @@ -1,91 +0,0 @@ -import fs from 'node:fs'; -import path from 'node:path'; -import {fileURLToPath} from 'node:url'; -import test from 'ava'; -import createProviderMacro from './_with-provider.js'; - -const __dirname = path.dirname(fileURLToPath(import.meta.url)); -const pkg = JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))); -const withProvider = createProviderMacro('ava-3.2', '3.15.0'); - -const validateConfig = (t, provider, config) => { - const error = t.throws(() => provider.main({config})); - error.message = error.message.replace(`v${pkg.version}`, 'v${pkg.version}'); // eslint-disable-line no-template-curly-in-string - t.snapshot(error); -}; - -test('negotiates ava-3.2 protocol', withProvider, t => t.plan(2)); - -test('main() config validation: throw when config is not a plain object', withProvider, (t, provider) => { - validateConfig(t, provider, false); - validateConfig(t, provider, true); - validateConfig(t, provider, null); - validateConfig(t, provider, []); -}); - -test('main() config validation: throw when config contains keys other than \'extensions\', \'rewritePaths\' or \'compile\'', withProvider, (t, provider) => { - validateConfig(t, provider, {compile: false, foo: 1, rewritePaths: {'src/': 'build/'}}); -}); - -test('main() config validation: throw when config.extensions contains empty strings', withProvider, (t, provider) => { - validateConfig(t, provider, {extensions: ['']}); -}); - -test('main() config validation: throw when config.extensions contains non-strings', withProvider, (t, provider) => { - validateConfig(t, provider, {extensions: [1]}); -}); - -test('main() config validation: throw when config.extensions contains duplicates', withProvider, (t, provider) => { - validateConfig(t, provider, {extensions: ['ts', 'ts']}); -}); - -test('main() config validation: config may not be an empty object', withProvider, (t, provider) => { - validateConfig(t, provider, {}); -}); - -test('main() config validation: throw when config.compile is invalid', withProvider, (t, provider) => { - validateConfig(t, provider, {rewritePaths: {'src/': 'build/'}, compile: 1}); - validateConfig(t, provider, {rewritePaths: {'src/': 'build/'}, compile: undefined}); -}); - -test('main() config validation: rewrite paths must end in a /', withProvider, (t, provider) => { - validateConfig(t, provider, {rewritePaths: {src: 'build/', compile: false}}); - validateConfig(t, provider, {rewritePaths: {'src/': 'build', compile: false}}); -}); - -test('main() extensions: defaults to [\'ts\', \'cts\', \'mts\']', withProvider, (t, provider) => { - t.deepEqual(provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}).extensions, ['ts', 'cts', 'mts']); -}); - -test('main() extensions: returns configured extensions', withProvider, (t, provider) => { - const extensions = ['tsx']; - t.deepEqual(provider.main({config: {extensions, rewritePaths: {'src/': 'build/'}, compile: false}}).extensions, extensions); -}); - -test('main() extensions: always returns new arrays', withProvider, (t, provider) => { - const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.not(main.extensions, main.extensions); -}); - -test('main() ignoreChange()', withProvider, (t, provider) => { - const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.true(main.ignoreChange(path.join(__dirname, 'src/foo.ts'))); - t.false(main.ignoreChange(path.join(__dirname, 'build/foo.js'))); -}); - -test('main() resolveTestfile()', withProvider, (t, provider) => { - const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolveTestFile(path.join(__dirname, 'src/foo.ts')), path.join(__dirname, 'build/foo.js')); - t.is(main.resolveTestFile(path.join(__dirname, 'src/foo.cts')), path.join(__dirname, 'build/foo.cjs')); - t.is(main.resolveTestFile(path.join(__dirname, 'src/foo.mts')), path.join(__dirname, 'build/foo.mjs')); - t.is(main.resolveTestFile(path.join(__dirname, 'build/foo.js')), path.join(__dirname, 'build/foo.js')); - t.is(main.resolveTestFile(path.join(__dirname, 'foo/bar.ts')), path.join(__dirname, 'foo/bar.ts')); -}); - -test('main() updateGlobs()', withProvider, (t, provider) => { - const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.snapshot(main.updateGlobs({ - filePatterns: ['src/test.ts'], - ignoredByWatcherPatterns: ['assets/**'], - })); -}); diff --git a/test/snapshots/protocol-ava-3.2.js.md b/test/snapshots/protocol-ava-3.2.js.md deleted file mode 100644 index f2f1ad2..0000000 --- a/test/snapshots/protocol-ava-3.2.js.md +++ /dev/null @@ -1,117 +0,0 @@ -# Snapshot report for `test/protocol-ava-3.2.js` - -The actual snapshot is saved in `protocol-ava-3.2.js.snap`. - -Generated by [AVA](https://avajs.dev). - -## main() config validation: throw when config is not a plain object - -> Snapshot 1 - - Error { - message: 'Unexpected Typescript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -> Snapshot 2 - - Error { - message: 'Unexpected Typescript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -> Snapshot 3 - - Error { - message: 'Unexpected Typescript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -> Snapshot 4 - - Error { - message: 'Unexpected Typescript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: throw when config contains keys other than 'extensions', 'rewritePaths' or 'compile' - -> Snapshot 1 - - Error { - message: 'Unexpected \'foo\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: throw when config.extensions contains empty strings - -> Snapshot 1 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: throw when config.extensions contains non-strings - -> Snapshot 1 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: throw when config.extensions contains duplicates - -> Snapshot 1 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: config may not be an empty object - -> Snapshot 1 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: throw when config.compile is invalid - -> Snapshot 1 - - Error { - message: 'Invalid \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -> Snapshot 2 - - Error { - message: 'Invalid \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() config validation: rewrite paths must end in a / - -> Snapshot 1 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -> Snapshot 2 - - Error { - message: 'Missing \'compile\' property in TypeScript configuration for AVA. See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md', - } - -## main() updateGlobs() - -> Snapshot 1 - - { - filePatterns: [ - 'src/test.ts', - '!**/*.d.ts', - '!build/**', - ], - ignoredByWatcherPatterns: [ - 'assets/**', - 'build/**/*.js.map', - 'build/**/*.cjs.map', - 'build/**/*.mjs.map', - ], - } diff --git a/test/snapshots/protocol-ava-3.2.js.snap b/test/snapshots/protocol-ava-3.2.js.snap deleted file mode 100644 index 6f7ecc79e0f566f03e7f9eed56350c5dde496550..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 782 zcmV+p1M&PpRzV~=RvQ+rWLKOhYZGs*d%nR9;gk+WN^ zG*qw!-+pi_Y=iHVBPQhBJPnkriW+UPh6tGzN-j}bH)@-1*SXBB0;p7$GO8QsMO9^! z2UdV&8tTfz=iLx}+3VkVXT*s=WQODxv0uhEO>$GDuwsld(_}as5|WK3Cnp_p)giO`Ciu4F?jx0o-@5fqZ`HgOH-MA8_g}1(AFi%=QFxixWnLE{uk6yw z<6K(oEXsjy@itIp>)fDZ}R? zT)4ZN=L+-bNnuJQ7cNo8D4(1ZW!TgW5irXKo#efvNv1zVtesRo6;AQt+`rKM)z3hp zyMLTRm_{6zkwPZYF1=4@L+|nay5~%9kaEpV%Hq){C9OQDj!O?3HNjFY!#GGr{WCuz z7vq8rQm*L{vFQnEYD}F!LKm2uKlHx7A-_6IMoIn-_II(ZCtMK5@U!Gyj%lRB3`fo( z*9iH5!VJhn6?4Xd*K#8vvHt9_&WM^+hKCQ@8_Wh+Hg}byWatkn_mU_a=O#%PFO-d8 z?PPnBQL$Kz#f3!_EMwci_7>asK8O4PhjAy4U?SeSPB2%%1U~*%ThBsjBP279&z4Gl z$qRdIolPH`tu#d=^h>2=;-UVD#~1*&kl6dCoyt6M?oIF_rVq`2y+;xp)a3uCiS{-B M0LHBeX@?L10O7iOIsgCw From 2ef012974ff424fb179cb818d17fdc620cb99897 Mon Sep 17 00:00:00 2001 From: Mark Wubben Date: Sun, 5 May 2024 22:11:15 +0200 Subject: [PATCH 4/6] Upgrade XO and apply fixes --- index.js | 30 ++++++++++++------------ package.json | 2 +- test/_with-provider.js | 10 ++++---- test/fixtures/install-and-load.js | 6 ++--- test/protocol-ava-6.js | 38 +++++++++++++++---------------- 5 files changed, 43 insertions(+), 43 deletions(-) diff --git a/index.js b/index.js index 48fc16b..6590eab 100644 --- a/index.js +++ b/index.js @@ -4,8 +4,8 @@ import {pathToFileURL} from 'node:url'; import escapeStringRegexp from 'escape-string-regexp'; import {execa} from 'execa'; -const pkg = JSON.parse(fs.readFileSync(new URL('package.json', import.meta.url))); -const help = `See https://github.com/avajs/typescript/blob/v${pkg.version}/README.md`; +const package_ = JSON.parse(fs.readFileSync(new URL('package.json', import.meta.url))); +const help = `See https://github.com/avajs/typescript/blob/v${package_.version}/README.md`; function isPlainObject(x) { return x !== null && typeof x === 'object' && Reflect.getPrototypeOf(x) === Object.prototype; @@ -36,8 +36,8 @@ function validate(target, properties) { } } -async function compileTypeScript(projectDir) { - return execa('tsc', ['--incremental'], {preferLocal: true, cwd: projectDir}); +async function compileTypeScript(projectDirectory) { + return execa('tsc', ['--incremental'], {preferLocal: true, cwd: projectDirectory}); } const configProperties = { @@ -62,7 +62,7 @@ const configProperties = { isValid(extensions) { return Array.isArray(extensions) && extensions.length > 0 - && extensions.every(ext => typeof ext === 'string' && ext !== '') + && extensions.every(extension => typeof extension === 'string' && extension !== '') && new Set(extensions).size === extensions.length; }, }, @@ -75,7 +75,7 @@ const changeInterpretations = Object.freeze(Object.assign(Object.create(null), { })); export default function typescriptProvider({negotiateProtocol}) { - const protocol = negotiateProtocol(['ava-6'], {version: pkg.version}); + const protocol = negotiateProtocol(['ava-6'], {version: package_.version}); if (protocol === null) { return; } @@ -98,7 +98,7 @@ export default function typescriptProvider({negotiateProtocol}) { path.join(protocol.projectDir, from), path.join(protocol.projectDir, to), ]); - const testFileExtension = new RegExp(`\\.(${extensions.map(ext => escapeStringRegexp(ext)).join('|')})$`); + const testFileExtension = new RegExp(`\\.(${extensions.map(extension => escapeStringRegexp(extension)).join('|')})$`); const watchMode = { changeInterpretations, @@ -245,21 +245,21 @@ export default function typescriptProvider({negotiateProtocol}) { worker({extensionsToLoadAsModules, state: {extensions, rewritePaths}}) { const importJs = extensionsToLoadAsModules.includes('js'); - const testFileExtension = new RegExp(`\\.(${extensions.map(ext => escapeStringRegexp(ext)).join('|')})$`); + const testFileExtension = new RegExp(`\\.(${extensions.map(extension => escapeStringRegexp(extension)).join('|')})$`); return { - canLoad(ref) { - return testFileExtension.test(ref) && rewritePaths.some(([from]) => ref.startsWith(from)); + canLoad(reference) { + return testFileExtension.test(reference) && rewritePaths.some(([from]) => reference.startsWith(from)); }, - async load(ref, {requireFn}) { - const [from, to] = rewritePaths.find(([from]) => ref.startsWith(from)); - let rewritten = `${to}${ref.slice(from.length)}`; + async load(reference, {requireFn}) { + const [from, to] = rewritePaths.find(([from]) => reference.startsWith(from)); + let rewritten = `${to}${reference.slice(from.length)}`; let useImport = true; - if (ref.endsWith('.cts')) { + if (reference.endsWith('.cts')) { rewritten = rewritten.replace(/\.cts$/, '.cjs'); useImport = false; - } else if (ref.endsWith('.mts')) { + } else if (reference.endsWith('.mts')) { rewritten = rewritten.replace(/\.mts$/, '.mjs'); } else { rewritten = rewritten.replace(testFileExtension, '.js'); diff --git a/package.json b/package.json index a414772..e698d64 100644 --- a/package.json +++ b/package.json @@ -31,7 +31,7 @@ "c8": "^8.0.0", "del": "^7.0.0", "typescript": "^5.1.3", - "xo": "^0.54.2" + "xo": "^0.58.0" }, "c8": { "reporter": [ diff --git a/test/_with-provider.js b/test/_with-provider.js index fbe3ea7..6a23896 100644 --- a/test/_with-provider.js +++ b/test/_with-provider.js @@ -4,20 +4,20 @@ import {fileURLToPath} from 'node:url'; import makeProvider from '@ava/typescript'; const __dirname = path.dirname(fileURLToPath(import.meta.url)); -const pkg = JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))); +const package_ = JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))); -const createProviderMacro = (identifier, avaVersion, projectDir = __dirname) => (t, run) => run(t, makeProvider({ +const createProviderMacro = (identifier, avaVersion, projectDirectory = __dirname) => (t, run) => run(t, makeProvider({ negotiateProtocol(identifiers, {version}) { t.true(identifiers.includes(identifier)); - t.is(version, pkg.version); + t.is(version, package_.version); return { ava: {avaVersion}, identifier, normalizeGlobPatterns: patterns => patterns, async findFiles({patterns}) { - return patterns.map(file => path.join(projectDir, file)); + return patterns.map(file => path.join(projectDirectory, file)); }, - projectDir, + projectDir: projectDirectory, }; }, })); diff --git a/test/fixtures/install-and-load.js b/test/fixtures/install-and-load.js index 4a5fc40..e5df78e 100644 --- a/test/fixtures/install-and-load.js +++ b/test/fixtures/install-and-load.js @@ -18,8 +18,8 @@ const worker = provider.worker({ ...JSON.parse(process.argv[2]), }); -const ref = path.resolve(process.argv[3]); +const reference = path.resolve(process.argv[3]); -if (worker.canLoad(ref)) { - worker.load(ref, {requireFn: createRequire(import.meta.url)}); +if (worker.canLoad(reference)) { + worker.load(reference, {requireFn: createRequire(import.meta.url)}); } diff --git a/test/protocol-ava-6.js b/test/protocol-ava-6.js index 55ed841..773f596 100644 --- a/test/protocol-ava-6.js +++ b/test/protocol-ava-6.js @@ -4,13 +4,13 @@ import {fileURLToPath} from 'node:url'; import test from 'ava'; import createProviderMacro from './_with-provider.js'; -const projectDir = path.dirname(fileURLToPath(import.meta.url)); -const pkg = JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))); +const projectDirectory = path.dirname(fileURLToPath(import.meta.url)); +const package_ = JSON.parse(fs.readFileSync(new URL('../package.json', import.meta.url))); const withProvider = createProviderMacro('ava-6', '5.3.0'); const validateConfig = (t, provider, config) => { const error = t.throws(() => provider.main({config})); - error.message = error.message.replace(`v${pkg.version}`, 'v${pkg.version}'); // eslint-disable-line no-template-curly-in-string + error.message = error.message.replace(`v${package_.version}`, 'v${pkg.version}'); // eslint-disable-line no-template-curly-in-string t.snapshot(error); }; @@ -77,64 +77,64 @@ test('main() updateGlobs()', withProvider, (t, provider) => { test('main() interpretChange() without compilation', withProvider, (t, provider) => { const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.interpretChange(path.join(projectDir, 'src/foo.ts')), main.changeInterpretations.waitForOutOfBandCompilation); - t.is(main.interpretChange(path.join(projectDir, 'build/foo.js')), main.changeInterpretations.unspecified); - t.is(main.interpretChange(path.join(projectDir, 'src/foo.txt')), main.changeInterpretations.unspecified); + t.is(main.interpretChange(path.join(projectDirectory, 'src/foo.ts')), main.changeInterpretations.waitForOutOfBandCompilation); + t.is(main.interpretChange(path.join(projectDirectory, 'build/foo.js')), main.changeInterpretations.unspecified); + t.is(main.interpretChange(path.join(projectDirectory, 'src/foo.txt')), main.changeInterpretations.unspecified); }); test('main() interpretChange() with compilation', withProvider, (t, provider) => { const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: 'tsc'}}); - t.is(main.interpretChange(path.join(projectDir, 'src/foo.ts')), main.changeInterpretations.unspecified); - t.is(main.interpretChange(path.join(projectDir, 'build/foo.js')), main.changeInterpretations.ignoreCompiled); - t.is(main.interpretChange(path.join(projectDir, 'src/foo.txt')), main.changeInterpretations.unspecified); + t.is(main.interpretChange(path.join(projectDirectory, 'src/foo.ts')), main.changeInterpretations.unspecified); + t.is(main.interpretChange(path.join(projectDirectory, 'build/foo.js')), main.changeInterpretations.ignoreCompiled); + t.is(main.interpretChange(path.join(projectDirectory, 'src/foo.txt')), main.changeInterpretations.unspecified); }); test('main() resolvePossibleOutOfBandCompilationSources() with compilation', withProvider, (t, provider) => { const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: 'tsc'}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.js')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.js')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() unknown extension', withProvider, (t, provider) => { const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.bar')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.bar')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() not a build path', withProvider, (t, provider) => { const main = provider.main({config: {rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'lib/foo.js')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'lib/foo.js')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() .cjs but .cts not configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['ts'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.cjs')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.cjs')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() .mjs but .mts not configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['ts'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.mjs')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.mjs')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() .js but .ts not configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['cts'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.js')), null); + t.is(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.js')), null); }); test('main() resolvePossibleOutOfBandCompilationSources() .cjs and .cjs and .cts configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['cjs', 'cts'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.cjs')), [path.join(projectDir, 'src/foo.cjs'), path.join(projectDir, 'src/foo.cts')]); + t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.cjs')), [path.join(projectDirectory, 'src/foo.cjs'), path.join(projectDirectory, 'src/foo.cts')]); }); test('main() resolvePossibleOutOfBandCompilationSources() .mjs and .mjs and .mts configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['mjs', 'mts'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.mjs')), [path.join(projectDir, 'src/foo.mjs'), path.join(projectDir, 'src/foo.mts')]); + t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.mjs')), [path.join(projectDirectory, 'src/foo.mjs'), path.join(projectDirectory, 'src/foo.mts')]); }); test('main() resolvePossibleOutOfBandCompilationSources() .js and .js, .ts and .tsx configured', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['js', 'ts', 'tsx'], rewritePaths: {'src/': 'build/'}, compile: false}}); - t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'build/foo.js')), [path.join(projectDir, 'src/foo.js'), path.join(projectDir, 'src/foo.ts'), path.join(projectDir, 'src/foo.tsx')]); + t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'build/foo.js')), [path.join(projectDirectory, 'src/foo.js'), path.join(projectDirectory, 'src/foo.ts'), path.join(projectDirectory, 'src/foo.tsx')]); }); test('main() resolvePossibleOutOfBandCompilationSources() returns the first possible path that exists', withProvider, (t, provider) => { const main = provider.main({config: {extensions: ['js', 'ts', 'tsx'], rewritePaths: {'fixtures/load/': 'fixtures/load/compiled/'}, compile: false}}); - t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDir, 'fixtures/load/compiled/index.js')), [path.join(projectDir, 'fixtures/load/index.ts')]); + t.deepEqual(main.resolvePossibleOutOfBandCompilationSources(path.join(projectDirectory, 'fixtures/load/compiled/index.js')), [path.join(projectDirectory, 'fixtures/load/index.ts')]); }); From 2beed01712089e3166353f79f8d71705c30fa7a8 Mon Sep 17 00:00:00 2001 From: Mark Wubben Date: Sun, 5 May 2024 22:12:21 +0200 Subject: [PATCH 5/6] Update dependencies --- package.json | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-) diff --git a/package.json b/package.json index e698d64..00429b2 100644 --- a/package.json +++ b/package.json @@ -24,13 +24,13 @@ }, "dependencies": { "escape-string-regexp": "^5.0.0", - "execa": "^7.1.1" + "execa": "^8.0.1" }, "devDependencies": { - "ava": "^5.3.1", - "c8": "^8.0.0", - "del": "^7.0.0", - "typescript": "^5.1.3", + "ava": "^6.1.2", + "c8": "^9.1.0", + "del": "^7.1.0", + "typescript": "^5.4.5", "xo": "^0.58.0" }, "c8": { @@ -44,10 +44,12 @@ "files": [ "!test/broken-fixtures/**" ], - "ignoredByWatcher": [ - "test/fixtures/**", - "test/broken-fixtures/**" - ], + "watcher": { + "ignoreChanges": [ + "test/fixtures/**", + "test/broken-fixtures/**" + ] + }, "timeout": "60s" }, "xo": { From a9eca56c97b457892e3f269633bd33a8c688905d Mon Sep 17 00:00:00 2001 From: Silas Rech Date: Sun, 5 May 2024 22:13:19 +0200 Subject: [PATCH 6/6] Include Node.js 22 in supported engines and test matrix --- .github/workflows/ci.yml | 2 +- package.json | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 99193b6..cf8b8ba 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -13,7 +13,7 @@ jobs: strategy: fail-fast: false matrix: - node-version: [^18.18, ^20.8, ^21] + node-version: [^18.18, ^20.8, ^21, ^22] os: [ubuntu-latest, windows-latest] steps: - uses: actions/checkout@v4 diff --git a/package.json b/package.json index 00429b2..26de27a 100644 --- a/package.json +++ b/package.json @@ -3,7 +3,7 @@ "version": "4.1.0", "description": "TypeScript provider for AVA", "engines": { - "node": "^18.18 || ^20.8 || ^21" + "node": "^18.18 || ^20.8 || ^21 || ^22" }, "files": [ "index.js"