From 33dd46c71f9772a0407a1e34124b655fa8551b7e Mon Sep 17 00:00:00 2001 From: Norbert de Langen Date: Thu, 11 Sep 2025 10:34:55 +0200 Subject: [PATCH] fix: optimize userEvent.type performance by filtering eventWrapper from instrumentation Add getKeys filter to exclude 'eventWrapper' property from instrumenter calls to prevent performance regression in userEvent.type operations. This addresses the slowdown reported when upgrading from Storybook 8 to 9 with addon-vitest. The instrumenter was spending significant time sorting large arrays of calls that included the eventWrapper property, which is not needed for testing interactions. By filtering it out at the instrumentation level, we avoid unnecessary processing overhead. --- code/core/src/test/preview.ts | 5 ++++- code/core/src/test/testing-library.ts | 3 ++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/code/core/src/test/preview.ts b/code/core/src/test/preview.ts index 0fb276a7215b..e2e8cfafd4ac 100644 --- a/code/core/src/test/preview.ts +++ b/code/core/src/test/preview.ts @@ -96,7 +96,10 @@ const enhanceContext: LoaderFunction = async (context) => { if (clipboard) { context.userEvent = instrument( { userEvent: uninstrumentedUserEvent.setup() }, - { intercept: true } + { + intercept: true, + getKeys: (obj) => Object.keys(obj).filter((key) => key !== 'eventWrapper'), + } ).userEvent; // Restore original clipboard, which was replaced with a stub by userEvent.setup() diff --git a/code/core/src/test/testing-library.ts b/code/core/src/test/testing-library.ts index 4c3df3ece65f..3c9fb5a6d1d2 100644 --- a/code/core/src/test/testing-library.ts +++ b/code/core/src/test/testing-library.ts @@ -15,6 +15,7 @@ type TestingLibraryDom = typeof domTestingLibrary; const testingLibrary = instrument( { ...domTestingLibrary }, { + getKeys: (obj) => Object.keys(obj).filter((key) => key !== 'eventWrapper'), intercept: (method, path) => path[0] === 'fireEvent' || method.startsWith('find') || method.startsWith('waitFor'), } @@ -118,5 +119,5 @@ export const uninstrumentedUserEvent = _userEvent.userEvent; export const { userEvent }: { userEvent: UserEvent['userEvent'] } = instrument( { userEvent: _userEvent.userEvent }, - { intercept: true } + { intercept: true, getKeys: (obj) => Object.keys(obj).filter((key) => key !== 'eventWrapper') } );