From 9fcb92c00639c78b7442e41d19bd53c2cc9223fd Mon Sep 17 00:00:00 2001 From: Benson Cho <100653148+bcho892@users.noreply.github.com> Date: Mon, 22 Jul 2024 19:04:42 +1200 Subject: [PATCH] enforce dietary requirements on booking creation (#676) --- .../BookingCreation/BookingCreation.test.tsx | 17 ++++ .../BookingCreation/BookingCreation.tsx | 78 +++++++++++++------ 2 files changed, 70 insertions(+), 25 deletions(-) diff --git a/client/src/components/composite/Booking/BookingCreation/BookingCreation.test.tsx b/client/src/components/composite/Booking/BookingCreation/BookingCreation.test.tsx index e0244beee..4c25b44df 100644 --- a/client/src/components/composite/Booking/BookingCreation/BookingCreation.test.tsx +++ b/client/src/components/composite/Booking/BookingCreation/BookingCreation.test.tsx @@ -50,8 +50,19 @@ describe("RequirementCheckBoxes", () => { "agreed-to-general-policy-checkbox" ) + const dietaryRequirementsInput = getByTestId("dietary-requirements-input") + fireEvent.click(nightPolicyCheckbox) fireEvent.click(bookingPolicyCheckbox) + fireEvent.change(dietaryRequirementsInput, { + target: { value: "i" } + }) + + expect(mockOnValidityChange).toHaveBeenCalledWith(false) + + fireEvent.change(dietaryRequirementsInput, { + target: { value: "i3" } + }) expect(mockOnValidityChange).toHaveBeenCalledWith(true) }) @@ -67,8 +78,14 @@ describe("RequirementCheckBoxes", () => { "agreed-to-general-policy-checkbox" ) + const dietaryRequirementsInput = getByTestId("dietary-requirements-input") + fireEvent.click(nightPolicyCheckbox) + fireEvent.change(dietaryRequirementsInput, { + target: { value: "ii" } + }) + expect(mockOnValidityChange).toHaveBeenCalledWith(false) fireEvent.click(bookingPolicyCheckbox) diff --git a/client/src/components/composite/Booking/BookingCreation/BookingCreation.tsx b/client/src/components/composite/Booking/BookingCreation/BookingCreation.tsx index 8f77a2701..adfd782c7 100644 --- a/client/src/components/composite/Booking/BookingCreation/BookingCreation.tsx +++ b/client/src/components/composite/Booking/BookingCreation/BookingCreation.tsx @@ -165,7 +165,9 @@ export const CreateBookingSection = ({ variant="default" onClick={() => { if (!isValidForCreation) { - alert("Please check all the required acknowledgements") + alert( + "Please check all the required acknowledgements and enter your dietary requirements" + ) return } if ( @@ -312,12 +314,7 @@ export const CreateBookingSection = ({ onValidityChange={(newValid) => { setIsValidForCreation(newValid) }} - /> - - handleAllergyChange?.(e.target.value)} - label="Please describe your dietary requirements" - placeholder="Enter dietary requirements here" + handleAllergyChange={handleAllergyChange} /> {hasExistingSession ? ( @@ -338,47 +335,78 @@ interface IRequirementCheckBoxes { * @param newValid if the current state of the checkboxes is valid */ onValidityChange: (newValid: boolean) => void + + /** + * @param newAllergies + */ + handleAllergyChange?: (newAllergies: string) => void } +/** + * To allow users to enter "no" + */ +const DIETARY_REQUIREMENTS_MIN_LENGTH = 2 as const + /** * Provides a way to see if the user has agreed to all required policy * @deprecated only for internal use in `BookingCreation`, exported for testing purposes */ export const RequirementCheckBoxes = ({ - onValidityChange + onValidityChange, + handleAllergyChange }: IRequirementCheckBoxes) => { const [acceptedRequirements, setAcceptedRequirements] = useState<{ nightPolicy?: boolean bookingPolicy?: boolean + dietaryRequirements?: boolean }>({}) useEffect(() => { onValidityChange( - !!acceptedRequirements.nightPolicy && !!acceptedRequirements.bookingPolicy + !!acceptedRequirements.nightPolicy && + !!acceptedRequirements.bookingPolicy && + !!acceptedRequirements.dietaryRequirements ) }, [acceptedRequirements, onValidityChange]) return ( - - { - setAcceptedRequirements({ - ...acceptedRequirements, - nightPolicy: e.target.checked - }) - }} - label="I understand that each date corresponds to one night's stay" - /> - + + { + setAcceptedRequirements({ + ...acceptedRequirements, + nightPolicy: e.target.checked + }) + }} + label="I understand that each date corresponds to one night's stay" + /> + { + setAcceptedRequirements({ + ...acceptedRequirements, + bookingPolicy: e.target.checked + }) + }} + /> + + + { + handleAllergyChange?.(e.target.value) + setAcceptedRequirements({ ...acceptedRequirements, - bookingPolicy: e.target.checked + dietaryRequirements: + e.target.value.length >= DIETARY_REQUIREMENTS_MIN_LENGTH }) }} + data-testid="dietary-requirements-input" + label="Please describe your dietary requirements" + placeholder="Enter dietary requirements here" /> - + ) }