From c5ebe2325663ef99efdc6508a960d06f47592560 Mon Sep 17 00:00:00 2001 From: Conor Hawes Date: Fri, 4 Aug 2023 11:34:43 -0400 Subject: [PATCH 1/4] Migrate paginator --- src/controls/paginator/page-link.js | 1 + test/controls/paginator/paginator.test.js | 104 ++++++++++++---------- 2 files changed, 57 insertions(+), 48 deletions(-) diff --git a/src/controls/paginator/page-link.js b/src/controls/paginator/page-link.js index f4e6b2d3..dcf2635a 100644 --- a/src/controls/paginator/page-link.js +++ b/src/controls/paginator/page-link.js @@ -22,6 +22,7 @@ function PageLink({ className, active, onClick, children, ...rest }) { return (
  • { - const wrapper = mount() - expect(wrapper.find('.prev').exists()).toBe(true) - wrapper.setProps({ value: 1 }) - expect(wrapper.find('.prev').exists()).toBe(false) +test('Previous control renders unless value is min', () => { + const { rerender } = render() + expect(screen.getByRole('link', { name: /previous page/i })).toBeInTheDocument() + rerender() + expect(screen.queryByRole('link', { name: /previous page/i })).not.toBeInTheDocument() }) -test('Next button renders unless value is max', () => { - const wrapper = mount() - expect(wrapper.find('.next').exists()).toBe(true) - wrapper.setProps({ value: 10 }) - expect(wrapper.find('.next').exists()).toBe(false) +test('Next control renders unless value is max', () => { + const { rerender } = render() + expect(screen.getByRole('link', { name: /next page/i })).toBeInTheDocument() + rerender() + expect(screen.queryByRole('link', { name: /next page/i })).not.toBeInTheDocument() }) -test('Button with current value is marked as active', () => { - const wrapper = mount() - expect(wrapper.find('.active').text()).toBe('5') +test('Control with current value is marked as active', () => { + render() + expect(screen.getByText(5).parentElement).toHaveClass('active') }) -test('Button click sets value', () => { +test('Control click sets value', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + + render( ) - wrapper.find('li > a').at(2).simulate('click') + await user.click(screen.getAllByRole('link').at(2)) expect(onChange).toHaveBeenCalledWith(4) }) -test('Previous button decrements value', () => { +test('Previous control decrements value', async () => { const onChange = jest.fn() - const wrapper = mount( - + const user = userEvent.setup() + const currentValue = 5 + render( + ) - wrapper.find('li > a').first().simulate('click') - expect(onChange).toHaveBeenCalledWith(4) + await user.click(screen.getByRole('link', { name: /previous page/i })) + expect(onChange).toHaveBeenCalledWith(currentValue - 1) }) -test('Next button increments value', () => { +test('Next control increments value', async () => { const onChange = jest.fn() - const wrapper = mount( - + const user = userEvent.setup() + const currentValue = 5 + render( + ) - wrapper.find('li > a').last().simulate('click') - expect(onChange).toHaveBeenCalledWith(6) + await user.click(screen.getByRole('link', { name: /next page/i })) + expect(onChange).toHaveBeenCalledWith(currentValue + 1) }) -test('Min button sets value to min', () => { +test('Min control sets value to min', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - wrapper.find('li > a').at(1).simulate('click') + await user.click(screen.getByRole('link', { name: /page 1$/ })) expect(onChange).toHaveBeenCalledWith(1) }) -test('Max button sets value to max', () => { +test('Max control sets value to max', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - wrapper.find('li > a').at(5).simulate('click') + await user.click(screen.getByRole('link', { name: /page 10$/ })) expect(onChange).toHaveBeenCalledWith(10) }) test('Current page is indicated via aria-current', () => { - const wrapper = mount() - expect(wrapper.find('.active > a').prop('aria-current')).toBe('page') - expect(wrapper.find('a').not('.active').first().prop('aria-current')).toBe( - false - ) + render() + expect(screen.getByText(5)).toHaveAttribute('aria-current', 'page') + expect(screen.getByText(1)).toHaveAttribute('aria-current', 'false') }) test('Destination is indicated via aria-label', () => { - const wrapper = mount() - expect(wrapper.find('.active > a').prop('aria-label')).toBe('Go to page 5') + render() + expect(screen.getByLabelText('Go to page 5')).toBeInTheDocument() }) -test('Page button is triggered via click or enter', () => { +test('Page control is triggered via click or enter', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - const link = wrapper.find('li > a').at(2) - link.simulate('click') - link.simulate('keypress', { keyCode: 13 }) - - expect(onChange).toHaveBeenCalledTimes(2) + await user.click(screen.getByLabelText('Go to page 1')) + await user.keyboard('{Enter}') + expect(onChange).toHaveBeenNthCalledWith(1, 1) + expect(onChange).toHaveBeenNthCalledWith(2, 1) }) test('Can accept custom delimiter', () => { - const wrapper = mount( + render( ) - expect(wrapper.find('.delimiter').contains('foo')).toBe(true) + expect(screen.getByText('foo')).toBeInTheDocument() }) From 896d99d6bd76bd96ee713df4a28a2d2ed594a5ce Mon Sep 17 00:00:00 2001 From: Conor Hawes Date: Fri, 4 Aug 2023 11:36:11 -0400 Subject: [PATCH 2/4] Add comment --- test/controls/color-picker.test.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/test/controls/color-picker.test.js b/test/controls/color-picker.test.js index 62dd3915..324a61f8 100644 --- a/test/controls/color-picker.test.js +++ b/test/controls/color-picker.test.js @@ -2,6 +2,9 @@ import React from 'react' import { mount } from 'enzyme' import { ColorPicker } from '../../src/' +// TODO: Migrate after incoming change to use a button instead of a div +// https://github.com/LaunchPadLab/lp-components/pull/596 + test('ColorPicker toggles expanded when swatch is clicked', () => { const wrapper = mount() expect(wrapper.find('.popover').exists()).toBe(false) From b279bc3d3e1c9953f720bd1d7cfc7dc263221ddc Mon Sep 17 00:00:00 2001 From: Conor Hawes Date: Fri, 4 Aug 2023 12:01:51 -0400 Subject: [PATCH 3/4] Remove unused import --- test/controls/paginator/paginator.test.js | 1 - 1 file changed, 1 deletion(-) diff --git a/test/controls/paginator/paginator.test.js b/test/controls/paginator/paginator.test.js index 85c99b21..d612762f 100644 --- a/test/controls/paginator/paginator.test.js +++ b/test/controls/paginator/paginator.test.js @@ -1,7 +1,6 @@ import React from 'react' import { render, screen } from '@testing-library/react' import userEvent from '@testing-library/user-event' -import { mount } from 'enzyme' import { Paginator } from '../../../src/' test('Previous control renders unless value is min', () => { From 1915297e992bd7112ce18a13baddf42e3b8de236 Mon Sep 17 00:00:00 2001 From: Conor Hawes Date: Fri, 4 Aug 2023 12:02:07 -0400 Subject: [PATCH 4/4] Migrate tab-bar --- test/controls/tab-bar.test.js | 100 +++++++++++++++------------------- 1 file changed, 44 insertions(+), 56 deletions(-) diff --git a/test/controls/tab-bar.test.js b/test/controls/tab-bar.test.js index 36bf8215..af263a59 100644 --- a/test/controls/tab-bar.test.js +++ b/test/controls/tab-bar.test.js @@ -1,5 +1,6 @@ import React from 'react' -import { mount } from 'enzyme' +import { render, screen } from '@testing-library/react' +import userEvent from '@testing-library/user-event' import { TabBar } from '../../src/' const defaultOptions = ['Home', 'Account'] @@ -9,107 +10,94 @@ const objectOptions = [ ] test('TabBar defaults to horizontal alignment', () => { - const wrapper = mount() - expect(wrapper.find('ul').hasClass('horizontal-tabs')).toEqual(true) + render() + expect(screen.getByRole('tablist')).toHaveAttribute('aria-orientation', 'horizontal') }) test('TabBar aligns vertically with vertical option', () => { - const wrapper = mount( + render( ) - expect(wrapper.find('ul').hasClass('vertical-tabs')).toEqual(true) + expect(screen.getByRole('tablist')).toHaveAttribute('aria-orientation', 'vertical') }) test('TabBar renders defaultOptions', () => { - const wrapper = mount() - expect(wrapper.find('li').first().text()).toEqual('Home') - expect(wrapper.find('li').last().text()).toEqual('Account') + render() + expect(screen.getByText('Home')).toBeInTheDocument() + expect(screen.getByText('Account')).toBeInTheDocument() }) test('TabBar renders objectOptions', () => { - const wrapper = mount() - expect(wrapper.find('li').first().text()).toEqual('Home') - expect(wrapper.find('li').last().text()).toEqual('Account') + render() + expect(screen.getByText('Home')).toBeInTheDocument() + expect(screen.getByText('Account')).toBeInTheDocument() }) test('TabBar adds Active class', () => { - const wrapper = mount() - expect(wrapper.find('li').first().hasClass('active')).toEqual(true) + render() + expect(screen.getByText('Home').parentElement).toHaveClass('active') }) -test('TabBar calls onChange', () => { +test('TabBar calls onChange', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - wrapper.find('li > a').first().simulate('click') - expect(onChange).toHaveBeenCalledWith('home') + await user.click(screen.getByText(objectOptions[0].key)) + expect(onChange).toHaveBeenCalledWith(objectOptions[0].value) }) test('TabBar passes down custom className to ul', () => { - const wrapper = mount( + render( ) - expect(wrapper.find('ul').hasClass('custom')).toEqual(true) + expect(screen.getByRole('tablist')).toHaveClass('tabs', 'custom') }) test('TabBar passes down custom activeClassName to li', () => { - const wrapper = mount( + render( ) - expect(wrapper.find('li').first().hasClass('custom')).toEqual(true) + const homeTab = screen.getByText('Home') + expect(homeTab.parentElement).toHaveClass('custom') + expect(homeTab.parentElement).not.toHaveClass('active') }) test('TabBar assigns appropriate aria roles', () => { - const wrapper = mount() - expect(wrapper.find('ul').prop('role')).toBe('tablist') - expect(wrapper.find('li > a').every('[role="tab"]')).toBe(true) -}) - -test('TabBar assigns appropriate aria orientation', () => { - const horizontalWrapper = mount( - - ) - const verticalWrapper = mount( - - ) - - expect( - horizontalWrapper.find('[role="tablist"]').prop('aria-orientation') - ).toBe('horizontal') - expect( - verticalWrapper.find('[role="tablist"]').prop('aria-orientation') - ).toBe('vertical') + render() + expect(screen.getByRole('tablist')).toBeInTheDocument() + expect(screen.getAllByRole('tab').length).toBe(defaultOptions.length) }) test('TabBar assigns unique id to tab', () => { - const wrapper = mount() - expect(wrapper.find('li > a').first().prop('id')).toContain( - defaultOptions[0].toLowerCase() - ) + render() + expect(screen.getByText('Home')).toHaveAttribute('id', 'tab-' + defaultOptions[0].toLowerCase()) }) test('Inactive tabs are explicitly removed from the natural tab order', () => { - const wrapper = mount() - expect( - wrapper.find('li').not('.active').find('a').every('[tabIndex="-1"]') - ).toBe(true) + render() + expect(screen.getByText('Account')).toHaveAttribute('tabIndex', '-1') }) -test('Tab to show is triggered via Enter', () => { +test('Tab to show is triggered via Enter', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - wrapper.find('li > a').first().simulate('keyPress', { keyCode: 13 }) - expect(onChange).toHaveBeenCalledWith('home') + screen.getByText(objectOptions[1].key).focus() + await user.keyboard('{Enter}') + expect(onChange).toHaveBeenCalledWith(objectOptions[1].value) }) -test('Tab to show is triggered via Space', () => { +test('Tab to show is triggered via Space', async () => { const onChange = jest.fn() - const wrapper = mount( + const user = userEvent.setup() + render( ) - wrapper.find('li > a').first().simulate('keyPress', { keyCode: 32 }) - expect(onChange).toHaveBeenCalledWith('home') + screen.getByText(objectOptions[1].key).focus() + await user.keyboard('[Space]') + expect(onChange).toHaveBeenCalledWith(objectOptions[1].value) })