Context
PR #1641 review flagged that new/updated tests use fireEvent (low-level event dispatch) instead of userEvent (realistic user interaction simulation). userEvent is the recommended approach per Testing Library best practices. This covers 112 fireEvent calls across 7 files.
Dependency
@testing-library/user-event needs to be added as a devDependency:
npm install --save-dev @testing-library/user-event
Migration patterns
Each file will:
- Add
import userEvent from '@testing-library/user-event';
- Remove
fireEvent from the @testing-library/react import (if no longer needed)
- Add
const user = userEvent.setup(); at the top of the describe block
- Make affected tests
async (if not already)
- Apply these conversions:
fireEvent pattern |
userEvent replacement |
fireEvent.click(el) |
await user.click(el) |
fireEvent.change(input, { target: { value: 'x' } }) |
await user.clear(input); await user.type(input, 'x') |
fireEvent.change(select, { target: { value: 'v' } }) |
await user.selectOptions(select, 'v') |
fireEvent.blur(el, { target: { value: 'x', name: 'n' } }) |
await user.type(el, 'x'); await user.tab() (clear first if needed) |
fireEvent.blur(el, { target: { value: '', name: 'n' } }) |
await user.click(el); await user.tab() |
fireEvent.blur(el) (no target) |
await user.click(el); await user.tab() |
fireEvent.focus(el) |
await user.click(el) |
fireEvent.mouseDown(el) |
Keep as fireEvent.mouseDown(el) (only 2 instances; tests preventDefault) |
Files (in order of complexity)
1. src/register/RegistrationFields/NameField/NameField.test.jsx (8 calls)
- 6x blur (with target value), 2x focus
- All sync → make async
2. src/forgot-password/tests/ForgotPasswordPage.test.jsx (14 calls)
- 5x change, 7x click, 1x blur, 1x focus
- 5 sync tests → make async; 4 already async
3. src/register/RegistrationFields/UsernameField/UsernameField.test.jsx (15 calls)
- 6x blur, 4x focus, 2x change, 3x click
- All sync → make async
4. src/register/RegistrationFields/EmailField/EmailField.test.jsx (16 calls)
- 12x blur, 2x click, 2x focus
- All sync → make async
5. src/progressive-profiling/tests/ProgressiveProfiling.test.jsx (14 calls)
- 8x click, 4x change (2 are selects), 2x mouseDown (keep as fireEvent)
- All sync → make async (except mouseDown test can stay sync)
6. src/reset-password/tests/ResetPasswordPage.test.jsx (19 calls)
- 10x change, 6x click, 2x focus, 1x blur
- All already async
7. src/login/tests/LoginPage.test.jsx (26 calls)
- 13x change, 11x click, 2x focus
- 16 sync → make async; 10 already async
Context
PR #1641 review flagged that new/updated tests use
fireEvent(low-level event dispatch) instead ofuserEvent(realistic user interaction simulation).userEventis the recommended approach per Testing Library best practices. This covers 112fireEventcalls across 7 files.Dependency
@testing-library/user-eventneeds to be added as a devDependency:Migration patterns
Each file will:
import userEvent from '@testing-library/user-event';fireEventfrom the@testing-library/reactimport (if no longer needed)const user = userEvent.setup();at the top of thedescribeblockasync(if not already)fireEventpatternuserEventreplacementfireEvent.click(el)await user.click(el)fireEvent.change(input, { target: { value: 'x' } })await user.clear(input); await user.type(input, 'x')fireEvent.change(select, { target: { value: 'v' } })await user.selectOptions(select, 'v')fireEvent.blur(el, { target: { value: 'x', name: 'n' } })await user.type(el, 'x'); await user.tab()(clear first if needed)fireEvent.blur(el, { target: { value: '', name: 'n' } })await user.click(el); await user.tab()fireEvent.blur(el)(no target)await user.click(el); await user.tab()fireEvent.focus(el)await user.click(el)fireEvent.mouseDown(el)fireEvent.mouseDown(el)(only 2 instances; testspreventDefault)Files (in order of complexity)
1.
src/register/RegistrationFields/NameField/NameField.test.jsx(8 calls)2.
src/forgot-password/tests/ForgotPasswordPage.test.jsx(14 calls)3.
src/register/RegistrationFields/UsernameField/UsernameField.test.jsx(15 calls)4.
src/register/RegistrationFields/EmailField/EmailField.test.jsx(16 calls)5.
src/progressive-profiling/tests/ProgressiveProfiling.test.jsx(14 calls)6.
src/reset-password/tests/ResetPasswordPage.test.jsx(19 calls)7.
src/login/tests/LoginPage.test.jsx(26 calls)