Delete Account unit tests: added tests related to Google reauthentication

This commit is contained in:
gianantoniopini
2021-05-20 15:57:01 +02:00
parent 7cb469657d
commit 9e63d0b2c7
18 changed files with 363 additions and 56 deletions

View File

@ -7,13 +7,14 @@ import {
expectDatabaseUpdateToHaveCompleted,
} from './helpers/builder';
const testTimeoutInMilliseconds = 20000;
const testTimeoutInMilliseconds = 30000;
jest.setTimeout(testTimeoutInMilliseconds);
test('when input value is changed, updates database', async () => {
const resumeId = DatabaseConstants.demoStateResume1Id;
const { mockDatabaseUpdateFunction } = await setupAndWait(
resumeId,
false,
true,
true,
);

View File

@ -20,6 +20,7 @@ jest.setTimeout(testTimeoutInMilliseconds);
test('renders first and last name', async () => {
const { resume } = await setupAndWait(
DatabaseConstants.demoStateResume1Id,
false,
true,
true,
);
@ -53,7 +54,7 @@ test('renders loading screen', async () => {
});
test('if resume is in initial state, renders load demo data notification', async () => {
await setup(DatabaseConstants.initialStateResumeId);
await setup(DatabaseConstants.initialStateResume1Id);
const notification = await screen.findByRole('alert');
expect(

View File

@ -14,9 +14,32 @@ import { delay } from '../../../utils/index';
const testTimeoutInMilliseconds = 60000;
jest.setTimeout(testTimeoutInMilliseconds);
async function setup() {
const resumeId = DatabaseConstants.demoStateResume1Id;
await setupAndWait(resumeId, true, true);
async function setup(signInWithGoogle, failReauthentication) {
const resumeId = signInWithGoogle
? DatabaseConstants.demoStateResume3Id
: DatabaseConstants.demoStateResume1Id;
await setupAndWait(resumeId, signInWithGoogle, true, true);
let mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage;
let mockFirebaseCurrentUserReauthenticateWithPopup;
if (failReauthentication) {
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage =
'Error occurred while reauthenticating.';
mockFirebaseCurrentUserReauthenticateWithPopup = jest.fn(async () => {
await delay(AuthConstants.defaultDelayInMilliseconds);
throw new Error(
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage,
);
});
FirebaseStub.auth().currentUser.reauthenticateWithPopup = mockFirebaseCurrentUserReauthenticateWithPopup;
} else {
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage = null;
mockFirebaseCurrentUserReauthenticateWithPopup = jest.spyOn(
FirebaseStub.auth().currentUser,
'reauthenticateWithPopup',
);
}
const mockFirebaseDeleteUserCloudFunction = jest.fn(async () => {
await delay(FunctionsConstants.defaultDelayInMilliseconds);
@ -61,6 +84,8 @@ async function setup() {
areYouSureButtonText,
deleteAccountButtonText,
waitForDeleteAccountButtonTextToChangeTo,
mockFirebaseCurrentUserReauthenticateWithPopup,
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage,
mockFirebaseDeleteUserCloudFunction,
mockFirebaseCurrentUserDelete,
mockFirebaseAuthSignOut,
@ -78,7 +103,7 @@ test('prompts for confirmation', async () => {
mockFirebaseCurrentUserDelete,
mockFirebaseAuthSignOut,
mockToastError,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
@ -98,7 +123,7 @@ test('calls Firebase delete user cloud function', async () => {
deleteAccountButtonText,
mockFirebaseDeleteUserCloudFunction,
waitForDeleteAccountButtonTextToChangeTo,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
@ -116,7 +141,7 @@ test('calls Firebase current user delete', async () => {
deleteAccountButtonText,
mockFirebaseCurrentUserDelete,
waitForDeleteAccountButtonTextToChangeTo,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
@ -134,7 +159,7 @@ test('calls Firebase auth sign out', async () => {
deleteAccountButtonText,
mockFirebaseAuthSignOut,
waitForDeleteAccountButtonTextToChangeTo,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
@ -150,7 +175,7 @@ describe('if an error occurs while signing out the current user', () => {
deleteAccountButton,
deleteAccountButtonText,
waitForDeleteAccountButtonTextToChangeTo,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
@ -167,7 +192,7 @@ describe('if an error occurs while signing out the current user', () => {
mockFirebaseAuthSignOutErrorMessage,
waitForDeleteAccountButtonTextToChangeTo,
mockToastError,
} = await setup();
} = await setup(false, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
@ -185,3 +210,75 @@ describe('if an error occurs while signing out the current user', () => {
);
});
});
describe('if the current user is signed in with Google', () => {
test('reauthenticates the user', async () => {
const googleAuthProvider = new FirebaseStub.auth.GoogleAuthProvider();
const {
deleteAccountButton,
deleteAccountButtonText,
mockFirebaseCurrentUserReauthenticateWithPopup,
waitForDeleteAccountButtonTextToChangeTo,
} = await setup(true, false);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
await waitForDeleteAccountButtonTextToChangeTo(deleteAccountButtonText);
expect(
mockFirebaseCurrentUserReauthenticateWithPopup,
).toHaveBeenCalledTimes(1);
expect(mockFirebaseCurrentUserReauthenticateWithPopup).toHaveBeenCalledWith(
googleAuthProvider,
);
});
describe('and reauthentication fails', () => {
test('does not proceed further', async () => {
const {
deleteAccountButton,
deleteAccountButtonText,
waitForDeleteAccountButtonTextToChangeTo,
mockFirebaseDeleteUserCloudFunction,
mockFirebaseCurrentUserDelete,
mockFirebaseAuthSignOut,
} = await setup(true, true);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
await waitForDeleteAccountButtonTextToChangeTo(deleteAccountButtonText);
expect(mockFirebaseDeleteUserCloudFunction).not.toHaveBeenCalled();
expect(mockFirebaseCurrentUserDelete).not.toHaveBeenCalled();
expect(mockFirebaseAuthSignOut).not.toHaveBeenCalled();
expect(mockNavigateFunction).not.toHaveBeenCalled();
});
test('displays error notifications', async () => {
const {
deleteAccountButton,
deleteAccountButtonText,
waitForDeleteAccountButtonTextToChangeTo,
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage,
mockToastError,
} = await setup(true, true);
fireEvent.click(deleteAccountButton);
fireEvent.click(deleteAccountButton);
await waitForDeleteAccountButtonTextToChangeTo(deleteAccountButtonText);
expect(mockToastError).toHaveBeenCalledTimes(2);
expect(mockToastError).toHaveBeenNthCalledWith(
1,
mockFirebaseCurrentUserReauthenticateWithPopupErrorMessage,
);
expect(mockToastError).toHaveBeenNthCalledWith(
2,
'An error occurred deleting your account.',
);
});
});
});

View File

@ -16,6 +16,7 @@ test('allows to change the language', async () => {
const resumeId = DatabaseConstants.demoStateResume1Id;
const { mockDatabaseUpdateFunction } = await setupAndWait(
resumeId,
false,
true,
true,
);

View File

@ -19,6 +19,7 @@ test('allows to drag & drop', async () => {
const resumeId = DatabaseConstants.demoStateResume1Id;
const { resume, mockDatabaseUpdateFunction } = await setupAndWait(
resumeId,
false,
true,
true,
);

View File

@ -44,7 +44,7 @@ async function setup() {
);
const resumeToDeleteId = resumeToDelete.id;
const [undeletedResume] = Object.values(userResumes).filter(
(resume) => resume.id === DatabaseConstants.initialStateResumeId,
(resume) => resume.id === DatabaseConstants.initialStateResume1Id,
);
const mockDatabaseRemoveFunction = jest.spyOn(

View File

@ -80,6 +80,7 @@ const dragAndDropListItem = (listItemElement, direction) => {
// eslint-disable-next-line no-underscore-dangle
async function _setup(
resumeId,
signInWithGoogle,
waitForLoadingScreenToDisappear,
waitForDatabaseUpdateToHaveCompleted,
) {
@ -96,7 +97,12 @@ async function _setup(
'update',
);
FirebaseStub.auth().signInAnonymously();
if (signInWithGoogle) {
const provider = new FirebaseStub.auth.GoogleAuthProvider();
FirebaseStub.auth().signInWithPopup(provider);
} else {
FirebaseStub.auth().signInAnonymously();
}
render(
<SettingsProvider>
@ -132,17 +138,19 @@ async function _setup(
}
async function setup(resumeId) {
const returnValue = await _setup(resumeId, false, false);
const returnValue = await _setup(resumeId, false, false, false);
return returnValue;
}
async function setupAndWait(
resumeId,
signInWithGoogle,
waitForLoadingScreenToDisappear,
waitForDatabaseUpdateToHaveCompleted,
) {
const returnValue = await _setup(
resumeId,
signInWithGoogle,
waitForLoadingScreenToDisappear,
waitForDatabaseUpdateToHaveCompleted,
);