diff --git a/.circleci/config.yml b/.circleci/config.yml index fcee3ee8e014..578043e864e6 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -58,7 +58,7 @@ jobs: - run: *install - save-cache: *save-cache - run: - command: JEST_CIRCUS=1 yarn test-ci-partial + command: JEST_CIRCUS=1 yarn test-ci-partial && JEST_CIRCUS=1 yarn test-leak - store_test_results: path: reports/junit diff --git a/CHANGELOG.md b/CHANGELOG.md index 8052d1334837..9e4741b83665 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -8,6 +8,8 @@ ### Performance +- `[jest-circus]` Fix memory leak when running in band ([#9934](https://github.com/facebook/jest/pull/9934)) + ## 25.5.2 ### Fixes diff --git a/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts b/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts index 4630f16c56bb..f5653ebf5927 100644 --- a/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts +++ b/packages/jest-circus/src/legacy-code-todo-rewrite/jestAdapter.ts @@ -11,6 +11,7 @@ import type {JestEnvironment} from '@jest/environment'; import type {TestResult} from '@jest/test-result'; import type {RuntimeType as Runtime} from 'jest-runtime'; import type {SnapshotStateType} from 'jest-snapshot'; +import {deepCyclicCopy} from 'jest-util'; const FRAMEWORK_INITIALIZER = path.resolve(__dirname, './jestAdapterInit.js'); const EXPECT_INITIALIZER = path.resolve(__dirname, './jestExpect.js'); @@ -101,7 +102,13 @@ const jestAdapter = async ( globalConfig, testPath, }); - return _addSnapshotData(results, snapshotState); + + _addSnapshotData(results, snapshotState); + + // We need to copy the results object to ensure we don't leaks the prototypes + // from the VM. Jasmine creates the result objects in the parent process, we + // should consider doing that for circus as well. + return deepCyclicCopy(results, {keepPrototype: false}); }; const _addSnapshotData = ( @@ -131,7 +138,6 @@ const _addSnapshotData = ( results.snapshot.unchecked = !status.deleted ? uncheckedCount : 0; // Copy the array to prevent memory leaks results.snapshot.uncheckedKeys = Array.from(uncheckedKeys); - return results; }; export = jestAdapter;