From 1f1cab89ca5720621118e9a7ff1b4cdf083c8098 Mon Sep 17 00:00:00 2001 From: Edward Runkel Date: Wed, 29 Nov 2023 00:06:06 -0500 Subject: [PATCH 01/19] Create `PasswordInput` component --- .../PasswordInput/PasswordInput.test.ts | 36 ++++++++++++ .../inputs/PasswordInput/PasswordInput.vue | 57 +++++++++++++++++++ 2 files changed, 93 insertions(+) create mode 100644 components/elements/inputs/PasswordInput/PasswordInput.test.ts create mode 100644 components/elements/inputs/PasswordInput/PasswordInput.vue diff --git a/components/elements/inputs/PasswordInput/PasswordInput.test.ts b/components/elements/inputs/PasswordInput/PasswordInput.test.ts new file mode 100644 index 00000000..04615898 --- /dev/null +++ b/components/elements/inputs/PasswordInput/PasswordInput.test.ts @@ -0,0 +1,36 @@ +import { mount, enableAutoUnmount } from '@vue/test-utils' +import { getByTestId, getHTMLElement } from 'root/testUtils' +import PasswordInput from './PasswordInput.vue' + +function getPasswordInputWrapper() { + return mount(PasswordInput) +} + +afterEach(() => { + vi.restoreAllMocks() +}) + +enableAutoUnmount(afterEach) + +describe('', () => { + it('should render without crashing', () => { + const wrapper = getPasswordInputWrapper() + + expect(wrapper.isVisible()).toBe(true) + }) + + describe('when the hide/show button is clicked', () => { + it('changes the password input type to be text', async () => { + const wrapper = getPasswordInputWrapper() + const passwordInputElement = getHTMLElement( + wrapper.get('input'), + ) as HTMLInputElement + + expect(passwordInputElement.type).toBe('password') + + await getByTestId(wrapper, 'hide-show-button').trigger('click') + + expect(passwordInputElement.type).toBe('text') + }) + }) +}) diff --git a/components/elements/inputs/PasswordInput/PasswordInput.vue b/components/elements/inputs/PasswordInput/PasswordInput.vue new file mode 100644 index 00000000..7e4fbe8e --- /dev/null +++ b/components/elements/inputs/PasswordInput/PasswordInput.vue @@ -0,0 +1,57 @@ + + + + + From d17e746eaa8344378d724d9550897f7a04bed8be Mon Sep 17 00:00:00 2001 From: Edward Runkel Date: Wed, 6 Dec 2023 21:19:06 -0500 Subject: [PATCH 02/19] Create `ForgotPasswordCard` and add it to the `SiteNavBar` --- .../ForgotPasswordCard.test.ts | 47 ++++++ .../ForgotPasswordCard/ForgotPasswordCard.vue | 134 ++++++++++++++++++ .../blocks/cards/LogInCard/LogInCard.test.ts | 25 ++-- .../blocks/cards/LogInCard/LogInCard.vue | 54 +++---- .../cards/SignUpCard/SignUpCard.test.ts | 11 +- .../blocks/cards/SignUpCard/SignUpCard.vue | 35 +++-- .../blocks/nav/SiteNavbar/SiteNavbar.test.ts | 15 ++ .../blocks/nav/SiteNavbar/SiteNavbar.vue | 44 +++++- .../HideShowPassword/HideShowPassword.test.ts | 2 +- .../elements/inputs/BaseInput/BaseInput.vue | 2 +- 10 files changed, 297 insertions(+), 72 deletions(-) create mode 100644 components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.test.ts create mode 100644 components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.vue diff --git a/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.test.ts b/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.test.ts new file mode 100644 index 00000000..36264124 --- /dev/null +++ b/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.test.ts @@ -0,0 +1,47 @@ +import { mount, enableAutoUnmount } from '@vue/test-utils' +import { getByTestId } from 'root/testUtils' +import ForgotPasswordCard from './ForgotPasswordCard.vue' + +function getForgotPasswordCardWrapper() { + return mount(ForgotPasswordCard) +} + +enableAutoUnmount(afterEach) + +describe('', () => { + it('should render without crashing', () => { + const wrapper = getForgotPasswordCardWrapper() + + expect(wrapper.isVisible()).toBe(true) + }) + + describe('when the close button is clicked', () => { + it('should emit the close event', async () => { + const wrapper = getForgotPasswordCardWrapper() + + await getByTestId(wrapper, 'close-button').trigger('click') + + expect(wrapper.emitted().close).toBeTruthy() + }) + }) + + describe('when the cancel button is clicked', () => { + it('should emit the cancelClick event', async () => { + const wrapper = getForgotPasswordCardWrapper() + + await getByTestId(wrapper, 'cancel-button').trigger('click') + + expect(wrapper.emitted().cancelClick).toBeTruthy() + }) + }) + + describe('when the reset password button is clicked', () => { + it('should emit the close event', async () => { + const wrapper = getForgotPasswordCardWrapper() + + await getByTestId(wrapper, 'reset-password-button').trigger('click') + + expect(wrapper.emitted().close).toBeTruthy() + }) + }) +}) diff --git a/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.vue b/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.vue new file mode 100644 index 00000000..8bfaee96 --- /dev/null +++ b/components/blocks/cards/ForgotPasswordCard/ForgotPasswordCard.vue @@ -0,0 +1,134 @@ + + + + + diff --git a/components/blocks/cards/LogInCard/LogInCard.test.ts b/components/blocks/cards/LogInCard/LogInCard.test.ts index e029c9e0..38598c71 100644 --- a/components/blocks/cards/LogInCard/LogInCard.test.ts +++ b/components/blocks/cards/LogInCard/LogInCard.test.ts @@ -52,21 +52,6 @@ describe('', () => { }) }) - describe('when the hide/show button is clicked', () => { - it('changes the password input type to be text', async () => { - const wrapper = getLogInCardWrapper() - const passwordInputElement = getHTMLElement( - getByTestId(wrapper, 'password-input'), - ) as HTMLInputElement - - expect(passwordInputElement.type).toBe('password') - - await getByTestId(wrapper, 'hide-show-button').trigger('click') - - expect(passwordInputElement.type).toBe('text') - }) - }) - // TODO: skip this for now describe.skip('when enter key is released on the password input field', () => { it('emits the close event', async () => { @@ -138,6 +123,16 @@ describe('', () => { }) }) + describe('when the forgot password button is clicked', () => { + it('emits the forgot password click event', async () => { + const wrapper = getLogInCardWrapper() + + await getByTestId(wrapper, 'forgot-password-button').trigger('click') + + expect(wrapper.emitted().forgotPasswordClick).toBeTruthy() + }) + }) + describe('when the sign up button is clicked', () => { it('emits the sign up click event', async () => { const wrapper = getLogInCardWrapper() diff --git a/components/blocks/cards/LogInCard/LogInCard.vue b/components/blocks/cards/LogInCard/LogInCard.vue index d4e822d9..760fd9d4 100644 --- a/components/blocks/cards/LogInCard/LogInCard.vue +++ b/components/blocks/cards/LogInCard/LogInCard.vue @@ -3,7 +3,7 @@ import { type Ref, ref } from 'vue' import BaseButton from 'elements/buttons/BaseButton/BaseButton.vue' import CloseButton from 'elements/buttons/CloseButton/CloseButton.vue' import BaseInput from 'elements/inputs/BaseInput/BaseInput.vue' -import HideShowPassword from 'elements/buttons/HideShowPassword/HideShowPassword.vue' +import PasswordInput from 'elements/inputs/PasswordInput/PasswordInput.vue' import CardBody from 'elements/cards/CardBody/CardBody.vue' import CardHeader from 'elements/cards/CardHeader/CardHeader.vue' import Card from 'elements/cards/Card/Card.vue' @@ -21,6 +21,7 @@ interface LogInCardState { const emit = defineEmits<{ (event: 'close'): void + (event: 'forgotPasswordClick'): void (event: 'signUpClick'): void }>() @@ -89,32 +90,14 @@ function login() { data-testid="email-input" /> - +