-
-
Notifications
You must be signed in to change notification settings - Fork 31
feat(core): support custom test environments #1287
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Open
9aoy
wants to merge
36
commits into
main
Choose a base branch
from
feat/custom-test-environment
base: main
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Open
Changes from all commits
Commits
Show all changes
36 commits
Select commit
Hold shift + click to select a range
4425446
feat(core): support custom test environments
9aoy 1fa7ba8
fix: align custom environment resolution and docs
9aoy 21fc374
fix: custom environments, transform mode, and review feedback
9aoy d76a0cd
style: format test files
9aoy 019d878
fix: stabilize custom test environment resolution
9aoy 3ff7c7d
fix: lint
9aoy c5f69a5
fix: expose package environment marker during setup
9aoy ea7d542
docs: update custom-environment-vs-setup-files
9aoy ca4c2b4
docs: add Test environment types
9aoy 6f32f28
docs: add Browser Mode tip
9aoy e3f6a20
fix(core): refine custom environment loading
9aoy f37d878
Merge remote-tracking branch 'origin/main' into feat/custom-test-envi…
9aoy 4223d16
fix(core): resolve test environment before worker run
9aoy bb8b3d0
chore: merge main into custom test environment
9aoy 2c18728
chore: format Vitest migration docs
9aoy 91a5e67
fix(core): continue environment fallback after import errors
9aoy 6a72fec
fix(core): surface custom environment import errors
9aoy 13ce612
fix(core): report fallback environment import errors
9aoy db997ce
docs: update custom environment guide
9aoy be31c9c
docs: clarify custom environment migration
9aoy 8be2ee7
fix: resolve custom environment packages from project roots
9aoy 33cb79b
fix: defer custom environment imports to worker
9aoy bded029
refactor: keep environment loading in worker
9aoy e17b033
fix: align environment package fallback with node resolution
9aoy f5e418a
fix: resolve environment packages with rspack resolver
9aoy 51ca46e
fix: avoid require condition for environment imports
9aoy 348cb4f
docs: move custom environment migration guide
9aoy 470b0f5
chore: merge main and update custom env target
9aoy caad7f5
Merge remote-tracking branch 'origin/main' into 9aoy/pr-1287-resolve-…
9aoy 69b1295
fix(core): type environment comments
9aoy fdeeb59
fix: address environment review feedback
9aoy ff4dc2b
fix: keep watch plugin snapshots stable
9aoy c88dc86
fix: refresh custom environment watch reruns
9aoy b6d4c1a
fix: handle optional watch changed files
9aoy 3467532
fix: refresh custom environment workers in watch
9aoy aabbe8c
fix: watch custom environment dependencies
9aoy File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| import fs from 'node:fs'; | ||
| import { dirname, join } from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { describe, expect, it } from '@rstest/core'; | ||
| import { runCli } from './utils'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = dirname(__filename); | ||
| const teardownFile = join( | ||
| __dirname, | ||
| 'fixtures', | ||
| 'test', | ||
| 'custom-node-environment.teardown.txt', | ||
| ); | ||
|
|
||
| describe('custom builtin node environment', () => { | ||
| it('should load a local custom environment that extends builtin node', async () => { | ||
| fs.rmSync(teardownFile, { force: true }); | ||
|
|
||
| const { expectExecSuccess } = await runCli( | ||
| 'test/customNodeEnvironment', | ||
| undefined, | ||
| { | ||
| args: ['--config', 'rstest.customNodeEnvironment.config.mts'], | ||
| }, | ||
| ); | ||
|
|
||
| await expectExecSuccess(); | ||
|
|
||
| expect(fs.readFileSync(teardownFile, 'utf8')).toBe('node-marker'); | ||
|
|
||
| fs.rmSync(teardownFile, { force: true }); | ||
| }); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| import fs from 'node:fs'; | ||
| import { dirname, join } from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { describe, expect, it } from '@rstest/core'; | ||
| import { runCli } from './utils'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = dirname(__filename); | ||
| const teardownFile = join( | ||
| __dirname, | ||
| 'fixtures', | ||
| 'test', | ||
| 'custom-environment.teardown.txt', | ||
| ); | ||
|
|
||
| describe('custom environment', () => { | ||
| it('should load a local custom environment and extend builtin environments', async () => { | ||
| fs.rmSync(teardownFile, { force: true }); | ||
|
|
||
| const { expectExecSuccess } = await runCli( | ||
| 'test/customEnvironment', | ||
| undefined, | ||
| { | ||
| args: ['--config', 'rstest.customEnvironment.config.mts'], | ||
| }, | ||
| ); | ||
|
|
||
| await expectExecSuccess(); | ||
|
|
||
| expect(fs.readFileSync(teardownFile, 'utf8')).toBe('custom-marker'); | ||
|
|
||
| fs.rmSync(teardownFile, { force: true }); | ||
| }); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
28 changes: 28 additions & 0 deletions
28
e2e/dom/fixtures/rstest-environment-package-marker/index.mjs
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,28 @@ | ||
| import { writeFile } from 'node:fs/promises'; | ||
| import { dirname, join } from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
|
|
||
| const __dirname = dirname(fileURLToPath(import.meta.url)); | ||
| const teardownFile = join( | ||
| __dirname, | ||
| '..', | ||
| 'test', | ||
| 'package-environment.teardown.txt', | ||
| ); | ||
|
|
||
| /** @type {import('@rstest/core').TestEnvironment<typeof globalThis, { marker: string }>} */ | ||
| const environment = { | ||
| name: 'package-marker', | ||
| async setup(global, options) { | ||
| global.__PACKAGE_ENV_MARKER__ = options.marker; | ||
|
|
||
| return { | ||
| async teardown() { | ||
| delete global.__PACKAGE_ENV_MARKER__; | ||
| await writeFile(teardownFile, options.marker, 'utf8'); | ||
| }, | ||
| }; | ||
| }, | ||
| }; | ||
|
|
||
| export default environment; |
8 changes: 8 additions & 0 deletions
8
e2e/dom/fixtures/rstest-environment-package-marker/package.json
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,8 @@ | ||
| { | ||
| "name": "rstest-environment-package-marker", | ||
| "private": true, | ||
| "type": "module", | ||
| "exports": { | ||
| "import": "./index.mjs" | ||
| } | ||
| } |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,17 @@ | ||
| import { defineConfig, type RstestConfig } from '@rstest/core'; | ||
| import rsbuildConfig from './rsbuild.config'; | ||
|
|
||
| export default defineConfig({ | ||
| ...(rsbuildConfig as RstestConfig), | ||
| setupFiles: ['./test/setup.ts'], | ||
| testEnvironment: { | ||
| name: './test/customEnvironment.mjs', | ||
| target: 'web', | ||
| options: { | ||
| marker: 'custom-marker', | ||
| jsdom: { | ||
| url: 'https://custom-env.example/', | ||
| }, | ||
| }, | ||
| }, | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,12 @@ | ||
| import { defineConfig, type RstestConfig } from '@rstest/core'; | ||
| import rsbuildConfig from './rsbuild.config'; | ||
|
|
||
| export default defineConfig({ | ||
| ...(rsbuildConfig as RstestConfig), | ||
| testEnvironment: { | ||
| name: './test/customNodeEnvironment.mjs', | ||
| options: { | ||
| marker: 'node-marker', | ||
| }, | ||
| }, | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,12 @@ | ||
| import { defineConfig, type RstestConfig } from '@rstest/core'; | ||
| import rsbuildConfig from './rsbuild.config'; | ||
|
|
||
| export default defineConfig({ | ||
| ...(rsbuildConfig as RstestConfig), | ||
| testEnvironment: { | ||
| name: 'package-marker', | ||
| options: { | ||
| marker: 'package-marker', | ||
| }, | ||
| }, | ||
| }); | ||
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,28 @@ | ||
| import fs from 'node:fs'; | ||
| import path from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { builtinEnvironments } from '@rstest/core'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = path.dirname(__filename); | ||
| const teardownFile = path.join(__dirname, 'custom-environment.teardown.txt'); | ||
|
|
||
| export default { | ||
| name: 'custom-jsdom', | ||
| async setup(global, options) { | ||
| const jsdomEnvironment = await builtinEnvironments.jsdom.setup( | ||
| global, | ||
| options.jsdom ?? {}, | ||
| ); | ||
|
|
||
| global.__CUSTOM_ENV_MARKER__ = options.marker; | ||
|
|
||
| return { | ||
| async teardown() { | ||
| delete global.__CUSTOM_ENV_MARKER__; | ||
| fs.writeFileSync(teardownFile, String(options.marker)); | ||
| await jsdomEnvironment.teardown(); | ||
| }, | ||
| }; | ||
| }, | ||
| }; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,8 @@ | ||
| import { expect, test } from '@rstest/core'; | ||
|
|
||
| test('custom environment can extend builtin jsdom', () => { | ||
| expect(window.location.href).toBe('https://custom-env.example/'); | ||
| expect( | ||
| (globalThis as { __CUSTOM_ENV_MARKER__?: string }).__CUSTOM_ENV_MARKER__, | ||
| ).toBe('custom-marker'); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,31 @@ | ||
| import fs from 'node:fs'; | ||
| import path from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { builtinEnvironments } from '@rstest/core'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = path.dirname(__filename); | ||
| const teardownFile = path.join( | ||
| __dirname, | ||
| 'custom-node-environment.teardown.txt', | ||
| ); | ||
|
|
||
| export default { | ||
| name: 'custom-node', | ||
| async setup(global, options) { | ||
| const nodeEnvironment = await builtinEnvironments.node.setup( | ||
| global, | ||
| options, | ||
| ); | ||
|
|
||
| global.__CUSTOM_NODE_ENV_MARKER__ = options.marker; | ||
|
|
||
| return { | ||
| async teardown() { | ||
| delete global.__CUSTOM_NODE_ENV_MARKER__; | ||
| fs.writeFileSync(teardownFile, String(options.marker)); | ||
| await nodeEnvironment.teardown(); | ||
| }, | ||
| }; | ||
| }, | ||
| }; |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,10 @@ | ||
| import { expect, test } from '@rstest/core'; | ||
|
|
||
| test('custom environment can extend builtin node', () => { | ||
| expect( | ||
| (globalThis as { __CUSTOM_NODE_ENV_MARKER__?: string }) | ||
| .__CUSTOM_NODE_ENV_MARKER__, | ||
| ).toBe('node-marker'); | ||
| expect('window' in globalThis).toBe(false); | ||
| expect(typeof process.cwd()).toBe('string'); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,8 @@ | ||
| import { expect, test } from '@rstest/core'; | ||
|
|
||
| test('custom environment can load from rstest-environment-* package fallback', () => { | ||
| expect( | ||
| (globalThis as { __PACKAGE_ENV_MARKER__?: string }).__PACKAGE_ENV_MARKER__, | ||
| ).toBe('package-marker'); | ||
| expect('window' in globalThis).toBe(false); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,34 @@ | ||
| import fs from 'node:fs'; | ||
| import { dirname, join } from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { describe, expect, it } from '@rstest/core'; | ||
| import { runCli } from './utils'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = dirname(__filename); | ||
| const teardownFile = join( | ||
| __dirname, | ||
| 'fixtures', | ||
| 'test', | ||
| 'package-environment.teardown.txt', | ||
| ); | ||
|
|
||
| describe('package environment fallback', () => { | ||
| it('should resolve rstest-environment-* packages from testEnvironment.name', async () => { | ||
| fs.rmSync(teardownFile, { force: true }); | ||
|
|
||
| const { expectExecSuccess } = await runCli( | ||
| 'test/packageEnvironment', | ||
| undefined, | ||
| { | ||
| args: ['--config', 'rstest.packageEnvironment.config.mts'], | ||
| }, | ||
| ); | ||
|
|
||
| await expectExecSuccess(); | ||
|
|
||
| expect(fs.readFileSync(teardownFile, 'utf8')).toBe('package-marker'); | ||
|
|
||
| fs.rmSync(teardownFile, { force: true }); | ||
| }); | ||
| }); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,84 @@ | ||
| import path from 'node:path'; | ||
| import { fileURLToPath } from 'node:url'; | ||
| import { describe, expect, it, rs } from '@rstest/core'; | ||
| import { prepareFixtures, runRstestCli } from '../scripts'; | ||
|
|
||
| const __filename = fileURLToPath(import.meta.url); | ||
| const __dirname = path.dirname(__filename); | ||
|
|
||
| rs.setConfig({ | ||
| retry: 3, | ||
| }); | ||
|
|
||
| describe.skipIf(process.platform === 'win32')( | ||
| 'watch custom environment', | ||
| () => { | ||
| it('should re-run all tests when custom environment file changes', async () => { | ||
| const fixturesTargetPath = `${__dirname}/fixtures-test-custom-environment${process.env.RSTEST_OUTPUT_MODULE !== 'false' ? '-module' : ''}`; | ||
|
|
||
| const { fs } = await prepareFixtures({ | ||
| fixturesPath: `${__dirname}/fixtures-custom-environment`, | ||
| fixturesTargetPath, | ||
| }); | ||
|
|
||
| const { cli } = await runRstestCli({ | ||
| command: 'rstest', | ||
| args: ['watch', '--disableConsoleIntercept'], | ||
| options: { | ||
| nodeOptions: { | ||
| cwd: fixturesTargetPath, | ||
| }, | ||
| }, | ||
| }); | ||
|
|
||
| await cli.waitForStdout('Duration'); | ||
| expect(cli.stdout).toMatch('Tests 1 passed'); | ||
| expect(cli.stdout).not.toMatch('Test files to re-run:'); | ||
|
|
||
| const environmentPath = path.join( | ||
| fixturesTargetPath, | ||
| 'test-environment.mjs', | ||
| ); | ||
| const environmentHelperPath = path.join( | ||
| fixturesTargetPath, | ||
| 'environment-helper.mjs', | ||
| ); | ||
|
|
||
| cli.resetStd(); | ||
| fs.update(environmentPath, (content) => { | ||
| return content.replace( | ||
| 'global.__CUSTOM_ENV_MARKER__ = marker;', | ||
| 'global.__CUSTOM_ENV_MARKER__ = `${marker}-modified`;', | ||
| ); | ||
| }); | ||
| fs.update(path.join(fixturesTargetPath, 'index.test.ts'), (content) => { | ||
| return content.replace("'initial'", "'initial-modified'"); | ||
| }); | ||
|
|
||
| await cli.waitForStdout('Duration'); | ||
| expect(cli.stdout).toMatch('Tests 1 passed'); | ||
|
|
||
| cli.resetStd(); | ||
| fs.update(path.join(fixturesTargetPath, 'index.test.ts'), (content) => { | ||
| return content.replace("'initial-modified'", "'dependency-modified'"); | ||
| }); | ||
|
|
||
| await cli.waitForStdout('Tests 1 failed'); | ||
|
|
||
| cli.resetStd(); | ||
| fs.update(environmentHelperPath, (content) => { | ||
| return content.replace("'initial'", "'dependency'"); | ||
| }); | ||
|
|
||
| await cli.waitForStdout('Duration'); | ||
| expect(cli.stdout).toMatch('Tests 1 passed'); | ||
|
|
||
| cli.resetStd(); | ||
| fs.delete(environmentPath); | ||
|
|
||
| await cli.waitForStderr('Failed to resolve testEnvironment'); | ||
|
|
||
| cli.exec.kill(); | ||
| }); | ||
| }, | ||
| ); |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1 @@ | ||
| export const marker = 'initial'; |
Oops, something went wrong.
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
Uh oh!
There was an error while loading. Please reload this page.