Skip to content

Commit

Permalink
fix: saving user account info (#4121)
Browse files Browse the repository at this point in the history
  • Loading branch information
emilyjablonski committed Jun 6, 2024
1 parent e7a5f54 commit fa2f6c4
Show file tree
Hide file tree
Showing 13 changed files with 458 additions and 297 deletions.
8 changes: 8 additions & 0 deletions api/prisma/seed-dev.ts
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,14 @@ export const devSeeding = async (
password: 'abcdef',
}),
});
await prismaClient.userAccounts.create({
data: await userFactory({
email: 'public-user@example.com',
confirmedAt: new Date(),
jurisdictionIds: [jurisdiction.id],
password: 'abcdef',
}),
});
await prismaClient.userAccounts.create({
data: await userFactory({
roles: { isJurisdictionalAdmin: true },
Expand Down
2 changes: 2 additions & 0 deletions api/prisma/seed-helpers/user-factory.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { passwordToHash } from '../../src/utilities/password-helpers';
export const userFactory = async (optionalParams?: {
roles?: Prisma.UserRolesUncheckedCreateWithoutUserAccountsInput;
firstName?: string;
middleName?: string;
lastName?: string;
email?: string;
singleUseCode?: string;
Expand All @@ -21,6 +22,7 @@ export const userFactory = async (optionalParams?: {
optionalParams?.email?.toLocaleLowerCase() ||
`${randomNoun().toLowerCase()}${randomNoun().toLowerCase()}@${randomAdjective().toLowerCase()}.com`,
firstName: optionalParams?.firstName || 'First',
middleName: optionalParams?.middleName || 'Middle',
lastName: optionalParams?.lastName || 'Last',
passwordHash: optionalParams?.password
? await passwordToHash(optionalParams?.password)
Expand Down
8 changes: 8 additions & 0 deletions api/prisma/seed-staging.ts
Original file line number Diff line number Diff line change
Expand Up @@ -95,6 +95,14 @@ export const stagingSeed = async (
singleUseCode: '12345',
}),
});
await prismaClient.userAccounts.create({
data: await userFactory({
email: 'public-user@example.com',
confirmedAt: new Date(),
jurisdictionIds: [jurisdiction.id],
password: 'abcdef',
}),
});
// add jurisdiction specific translations and default ones
await prismaClient.translations.create({
data: translationFactory(jurisdiction.id, jurisdiction.name),
Expand Down
2 changes: 1 addition & 1 deletion sites/partners/src/components/users/FormUserConfirm.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ type FormUserConfirmFields = {
agree: boolean
}

const MIN_PASSWORD_LENGTH = 8
const MIN_PASSWORD_LENGTH = 12

const FormUserConfirm = () => {
// eslint-disable-next-line @typescript-eslint/unbound-method
Expand Down
63 changes: 63 additions & 0 deletions sites/public/cypress/e2e/account/account.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
import { publicUser, updatedPublicUser } from "../../mockData/userData"

describe("User accounts", () => {
it("should allow users to update their account information", () => {
cy.visit("/sign-in")
cy.signIn(publicUser.email, publicUser.password)

// Assert that a user's data shows up on their settings page
cy.getByID("account-dashboard-settings").click()
cy.getByTestId("loading-overlay").should("not.exist")
cy.getByTestId("account-first-name").should("have.value", publicUser.firstName)
cy.getByTestId("account-middle-name").should("have.value", publicUser.middleName)
cy.getByTestId("account-last-name").should("have.value", publicUser.lastName)
cy.getByTestId("dob-field-month").should("have.value", publicUser.birthMonth)
cy.getByTestId("dob-field-day").should("have.value", publicUser.birthDay)
cy.getByTestId("dob-field-year").should("have.value", publicUser.birthYear)
cy.getByTestId("account-email").should("have.value", publicUser.email)

// Change the name fields
cy.getByTestId("account-first-name").clear().type(updatedPublicUser.firstName)
cy.getByTestId("account-middle-name").clear().type(updatedPublicUser.middleName)
cy.getByTestId("account-last-name").clear().type(updatedPublicUser.lastName)
cy.getByID("account-submit-name").click()
cy.getByTestId("alert-box").contains("Name update successful")
cy.get("[aria-label='close alert']").click()
cy.getByTestId("alert-box").should("not.exist")

// Change the birthday field
cy.getByTestId("dob-field-month").clear().type(updatedPublicUser.birthMonth)
cy.getByTestId("dob-field-day").clear().type(updatedPublicUser.birthDay)
cy.getByTestId("dob-field-year").clear().type(updatedPublicUser.birthYear)
cy.getByID("account-submit-dob").click()
cy.getByTestId("alert-box").contains("Birthdate update successful")
cy.get("[aria-label='close alert']").click()
cy.getByTestId("alert-box").should("not.exist")

// Change the password
cy.getByTestId("account-current-password").type(publicUser.password)
cy.getByTestId("account-password").type(updatedPublicUser.password)
cy.getByTestId("account-password-confirmation").type(updatedPublicUser.passwordConfirmation)
cy.getByID("account-submit-password").click()
cy.getByTestId("alert-box").contains("Password update successful")
cy.get("[aria-label='close alert']").click()
cy.getByTestId("alert-box").should("not.exist")

cy.visit("/account/edit")

// Confirm that the data actually updated
cy.getByTestId("loading-overlay").should("not.exist")
cy.getByTestId("account-first-name").should("have.value", updatedPublicUser.firstName)
cy.getByTestId("account-middle-name").should("have.value", updatedPublicUser.middleName)
cy.getByTestId("account-last-name").should("have.value", updatedPublicUser.lastName)
cy.getByTestId("dob-field-month").should("have.value", updatedPublicUser.birthMonth)
cy.getByTestId("dob-field-day").should("have.value", updatedPublicUser.birthDay)
cy.getByTestId("dob-field-year").should("have.value", updatedPublicUser.birthYear)

cy.signOut()

// Confirm that the new password works
cy.visit("/sign-in")
cy.signIn(updatedPublicUser.email, updatedPublicUser.password)
})
})
8 changes: 5 additions & 3 deletions sites/public/cypress/mockData/applicationData.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,8 @@ import {
YesNoEnum,
UnitTypeEnum,
ApplicationMultiselectQuestion,
AlternateContactRelationship,
HouseholdMemberRelationship,
} from "@bloom-housing/shared-helpers/src/types/backend-swagger"

const idDefaults = {
Expand Down Expand Up @@ -133,7 +135,7 @@ export const ElmVillageApplication: Application = {
},
alternateContact: {
...idDefaults,
type: "other",
type: AlternateContactRelationship.other,
firstName: "Alternate Name",
lastName: "Alternate Last Name",
agency: "Agency Name",
Expand Down Expand Up @@ -184,7 +186,7 @@ export const ElmVillageApplication: Application = {
zipCode: "90224",
},
sameAddress: YesNoEnum.no,
relationship: "spouse",
relationship: HouseholdMemberRelationship.spouse,
workInRegion: YesNoEnum.yes,
},
],
Expand Down Expand Up @@ -370,7 +372,7 @@ export const minimalDataApplication: Application = {
},
alternateContact: {
...idDefaults,
type: "dontHave",
type: AlternateContactRelationship.noContact,
firstName: "",
lastName: "",
agency: "",
Expand Down
22 changes: 22 additions & 0 deletions sites/public/cypress/mockData/userData.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
export const publicUser = {
email: "public-user@example.com",
password: "abcdef",
firstName: "First",
middleName: "Middle",
lastName: "Last",
birthDay: "01",
birthMonth: "01",
birthYear: "1970",
}

export const updatedPublicUser = {
email: "public-user@example.com",
password: "Abcdefghijk1!",
passwordConfirmation: "Abcdefghijk1!",
firstName: "First Updated",
middleName: "Middle Updated",
lastName: "Last Updated",
birthDay: "20",
birthMonth: "12",
birthYear: "2000",
}
10 changes: 5 additions & 5 deletions sites/public/cypress/support/commands.js
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,9 @@ import {
raceCheckboxesOrder,
} from "./../mockData/applicationData"

Cypress.Commands.add("signIn", () => {
cy.get(`[data-testid="sign-in-email-field"]`).type("admin@example.com")
cy.get(`[data-testid="sign-in-password-field"]`).type("abcdef")
Cypress.Commands.add("signIn", (email, password) => {
cy.get(`[data-testid="sign-in-email-field"]`).type(email ?? "admin@example.com")
cy.get(`[data-testid="sign-in-password-field"]`).type(password ?? "abcdef")
cy.getByID("sign-in-button").click()
})

Expand Down Expand Up @@ -578,7 +578,7 @@ Cypress.Commands.add("step18Summary", (application, verify) => {
fields.push({ id: val, fieldValue: val })
}

if (application.alternateContact.type !== "dontHave") {
if (application.alternateContact.type !== "noContact") {
fields.push({
id: "app-summary-alternate-name",
fieldValue: `${application.alternateContact.firstName} ${application.alternateContact.lastName}`,
Expand Down Expand Up @@ -682,7 +682,7 @@ Cypress.Commands.add("submitApplication", (listingName, application, signedIn, v
cy.step1PrimaryApplicantName(application)
cy.step2PrimaryApplicantAddresses(application)
cy.step3AlternateContactType(application)
if (application.alternateContact.type !== "dontHave") {
if (application.alternateContact.type !== "noContact") {
cy.step4AlternateContactName(application)
cy.step5AlternateContactInfo(application)
}
Expand Down
2 changes: 1 addition & 1 deletion sites/public/cypress/support/helpers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ export const getListingIncome = (): GetIncomeReturn => {
}

export const updatePreferredUnits = ({ config, listing }: UpdatePreferredUnitsProps) => {
const firstUnitType = listing.units[0].unitType
const firstUnitType = listing.units[0].unitTypes
config.preferredUnit = [{ id: firstUnitType?.id }]

return config
Expand Down
2 changes: 1 addition & 1 deletion sites/public/cypress/support/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ declare namespace Cypress {
getPhoneFieldByTestId(testId: string): Chainable<Element>
goNext(): Chainable<Element>
isNextRouteValid(currentStep: string, skip?: number): Chainable
signIn(): Chainable
signIn(email?: string, password?: string): Chainable
signOut(): Chainable
step1PrimaryApplicantName(application: Application): Chainable
step2PrimaryApplicantAddresses(application: Application): Chainable
Expand Down
113 changes: 54 additions & 59 deletions sites/public/src/components/shared/FormSummaryDetails.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,8 +78,6 @@ const FormSummaryDetails = ({
return application.alternateContact.otherType
case "caseManager":
return application.alternateContact.agency
case "":
return ""
default:
return t(`application.alternateContact.type.options.${application.alternateContact.type}`)
}
Expand Down Expand Up @@ -291,69 +289,66 @@ const FormSummaryDetails = ({
)}
</Card.Section>

{application.alternateContact.type !== "" &&
application.alternateContact.type !== "noContact" && (
<>
<Card.Header className={styles["summary-header"]}>
<Heading priority={3} size="xl" className="font-serif font-normal">
{t("application.alternateContact.type.label")}
</Heading>
{editMode && !validationError && (
<Link href="/applications/contact/alternate-contact-type">{t("t.edit")}</Link>
)}
</Card.Header>

<Card.Section className={styles["summary-section"]}>
<p className={styles["summary-note-text"]}>
{t(`application.alternateContact.type.description`)}
</p>
{application.alternateContact.type && application.alternateContact.type !== "noContact" && (
<>
<Card.Header className={styles["summary-header"]}>
<Heading priority={3} size="xl" className="font-serif font-normal">
{t("application.alternateContact.type.label")}
</Heading>
{editMode && !validationError && (
<Link href="/applications/contact/alternate-contact-type">{t("t.edit")}</Link>
)}
</Card.Header>

<Card.Section className={styles["summary-section"]}>
<p className={styles["summary-note-text"]}>
{t(`application.alternateContact.type.description`)}
</p>
<FieldValue
testId={"app-summary-alternate-name"}
id="alternateName"
label={t("t.name")}
helpText={alternateContactName()}
className={styles["summary-value"]}
>
{application.alternateContact.firstName} {application.alternateContact.lastName}
</FieldValue>

{application.alternateContact.emailAddress && (
<FieldValue
testId={"app-summary-alternate-name"}
id="alternateName"
label={t("t.name")}
helpText={alternateContactName()}
testId={"app-summary-alternate-email"}
id="alternateEmail"
label={t("t.email")}
className={styles["summary-value"]}
>
{application.alternateContact.firstName} {application.alternateContact.lastName}
{application.alternateContact.emailAddress}
</FieldValue>
)}

{application.alternateContact.emailAddress && (
<FieldValue
testId={"app-summary-alternate-email"}
id="alternateEmail"
label={t("t.email")}
className={styles["summary-value"]}
>
{application.alternateContact.emailAddress}
</FieldValue>
)}

{application.alternateContact.phoneNumber && (
<FieldValue
testId={"app-summary-alternate-phone"}
id="alternatePhone"
label={t("t.phone")}
className={styles["summary-value"]}
>
{application.alternateContact.phoneNumber}
</FieldValue>
)}
{application.alternateContact.phoneNumber && (
<FieldValue
testId={"app-summary-alternate-phone"}
id="alternatePhone"
label={t("t.phone")}
className={styles["summary-value"]}
>
{application.alternateContact.phoneNumber}
</FieldValue>
)}

{Object.values(application.alternateContact.address).some(
(value) => value !== ""
) && (
<FieldValue
testId={"app-summary-alternate-mailing-address"}
id="alternateMailingAddress"
label={t("application.contact.address")}
className={styles["summary-value"]}
>
<MultiLineAddress address={application.alternateContact.address} />
</FieldValue>
)}
</Card.Section>
</>
)}
{Object.values(application.alternateContact.address).some((value) => value !== "") && (
<FieldValue
testId={"app-summary-alternate-mailing-address"}
id="alternateMailingAddress"
label={t("application.contact.address")}
className={styles["summary-value"]}
>
<MultiLineAddress address={application.alternateContact.address} />
</FieldValue>
)}
</Card.Section>
</>
)}

{application.householdSize > 1 && (
<>
Expand Down
7 changes: 6 additions & 1 deletion sites/public/src/pages/account/dashboard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,12 @@ function Dashboard(props: DashboardProps) {
headingPriority={2}
>
<Card.Section>
<Button size="sm" href={"/account/edit"} variant="primary-outlined">
<Button
size="sm"
href={"/account/edit"}
variant="primary-outlined"
id={"account-dashboard-settings"}
>
{t("account.accountSettingsUpdate")}
</Button>
</Card.Section>
Expand Down
Loading

0 comments on commit fa2f6c4

Please sign in to comment.