Skip to content

Commit

Permalink
Use *ByRole when possible
Browse files Browse the repository at this point in the history
  • Loading branch information
tkrotoff committed Mar 16, 2023
1 parent b21ed45 commit 85560e4
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 57 deletions.
10 changes: 5 additions & 5 deletions src/Hero.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,14 @@ test('page title', async () => {
const { rerender } = render(<Hero />);
expect(document.title).toEqual('... - Marvel Heroes');
await act(flushPromises);
await screen.findByText('3-D Man');
await screen.findByRole('heading', { level: 1, name: '3-D Man' });
expect(document.title).toEqual('3-D Man - Marvel Heroes');

useParamsMock.mockReturnValue({ id: '1017100' });
rerender(<Hero />);
//expect(document.title).toEqual('... - Marvel Heroes');
await act(flushPromises);
await screen.findByText('A-Bomb (HAS)');
await screen.findByRole('heading', { level: 1, name: 'A-Bomb (HAS)' });
expect(document.title).toEqual('A-Bomb (HAS) - Marvel Heroes');
});

Expand All @@ -39,21 +39,21 @@ test('render', async () => {
expect(fetchCharacterSpy).toHaveBeenCalledTimes(1);
screen.getByText(pleaseWait);
await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('3-D Man');
screen.getByRole('heading', { level: 1, name: '3-D Man' });

useParamsMock.mockReturnValue({ id: '1017100' });
rerender(<Hero />);
expect(fetchCharacterSpy).toHaveBeenCalledTimes(2);
screen.getByText(pleaseWait);
await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('A-Bomb (HAS)');
screen.getByRole('heading', { level: 1, name: 'A-Bomb (HAS)' });

useParamsMock.mockReturnValue({ id: '1009144' });
rerender(<Hero />);
expect(fetchCharacterSpy).toHaveBeenCalledTimes(3);
screen.getByText(pleaseWait);
await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('A.I.M.');
screen.getByRole('heading', { level: 1, name: 'A.I.M.' });
});

