Dashboard: unit tests related to rename resume

This commit is contained in:
gianantoniopini
2021-02-02 14:01:17 +01:00
parent 23386839a6
commit fd79891a1a
6 changed files with 237 additions and 20 deletions

View File

@ -15,7 +15,7 @@ import {
waitForModalWindowToHaveBeenClosed,
dismissNotification,
unsplashPhotoResponseUrl,
setupWithFetchMockAndWaitForLoadingScreenToDisappear,
setupWithFetchMockAndWait,
} from './helpers/dashboard';
const tooShortResumeName = 'CV 1';
@ -23,7 +23,7 @@ const validResumeName = 'Resume for SW development roles';
async function setup() {
const user = DatabaseConstants.user1;
await setupWithFetchMockAndWaitForLoadingScreenToDisappear(user);
await setupWithFetchMockAndWait(user, true);
const dashboardCreateResumeButton = await screen.findByTestId(
createResumeButtonDataTestId,

View File

@ -10,7 +10,7 @@ import FirebaseStub, { DatabaseConstants } from 'gatsby-plugin-firebase';
import { menuToggleDataTestIdPrefix as resumePreviewMenuToggleDataTestIdPrefix } from '../../../components/dashboard/ResumePreview';
import {
setupAndWaitForLoadingScreenToDisappear,
setupAndWait,
waitForResumeToDisappearFromPreview,
expectResumeToBeRenderedInPreview,
dismissNotification,
@ -37,9 +37,7 @@ const expectDatabaseRemoveToHaveCompleted = async (
};
async function setup() {
const userResumes = await setupAndWaitForLoadingScreenToDisappear(
DatabaseConstants.user1,
);
const userResumes = await setupAndWait(DatabaseConstants.user1, true);
const [resumeToDelete] = Object.values(userResumes).filter(
(resume) => resume.id === DatabaseConstants.demoStateResume1Id,

View File

@ -9,7 +9,7 @@ import FirebaseStub, { DatabaseConstants } from 'gatsby-plugin-firebase';
import { menuToggleDataTestIdPrefix as resumePreviewMenuToggleDataTestIdPrefix } from '../../../components/dashboard/ResumePreview';
import {
setupWithFetchMockAndWaitForLoadingScreenToDisappear,
setupWithFetchMockAndWait,
waitForResumeToBeRenderedInPreview,
expectResumeToBeRenderedInPreview,
unsplashPhotoResponseUrl,
@ -17,9 +17,7 @@ import {
async function setup() {
const user = DatabaseConstants.user1;
const userResumes = await setupWithFetchMockAndWaitForLoadingScreenToDisappear(
user,
);
const userResumes = await setupWithFetchMockAndWait(user, true);
const [resumeToDuplicate] = Object.values(userResumes).filter(
(resume) => resume.id === DatabaseConstants.demoStateResume1Id,

View File

@ -0,0 +1,214 @@
import {
fireEvent,
getByText,
queryByText,
screen,
waitFor,
waitForElementToBeRemoved,
} from '@testing-library/react';
import FirebaseStub, { DatabaseConstants } from 'gatsby-plugin-firebase';
import { menuToggleDataTestIdPrefix as resumePreviewMenuToggleDataTestIdPrefix } from '../../../components/dashboard/ResumePreview';
import {
setupAndWait,
waitForResumeToBeRenderedInPreview,
expectResumeToBeRenderedInPreview,
dismissNotification,
waitForModalWindowToHaveBeenClosed,
} from './helpers/dashboard';
const tooShortResumeName = 'CV 2';
const validResumeName = 'Resume for SW development roles - renamed';
const waitForDatabaseUpdateToHaveCompleted = async (
mockDatabaseUpdateFunction,
) => {
await waitFor(() => mockDatabaseUpdateFunction.mock.calls[0][0]);
await waitFor(() => mockDatabaseUpdateFunction.mock.results[0].value);
};
const expectDatabaseUpdateToHaveCompleted = async (
mockDatabaseUpdateFunction,
) => {
await waitFor(() =>
expect(mockDatabaseUpdateFunction).toHaveBeenCalledTimes(1),
);
await waitFor(() =>
expect(
mockDatabaseUpdateFunction.mock.results[0].value,
).resolves.toBeUndefined(),
);
};
async function setup() {
const userResumes = await setupAndWait(DatabaseConstants.user1, true);
const [resumeToRename] = Object.values(userResumes).filter(
(resume) => resume.id === DatabaseConstants.demoStateResume1Id,
);
const resumeToRenameId = resumeToRename.id;
const mockDatabaseUpdateFunction = jest.spyOn(
FirebaseStub.database().ref(
`${DatabaseConstants.resumesPath}/${resumeToRenameId}`,
),
'update',
);
mockDatabaseUpdateFunction.mockClear();
const resumeToRenameMenuToggle = await screen.findByTestId(
`${resumePreviewMenuToggleDataTestIdPrefix}${resumeToRenameId}`,
);
fireEvent.click(resumeToRenameMenuToggle);
const menuItems = screen.getAllByRole('menuitem');
let renameMenuItem = null;
for (let index = 0; index < menuItems.length; index++) {
if (queryByText(menuItems[index], /rename/i)) {
renameMenuItem = menuItems[index];
break;
}
}
fireEvent.click(renameMenuItem);
const nameTextBox = screen.getByRole('textbox', { name: /name/i });
return { resumeToRename, mockDatabaseUpdateFunction, nameTextBox };
}
async function setupAndSubmit(resumeNewName) {
const {
resumeToRename,
mockDatabaseUpdateFunction,
nameTextBox,
} = await setup();
fireEvent.change(nameTextBox, {
target: { value: resumeNewName },
});
const modalEditResumeButton = screen.getByRole('button', {
name: /edit resume/i,
});
fireEvent.click(modalEditResumeButton);
return {
renamedResume: resumeToRename,
mockDatabaseUpdateFunction,
nameTextBox,
};
}
test('renders current name in modal window', async () => {
const { resumeToRename, nameTextBox } = await setup();
expect(nameTextBox).toHaveValue(resumeToRename.name);
});
describe('with invalid name', () => {
test('displays validation error', async () => {
const { nameTextBox } = await setup();
fireEvent.change(nameTextBox, { target: { value: tooShortResumeName } });
fireEvent.blur(nameTextBox);
await waitFor(() =>
expect(
screen.getByText(/Please enter at least 5 characters/i),
).toBeInTheDocument(),
);
});
test('displays notification', async () => {
await setupAndSubmit(tooShortResumeName);
const notification = await screen.findByRole('alert');
/*
const notification = await screen.findByText(
/You might need to fill up all the required fields/i,
);
*/
expect(
getByText(
notification,
/You might need to fill up all the required fields/i,
),
).toBeInTheDocument();
dismissNotification(notification);
});
});
describe('with valid name', () => {
test('renders loading message', async () => {
const { mockDatabaseUpdateFunction } = await setupAndSubmit(
validResumeName,
);
await waitFor(() =>
expect(
screen.getByRole('button', {
name: /loading/i,
}),
).toBeInTheDocument(),
);
await waitForElementToBeRemoved(() =>
screen.getByRole('button', {
name: /loading/i,
}),
);
await waitForModalWindowToHaveBeenClosed();
await waitForDatabaseUpdateToHaveCompleted(mockDatabaseUpdateFunction);
await waitForResumeToBeRenderedInPreview(validResumeName);
});
test('closes modal window', async () => {
const { mockDatabaseUpdateFunction } = await setupAndSubmit(
validResumeName,
);
await waitFor(() =>
expect(waitForModalWindowToHaveBeenClosed()).resolves.toBeUndefined(),
);
await waitForDatabaseUpdateToHaveCompleted(mockDatabaseUpdateFunction);
await waitForResumeToBeRenderedInPreview(validResumeName);
});
test('renders renamed resume in preview', async () => {
const { mockDatabaseUpdateFunction } = await setupAndSubmit(
validResumeName,
);
await waitForModalWindowToHaveBeenClosed();
await waitForDatabaseUpdateToHaveCompleted(mockDatabaseUpdateFunction);
await waitFor(() =>
expect(
expectResumeToBeRenderedInPreview(validResumeName),
).resolves.toBeUndefined(),
);
});
test('updates database', async () => {
const now = new Date().getTime();
const { renamedResume, mockDatabaseUpdateFunction } = await setupAndSubmit(
validResumeName,
);
const renamedResumeId = renamedResume.id;
await waitForModalWindowToHaveBeenClosed();
await expectDatabaseUpdateToHaveCompleted(mockDatabaseUpdateFunction);
const mockDatabaseUpdateFunctionCallArgument =
mockDatabaseUpdateFunction.mock.calls[0][0];
expect(mockDatabaseUpdateFunctionCallArgument.id).toBe(renamedResumeId);
expect(mockDatabaseUpdateFunctionCallArgument.name).toBe(validResumeName);
expect(
mockDatabaseUpdateFunctionCallArgument.updatedAt,
).toBeGreaterThanOrEqual(now);
await waitForResumeToBeRenderedInPreview(validResumeName);
});
});

View File

@ -4,7 +4,7 @@ import { DatabaseConstants } from 'gatsby-plugin-firebase';
import { createResumeButtonDataTestId } from '../../../components/dashboard/CreateResume';
import setup, {
setupAndWaitForLoadingScreenToDisappear,
setupAndWait,
expectResumeToBeRenderedInPreview,
expectLoadingScreenToBeRendered,
waitForLoadingScreenToDisappear,
@ -20,7 +20,7 @@ it('renders loading screen', async () => {
});
it('renders document title', async () => {
await setupAndWaitForLoadingScreenToDisappear(user);
await setupAndWait(user, true);
await waitFor(() => {
expect(document.title).toEqual('Dashboard | Reactive Resume');
@ -28,7 +28,7 @@ it('renders document title', async () => {
});
it('renders create resume', async () => {
await setupAndWaitForLoadingScreenToDisappear(user);
await setupAndWait(user, true);
await waitFor(() => {
expect(screen.getByText(/create resume/i)).toBeInTheDocument();
@ -41,7 +41,7 @@ it('renders create resume', async () => {
});
it('renders preview of user resumes', async () => {
const userResumes = await setupAndWaitForLoadingScreenToDisappear(user);
const userResumes = await setupAndWait(user, true);
expect(Object.keys(userResumes)).toHaveLength(2);

View File

@ -133,21 +133,28 @@ async function setup(user) {
return userResumes;
}
async function setupAndWaitForLoadingScreenToDisappear(user) {
const userResumes = await _setup(user, true, false);
async function setupAndWait(user, waitForLoadingScreenToDisappear) {
const userResumes = await _setup(
user,
waitForLoadingScreenToDisappear,
false,
);
return userResumes;
}
async function setupWithFetchMockAndWaitForLoadingScreenToDisappear(user) {
const userResumes = await _setup(user, true, true);
async function setupWithFetchMockAndWait(
user,
waitForLoadingScreenToDisappear,
) {
const userResumes = await _setup(user, waitForLoadingScreenToDisappear, true);
return userResumes;
}
export default setup;
export {
setupAndWaitForLoadingScreenToDisappear,
setupWithFetchMockAndWaitForLoadingScreenToDisappear,
setupAndWait,
setupWithFetchMockAndWait,
waitForResumeToBeRenderedInPreview,
waitForResumeToDisappearFromPreview,
expectResumeToBeRenderedInPreview,