import React from 'react'; import styled from '@emotion/styled'; import { ColumnDef, Header } from '@tanstack/react-table'; import { queryByRole as globalQueryByRole, render, } from '@testing-library/react'; import userEvent from '@testing-library/user-event'; import { axe } from 'jest-axe'; import { renderHook } from '@leafygreen-ui/testing-lib'; import useLeafyGreenTable, { LGTableDataType } from '../../useLeafyGreenTable'; import { getLgIds } from '../../utils/getLgIds'; import { Person } from '../../utils/makeData.testutils'; import HeaderCell, { HeaderCellProps } from '.'; const lgIds = getLgIds(); const headerCellSortIconTestId = lgIds.sortIcon; function renderSimpleHeaderCell(props: HeaderCellProps) { return render( test header cell
th 2
td 1 td 2
, ); } const headerCellTestColumns: Array>> = [ { accessorKey: 'firstName', header: 'First Name', enableSorting: true, }, { accessorKey: 'age', header: 'Age', enableSorting: true, }, ]; const headerCellTestData: Array> = [ { firstName: 'Aaron', age: 99, }, { firstName: 'Zara', age: 21, }, ]; const TestSortableHeaderCell = () => { const table = useLeafyGreenTable({ columns: headerCellTestColumns, data: headerCellTestData, }); return (
{table.getHeaderGroups()[0].headers.map(header => ( ))}
td 1 td 2
); }; /** Returns the `header` data for a given column def */ const useMockTestHeaderData = ( columnDef: ColumnDef, ): Header, unknown> => { const table = useLeafyGreenTable({ data: [], columns: [columnDef], }); return table.getFlatHeaders()[0]; }; describe('packages/table/HeaderCell', () => { describe('a11y', () => { test('does not have basic accessibility issues', async () => { const { container } = renderSimpleHeaderCell({}); const results = await axe(container); expect(results).toHaveNoViolations(); }); }); describe('sort prop', () => { test('sort prop renders sort icon button', async () => { const { getAllByTestId } = render(); const sortIconButtons = getAllByTestId(headerCellSortIconTestId); expect(sortIconButtons[0]).toBeInTheDocument(); expect(sortIconButtons[1]).toBeInTheDocument(); }); // Sorting behaves differently for string and numeric data describe.each([ { columnIndex: 0, dataType: 'string', initialSort: 'Ascending', secondSort: 'Descending', }, { columnIndex: 1, dataType: 'number', initialSort: 'Descending', secondSort: 'Ascending', }, ])('for $dataType data', ({ columnIndex, initialSort, secondSort }) => { const iconButtonTestId = headerCellSortIconTestId; test('initial state of sort icon is unsorted', async () => { const { queryAllByLabelText } = render(); const unsortedIcon = queryAllByLabelText('Unsorted Icon')[columnIndex]; expect(unsortedIcon).toBeInTheDocument(); }); test(`clicking sort icon switches to sort ${initialSort}`, async () => { const { getAllByTestId } = render(); const sortIconButton = getAllByTestId(iconButtonTestId)[columnIndex]; userEvent.click(sortIconButton); const sortIcon = globalQueryByRole(sortIconButton, 'img'); expect(sortIcon).toHaveAttribute( 'aria-label', `Sort ${initialSort} Icon`, ); }); test(`clicking sort icon twice switches to sort ${secondSort}`, async () => { const { getAllByTestId } = render(); const sortIconButton = getAllByTestId(iconButtonTestId)[columnIndex]; userEvent.click(sortIconButton); userEvent.click(sortIconButton); const sortIcon = globalQueryByRole(sortIconButton, 'img'); expect(sortIcon).toHaveAttribute( 'aria-label', `Sort ${secondSort} Icon`, ); }); test(`clicking sort icon three times reverts to unsorted icon`, async () => { const { getAllByTestId } = render(); const sortIconButton = getAllByTestId(iconButtonTestId)[columnIndex]; userEvent.click(sortIconButton); userEvent.click(sortIconButton); userEvent.click(sortIconButton); const sortIcon = globalQueryByRole(sortIconButton, 'img'); expect(sortIcon).toHaveAttribute('aria-label', 'Unsorted Icon'); }); }); }); test('setting size in columnDef sets HeaderCell width', async () => { const { result } = renderHook(() => useMockTestHeaderData({ accessorKey: 'id', size: 700, }), ); const mockHeader = result.current; const { getByTestId } = render( , ); const headerCell = getByTestId('lg-header-cell-test'); expect(getComputedStyle(headerCell).width).toBe('700px'); }); test('Accepts a ref', () => { const ref = React.createRef(); render(Hello); expect(ref.current).toBeInTheDocument(); expect(ref.current!.textContent).toBe('Hello'); }); describe('styled', () => { test('works with `styled`', () => { const StyledHeaderCell = styled(HeaderCell)` color: #69ffc6; `; const { getByTestId } = render( Some text, ); expect(getByTestId('styled')).toHaveStyle(`color: #69ffc6;`); }); test('works with `styled` props', () => { // We need to define the additional props that styled should expect interface StyledProps { color?: string; } const StyledHeaderCell = styled(HeaderCell)` color: ${props => props.color}; `; const { getByTestId } = render( Some text , ); expect(getByTestId('styled')).toHaveStyle(`color: #69ffc6;`); }); }); // eslint-disable-next-line jest/no-disabled-tests describe.skip('types behave as expected', () => { const { result } = renderHook(() => useMockTestHeaderData({ accessorKey: 'id', size: 700, }), ); const mockHeader = result.current; const ref = React.createRef(); <> ; }); });