test('fetchCharacter() error', async () => {
Expand Down
40 changes: 20 additions & 20 deletions src/Heroes.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,15 @@ test('page title', async () => {
</MemoryRouter>
);
expect(document.title).toEqual('Page 0 - Marvel Heroes');
await screen.findByText('3-D Man'); // Wait for fetchCharacters request
await screen.findByRole('heading', { level: 5, name: '3-D Man' }); // Wait for fetchCharacters request

rerender(
<MemoryRouter>
<Heroes page={1} />
</MemoryRouter>
);
expect(document.title).toEqual('Page 1 - Marvel Heroes');
await screen.findByText('Anita Blake'); // Wait for fetchCharacters request
await screen.findByRole('heading', { level: 5, name: 'Anita Blake' }); // Wait for fetchCharacters request
});

const pleaseWait = 'Please wait...';
Expand All @@ -41,12 +41,12 @@ test('render', async () => {
expect(fetchCharactersSpy).toHaveBeenCalledTimes(1);
screen.getByText(pleaseWait);
await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('3-D Man');
screen.getByText('A-Bomb (HAS)');
screen.getByText('A.I.M.');
screen.getByText('Angel (Ultimate)');
screen.getByText('Angel (Warren Worthington III)');
screen.getByText('Angela (Aldrif Odinsdottir)');
screen.getByRole('heading', { level: 5, name: '3-D Man' });
screen.getByRole('heading', { level: 5, name: 'A-Bomb (HAS)' });
screen.getByRole('heading', { level: 5, name: 'A.I.M.' });
screen.getByRole('heading', { level: 5, name: 'Angel (Ultimate)' });
screen.getByRole('heading', { level: 5, name: 'Angel (Warren Worthington III)' });
screen.getByRole('heading', { level: 5, name: 'Angela (Aldrif Odinsdottir)' });

rerender(
<MemoryRouter>
Expand All @@ -56,12 +56,12 @@ test('render', async () => {
expect(fetchCharactersSpy).toHaveBeenCalledTimes(2);
screen.getByText(pleaseWait);
await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('Anita Blake');
screen.getByText('Anne Marie Hoag');
screen.getByText('Annihilus');
screen.getByText('Battering Ram');
screen.getByText('Battlestar');
screen.getByText('Beak');
screen.getByRole('heading', { level: 5, name: 'Anita Blake' });
screen.getByRole('heading', { level: 5, name: 'Anne Marie Hoag' });
screen.getByRole('heading', { level: 5, name: 'Annihilus' });
screen.getByRole('heading', { level: 5, name: 'Battering Ram' });
screen.getByRole('heading', { level: 5, name: 'Battlestar' });
screen.getByRole('heading', { level: 5, name: 'Beak' });
});

test('render "No results found :("', async () => {
Expand All @@ -85,9 +85,9 @@ test('click on Details link', async () => {

expect(window.location.href).toEqual('http://localhost/');
expect(document.title).toEqual('Page 0 - Marvel Heroes');
await screen.findByText('3-D Man');
await screen.findByRole('heading', { level: 5, name: '3-D Man' });

const detailsLink = screen.getAllByText<HTMLLinkElement>('Details')[0];
const detailsLink = screen.getAllByRole<HTMLAnchorElement>('link', { name: 'Details' })[0];
act(() => detailsLink.click());

screen.getByText(pleaseWait);
Expand All @@ -98,10 +98,10 @@ test('click on Details link', async () => {

expect(screen.queryByText(pleaseWait)).toBeNull();

screen.getByText('3-D Man');
screen.getByText('Comics');
screen.getByText('Series');
screen.getByText('Stories');
await screen.findByRole('heading', { level: 1, name: '3-D Man' });
await screen.findByRole('heading', { level: 6, name: 'Comics' });
await screen.findByRole('heading', { level: 6, name: 'Series' });
await screen.findByRole('heading', { level: 6, name: 'Stories' });
});

test('fetchCharacters() error "500 Internal Server Error"', async () => {
Expand Down
54 changes: 27 additions & 27 deletions src/HeroesPagination.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,21 +19,21 @@ test('render without page query param', async () => {
);

expect(spy).toHaveBeenCalledTimes(1);
screen.getByText('Marvel Heroes');
const prevLink = screen.getByText<HTMLLinkElement>('‹ Previous');
expect(prevLink.href).toBeUndefined();
screen.getByRole('heading', { level: 1, name: 'Marvel Heroes' });
const prevLink = screen.getByRole<HTMLButtonElement>('button', { name: '‹ Previous' });
expect((prevLink as unknown as HTMLAnchorElement).href).toBeUndefined();
expect(prevLink.disabled).toEqual(true);
const nextLink = screen.getByText<HTMLLinkElement>('Next ›');
const nextLink = screen.getByRole<HTMLAnchorElement>('link', { name: 'Next ›' });
expect(nextLink.href).toEqual('http://localhost/1');
screen.getByText(pleaseWait);

await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('3-D Man');
screen.getByText('A-Bomb (HAS)');
screen.getByText('A.I.M.');
screen.getByText('Angel (Ultimate)');
screen.getByText('Angel (Warren Worthington III)');
screen.getByText('Angela (Aldrif Odinsdottir)');
screen.getByRole('heading', { level: 5, name: '3-D Man' });
screen.getByRole('heading', { level: 5, name: 'A-Bomb (HAS)' });
screen.getByRole('heading', { level: 5, name: 'A.I.M.' });
screen.getByRole('heading', { level: 5, name: 'Angel (Ultimate)' });
screen.getByRole('heading', { level: 5, name: 'Angel (Warren Worthington III)' });
screen.getByRole('heading', { level: 5, name: 'Angela (Aldrif Odinsdottir)' });

// FIXME Cannot do a rerender with initialEntries={['/1']}: useParams() inside HeroesPagination is not updated
// https://github.com/tkrotoff/MarvelHeroes/blob/dfb842607c421ba1762fc844afcc7916c17a47b4/src/HeroesPagination.test.tsx#L43-L61
Expand All @@ -51,21 +51,21 @@ test('render given a page query param', async () => {
);

expect(spy).toHaveBeenCalledTimes(1);
screen.getByText('Marvel Heroes');
const prevLink = screen.getByText<HTMLLinkElement>('‹ Previous');
screen.getByRole('heading', { level: 1, name: 'Marvel Heroes' });
const prevLink = screen.getByRole<HTMLAnchorElement>('link', { name: '‹ Previous' });
expect(prevLink.href).toEqual('http://localhost/0');
expect(prevLink.disabled).toBeUndefined();
const nextLink = screen.getByText<HTMLLinkElement>('Next ›');
expect((prevLink as unknown as HTMLButtonElement).disabled).toBeUndefined();
const nextLink = screen.getByRole<HTMLAnchorElement>('link', { name: 'Next ›' });
expect(nextLink.href).toEqual('http://localhost/2');
screen.getByText(pleaseWait);

await waitForElementToBeRemoved(() => screen.queryByText(pleaseWait));
screen.getByText('Anita Blake');
screen.getByText('Anne Marie Hoag');
screen.getByText('Annihilus');
screen.getByText('Battering Ram');
screen.getByText('Battlestar');
screen.getByText('Beak');
screen.getByRole('heading', { level: 5, name: 'Anita Blake' });
screen.getByRole('heading', { level: 5, name: 'Anne Marie Hoag' });
screen.getByRole('heading', { level: 5, name: 'Annihilus' });
screen.getByRole('heading', { level: 5, name: 'Battering Ram' });
screen.getByRole('heading', { level: 5, name: 'Battlestar' });
screen.getByRole('heading', { level: 5, name: 'Beak' });

spy.mockRestore();
});
Expand All @@ -77,43 +77,43 @@ test('click on Previous & Next links', async () => {
</BrowserRouter>
);

const prevLink = () => screen.getByText<HTMLLinkElement>('‹ Previous');
const nextLink = screen.getByText<HTMLLinkElement>('Next ›');
const prevLink = () => screen.getByText<HTMLButtonElement>('‹ Previous');
const nextLink = screen.getByRole<HTMLAnchorElement>('link', { name: 'Next ›' });

expect(window.location.href).toEqual('http://localhost/');
expect(document.title).toEqual('Page 0 - Marvel Heroes');
await screen.findByText('3-D Man');
await screen.findByRole('heading', { level: 5, name: '3-D Man' });
expect(prevLink().disabled).toEqual(true);

act(() => nextLink.click());
expect(window.location.href).toEqual('http://localhost/1');
expect(document.title).toEqual('Page 1 - Marvel Heroes');
screen.getByText(pleaseWait);
await screen.findByText('Anita Blake');
await screen.findByRole('heading', { level: 5, name: 'Anita Blake' });
expect(screen.queryByText(pleaseWait)).toBeNull();
expect(prevLink().disabled).toBeUndefined();

act(() => nextLink.click());
expect(window.location.href).toEqual('http://localhost/2');
expect(document.title).toEqual('Page 2 - Marvel Heroes');
screen.getByText(pleaseWait);
await screen.findByText('Beast');
await screen.findByRole('heading', { level: 5, name: 'Beast' });
expect(screen.queryByText(pleaseWait)).toBeNull();
expect(prevLink().disabled).toBeUndefined();

act(() => prevLink().click());
expect(window.location.href).toEqual('http://localhost/1');
expect(document.title).toEqual('Page 1 - Marvel Heroes');
screen.getByText(pleaseWait);
await screen.findByText('Anita Blake');
await screen.findByRole('heading', { level: 5, name: 'Anita Blake' });
expect(screen.queryByText(pleaseWait)).toBeNull();
expect(prevLink().disabled).toBeUndefined();

act(() => prevLink().click());
expect(window.location.href).toEqual('http://localhost/0');
expect(document.title).toEqual('Page 0 - Marvel Heroes');
screen.getByText(pleaseWait);
await screen.findByText('3-D Man');
await screen.findByRole('heading', { level: 5, name: '3-D Man' });
expect(screen.queryByText(pleaseWait)).toBeNull();
expect(prevLink().disabled).toEqual(true);
});
4 changes: 3 additions & 1 deletion src/PageNotFound.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,9 @@ test('render', async () => {
useLocationMock.mockReturnValue({ pathname: 'unknown' } as ReturnType<typeof useLocation>);
render(<PageNotFound />);

screen.getByText('Whoops');
expect(document.title).toEqual('Page not found - Marvel Heroes');

screen.getByRole('heading', { level: 1, name: 'Whoops' });

// Tests "Sorry but <em>unknown</em> didn't match any pages"
screen.getByText("Sorry but didn't match any pages");
Expand Down
4 changes: 4 additions & 0 deletions src/PageNotFound.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
import { useLocation } from 'react-router';

import { setPageTitle } from './utils/setPageTitle';

export function PageNotFound() {
setPageTitle('Page not found');

const location = useLocation();

return (
Expand Down
4 changes: 2 additions & 2 deletions src/utils/ErrorBoundary.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ describe('if an error has occurred', () => {
<MyComponent throwError={true} />
</ErrorBoundary>
);
screen.getByText('Something went wrong :(');
screen.getByRole('heading', { level: 1, name: 'Something went wrong :(' });
screen.getByText('Error: Oops!');
screen.getByText('Report feedback');

Expand Down Expand Up @@ -60,7 +60,7 @@ describe('if an error has occurred', () => {
);
mockConsole.mockRestore();

const button = screen.getByText('Report feedback');
const button = screen.getByRole<HTMLButtonElement>('button', { name: 'Report feedback' });
button.click();
expect(spyShowReportDialog).toHaveBeenCalledTimes(1);
expect(spyShowReportDialog).toHaveBeenCalledWith({ eventId: expect.any(String) });
Expand Down
4 changes: 2 additions & 2 deletions src/utils/useErrorHandler.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ test('render children if no error', () => {
screen.getByText('Hello, World!');
});

test('render message + report button if an error occured', async () => {
test('render message + report button if an error occurred', async () => {
render(
<ErrorBoundary>
<MyComponent throwError={true} />
Expand All @@ -49,7 +49,7 @@ test('render message + report button if an error occured', async () => {
);
mockConsole.mockRestore();

screen.getByText('Something went wrong :(');
screen.getByRole('heading', { level: 1, name: 'Something went wrong :(' });
screen.getByText('Error: Oops!');
screen.getByText('Report feedback');
});

0 comments on commit 85560e4

Please sign in to comment.