From 78e16fbb14063bcbb831ffccbba35db9588b8234 Mon Sep 17 00:00:00 2001 From: markpit Date: Tue, 10 Dec 2024 09:56:32 +0000 Subject: [PATCH 1/3] LP-239 Add the limited partner choice page --- locales/cy/translations.json | 7 +++ locales/en/translations.json | 7 +++ src/config/constants.ts | 8 +-- .../controller/registration/Controller.ts | 9 +-- .../controller/registration/PageType.ts | 1 + .../controller/registration/Routing.ts | 21 +++++-- ...reateTransactionAndFirstSubmission.test.ts | 5 +- .../limited-partner-choice.test.ts | 60 +++++++++++++++++++ src/routes/registration.ts | 12 +++- src/views/general-partners.njk | 4 -- src/views/limited-partner-choice.njk | 47 +++++++++++++++ 11 files changed, 160 insertions(+), 21 deletions(-) create mode 100644 src/presentation/test/integration/registration/limited-partner-choice.test.ts create mode 100644 src/views/limited-partner-choice.njk diff --git a/locales/cy/translations.json b/locales/cy/translations.json index 165f6b6..68bf7c2 100644 --- a/locales/cy/translations.json +++ b/locales/cy/translations.json @@ -4,6 +4,13 @@ "saveAndContinue" : "WELSH - Save and continue" }, + "limitedPartnerChoicePage" : { + "isPersonOrLegalEntity" : "WELSH - Is the limited partner a person or a legal entity?", + "isPersonOrLegalEntityHint" : "WELSH - You can add more later.", + "person" : "WELSH - A person", + "legalEntity" : "WELSH - A legal entity" + }, + "namePage" : { "title" : "WELSH - Limited partnership name", "whatIsName" : "WELSH - What is the limited partnership name?", diff --git a/locales/en/translations.json b/locales/en/translations.json index c6de83e..2bc2c3c 100644 --- a/locales/en/translations.json +++ b/locales/en/translations.json @@ -4,6 +4,13 @@ "saveAndContinue" : "Save and continue" }, + "limitedPartnerChoicePage" : { + "isPersonOrLegalEntity" : "Is the limited partner a person or a legal entity?", + "isPersonOrLegalEntityHint" : "You can add more later.", + "person" : "A person", + "legalEntity" : "A legal entity" + }, + "namePage" : { "title" : "Limited partnership name", "whatIsName" : "What is the limited partnership name?", diff --git a/src/config/constants.ts b/src/config/constants.ts index c38c14f..c390fad 100644 --- a/src/config/constants.ts +++ b/src/config/constants.ts @@ -35,9 +35,7 @@ export const ERROR_TEMPLATE = "error-page"; export const NOT_FOUND_TEMPLATE = "page-not-found"; // Routing Paths +export const SUBMISSION_ID = "submissionId"; +export const TRANSACTION_ID = "transactionId"; export const BASE_URL = "/limited-partnerships"; - -export const TRANSACTION_ID = ":transactionId"; -export const SUBMISSION_ID = ":submissionId"; - -export const BASE_WITH_IDS_URL = `${BASE_URL}/transaction/${TRANSACTION_ID}/submission/${SUBMISSION_ID}`; +export const BASE_WITH_IDS_URL = `${BASE_URL}/transaction/:${TRANSACTION_ID}/submission/:${SUBMISSION_ID}`; diff --git a/src/presentation/controller/registration/Controller.ts b/src/presentation/controller/registration/Controller.ts index 70f7fa5..98627be 100644 --- a/src/presentation/controller/registration/Controller.ts +++ b/src/presentation/controller/registration/Controller.ts @@ -5,6 +5,7 @@ import RegistrationService from "../../../application/registration/Service"; import registrationsRouting from "./Routing"; import AbstractController from "../AbstractController"; import PageType from "./PageType"; +import { SUBMISSION_ID, TRANSACTION_ID } from "../../../config/constants"; class RegistrationController extends AbstractController { private registrationService: RegistrationService; @@ -85,15 +86,15 @@ class RegistrationController extends AbstractController { const registrationRouting = super.getRouting( registrationsRouting, - type + type, + request.params[TRANSACTION_ID], + request.params[SUBMISSION_ID] ); - const url = super.insertIdsInUrl(registrationRouting.nextUrl); - const pageType = escape(request.body.pageType); const parameter = escape(request.body.parameter); - response.redirect(`${url}?${pageType}=${parameter}`); + response.redirect(`${registrationRouting.nextUrl}?${pageType}=${parameter}`); } catch (error) { next(error); } diff --git a/src/presentation/controller/registration/PageType.ts b/src/presentation/controller/registration/PageType.ts index 2ff80e3..0047425 100644 --- a/src/presentation/controller/registration/PageType.ts +++ b/src/presentation/controller/registration/PageType.ts @@ -2,6 +2,7 @@ enum RegistrationPageType { name = "name", whichType = "which-type", generalPartners = "general-partners", + limitedPartnerChoice = "limited-partner-choice", next = "next", } diff --git a/src/presentation/controller/registration/Routing.ts b/src/presentation/controller/registration/Routing.ts index da441b3..ba2fe06 100644 --- a/src/presentation/controller/registration/Routing.ts +++ b/src/presentation/controller/registration/Routing.ts @@ -7,17 +7,20 @@ import { import RegistrationPageType from "./PageType"; import PageType from "../PageType"; -const START_URL = `${BASE_URL}/start`; +// Templates export const WHICH_TYPE_TEMPLATE = RegistrationPageType.whichType; export const NAME_TEMPLATE = RegistrationPageType.name; export const GENERAL_PARTNERS_TEMPLATE = RegistrationPageType.generalPartners; +export const LIMITED_PARTNER_CHOICE_TEMPLATE = RegistrationPageType.limitedPartnerChoice; export const NEXT_TEMPLATE = RegistrationPageType.next; +// URLs +const START_URL = `${BASE_URL}/start`; export const WHICH_TYPE_URL = `${BASE_URL}/${WHICH_TYPE_TEMPLATE}`; export const NAME_URL = `${BASE_URL}/${NAME_TEMPLATE}`; - +export const NAME_URL_WITH_IDS = `${BASE_WITH_IDS_URL}/${NAME_TEMPLATE}`; export const GENERAL_PARTNERS_URL = `${BASE_WITH_IDS_URL}/${GENERAL_PARTNERS_TEMPLATE}`; - +export const LIMITED_PARTNER_CHOICE_URL = `${BASE_WITH_IDS_URL}/${LIMITED_PARTNER_CHOICE_TEMPLATE}`; export const NEXT_URL = `${BASE_WITH_IDS_URL}/${NEXT_TEMPLATE}`; const registrationRoutingPartnershipType = { @@ -30,7 +33,7 @@ const registrationRoutingPartnershipType = { export const registrationRoutingName = { previousUrl: WHICH_TYPE_URL, currentUrl: NAME_URL, - nextUrl: NEXT_URL, + nextUrl: LIMITED_PARTNER_CHOICE_URL, pageType: RegistrationPageType.name, }; @@ -41,8 +44,15 @@ const registrationRoutingGeneralPartners = { pageType: RegistrationPageType.generalPartners, }; +export const registrationRoutingLimitedPartnerChoice = { + previousUrl: NAME_URL_WITH_IDS, + currentUrl: LIMITED_PARTNER_CHOICE_URL, + nextUrl: NEXT_URL, + pageType: RegistrationPageType.limitedPartnerChoice, +}; + const registrationRoutingNext = { - previousUrl: WHICH_TYPE_URL, + previousUrl: LIMITED_PARTNER_CHOICE_URL, currentUrl: NEXT_URL, nextUrl: "/", pageType: RegistrationPageType.next, @@ -52,6 +62,7 @@ const list = [ registrationRoutingPartnershipType, registrationRoutingName, registrationRoutingGeneralPartners, + registrationRoutingLimitedPartnerChoice, registrationRoutingNext, ]; diff --git a/src/presentation/test/integration/registration/createTransactionAndFirstSubmission.test.ts b/src/presentation/test/integration/registration/createTransactionAndFirstSubmission.test.ts index 7ebe57f..98c2386 100644 --- a/src/presentation/test/integration/registration/createTransactionAndFirstSubmission.test.ts +++ b/src/presentation/test/integration/registration/createTransactionAndFirstSubmission.test.ts @@ -11,6 +11,7 @@ import app from "../app"; import appRealDependencies from "../../../../app"; import { appDevDependencies } from "../../../../config/dev-dependencies"; import { + LIMITED_PARTNER_CHOICE_TEMPLATE, NAME_URL, registrationRoutingName, } from "../../../controller/registration/Routing"; @@ -45,7 +46,7 @@ describe("Create transaction and the first submission", () => { name_ending: NameEndingType.LIMITED_PARTNERSHIP, }); - const redirectUrl = `/limited-partnerships/transaction/${appDevDependencies.registrationGateway.transactionId}/submission/${appDevDependencies.registrationGateway.submissionId}/next`; + const redirectUrl = `/limited-partnerships/transaction/${appDevDependencies.registrationGateway.transactionId}/submission/${appDevDependencies.registrationGateway.submissionId}/${LIMITED_PARTNER_CHOICE_TEMPLATE}`; expect(res.status).toBe(302); expect(res.text).toContain(`Redirecting to ${redirectUrl}`); @@ -86,7 +87,7 @@ describe("Create transaction and the first submission", () => { name_ending: NameEndingType.LIMITED_PARTNERSHIP, }); - const partialRedirectUrl = `/limited-partnerships/transaction/${appDevDependencies.registrationGateway.transactionId}/submission/${appDevDependencies.registrationGateway.submissionId}/next`; + const partialRedirectUrl = `/limited-partnerships/transaction/${appDevDependencies.registrationGateway.transactionId}/submission/${appDevDependencies.registrationGateway.submissionId}/${LIMITED_PARTNER_CHOICE_TEMPLATE}`; expect(res.status).toBe(302); expect(res.text).toContain(`Redirecting to ${partialRedirectUrl}`); diff --git a/src/presentation/test/integration/registration/limited-partner-choice.test.ts b/src/presentation/test/integration/registration/limited-partner-choice.test.ts new file mode 100644 index 0000000..36b02a5 --- /dev/null +++ b/src/presentation/test/integration/registration/limited-partner-choice.test.ts @@ -0,0 +1,60 @@ +import request from "supertest"; +import { LocalesService } from "@companieshouse/ch-node-utils"; +import * as config from "../../../../config/constants"; +import enTranslationText from "../../../../../locales/en/translations.json"; +import cyTranslationText from "../../../../../locales/cy/translations.json"; +import app from "../app"; +import { + LIMITED_PARTNER_CHOICE_URL, + NEXT_URL, + registrationRoutingLimitedPartnerChoice, +} from "../../../controller/registration/Routing"; + +describe("Limited Partner Choice Page", () => { + beforeEach(() => { + setLocalesEnabled(false); + }); + + const setLocalesEnabled = (bool: boolean) => { + jest.spyOn(config, "isLocalesEnabled").mockReturnValue(bool); + LocalesService.getInstance().enabled = bool; + }; + + it("should load the limited partner choice page with Welsh text", async () => { + setLocalesEnabled(true); + const res = await request(app).get(LIMITED_PARTNER_CHOICE_URL + "?lang=cy"); + + expect(res.status).toBe(200); + expect(res.text).toContain(cyTranslationText.limitedPartnerChoicePage.isPersonOrLegalEntity); + }); + + it("should load the limited partner choice page with English text", async () => { + setLocalesEnabled(true); + const res = await request(app).get(LIMITED_PARTNER_CHOICE_URL + "?lang=en"); + + expect(res.status).toBe(200); + expect(res.text).toContain(enTranslationText.limitedPartnerChoicePage.isPersonOrLegalEntity); + }); + + it("should pass the limited partner choice as a url query param to next page", async () => { + const transactionId = "3664373"; + const submissionId = "1543454"; + + const url = LIMITED_PARTNER_CHOICE_URL + .replace(`:${config.TRANSACTION_ID}`, transactionId) + .replace(`:${config.SUBMISSION_ID}`, submissionId); + const res = await request(app) + .post(url) + .send({ + pageType: registrationRoutingLimitedPartnerChoice.pageType, + parameter: "person", + }); + + expect(res.status).toBe(302); + const nextPageUrl = NEXT_URL + .replace(`:${config.TRANSACTION_ID}`, transactionId) + .replace(`:${config.SUBMISSION_ID}`, submissionId) + + "?limited-partner-choice=person"; + expect(res.header.location).toEqual(nextPageUrl); + }); +}); diff --git a/src/routes/registration.ts b/src/routes/registration.ts index fdb9123..15466b9 100644 --- a/src/routes/registration.ts +++ b/src/routes/registration.ts @@ -9,6 +9,7 @@ import { NEXT_URL, WHICH_TYPE_URL, GENERAL_PARTNERS_URL, + LIMITED_PARTNER_CHOICE_URL, } from "../presentation/controller/registration/Routing"; export const registrationEndpoints = ( @@ -40,7 +41,16 @@ export const registrationEndpoints = ( authentication, dependencies.registrationController.getPageRouting() ); - + router.get( + LIMITED_PARTNER_CHOICE_URL, + authentication, + dependencies.registrationController.getPageRouting() + ); + router.post( + LIMITED_PARTNER_CHOICE_URL, + authentication, + dependencies.registrationController.redirectWithParameter() + ); router.get( NEXT_URL, authentication, diff --git a/src/views/general-partners.njk b/src/views/general-partners.njk index 926525e..0fb7a26 100644 --- a/src/views/general-partners.njk +++ b/src/views/general-partners.njk @@ -1,9 +1,5 @@ {% extends "layout.njk" %} -{% block beforeContent %} - {% include "includes/back-link.njk" %} -{% endblock %} - {% block content %}
diff --git a/src/views/limited-partner-choice.njk b/src/views/limited-partner-choice.njk new file mode 100644 index 0000000..d7f086f --- /dev/null +++ b/src/views/limited-partner-choice.njk @@ -0,0 +1,47 @@ +{% extends "layout.njk" %} + + +{% block content %} +
+
+ +
+ + {% include "includes/csrf_token.njk" %} + + {{ govukRadios({ + name: "parameter", + value: props.data.limitedPartnership.limited_partner, + fieldset: { + legend: { + text: i18n.limitedPartnerChoicePage.isPersonOrLegalEntity, + isPageHeading: true, + classes: "govuk-fieldset__legend--xl" + } + }, + hint: { + text: i18n.limitedPartnerChoicePage.isPersonOrLegalEntityHint + }, + items: [ + { + value: "person", + text: i18n.limitedPartnerChoicePage.person, + attributes : { + required : true + } + }, + { + value: "legal_entity", + text: i18n.limitedPartnerChoicePage.legalEntity, + attributes : { + required : true + } + } + ] + }) }} + + {% include "includes/save-and-continue-button.njk" %} +
+
+
+{% endblock %} From eab9e64c99a45b0d515894d0a31bfe71099dea5e Mon Sep 17 00:00:00 2001 From: markpit Date: Tue, 10 Dec 2024 13:31:48 +0000 Subject: [PATCH 2/3] LP-239 Remove whitespace --- src/presentation/controller/registration/Routing.ts | 2 -- .../registration/limited-partner-choice.test.ts | 12 ++++++------ src/views/limited-partner-choice.njk | 1 - 3 files changed, 6 insertions(+), 9 deletions(-) diff --git a/src/presentation/controller/registration/Routing.ts b/src/presentation/controller/registration/Routing.ts index 7f202cb..63734e0 100644 --- a/src/presentation/controller/registration/Routing.ts +++ b/src/presentation/controller/registration/Routing.ts @@ -12,7 +12,6 @@ export const WHICH_TYPE_TEMPLATE = RegistrationPageType.whichType; export const NAME_TEMPLATE = RegistrationPageType.name; export const EMAIL_TEMPLATE = RegistrationPageType.email; export const GENERAL_PARTNERS_TEMPLATE = RegistrationPageType.generalPartners; - export const LIMITED_PARTNER_CHOICE_TEMPLATE = RegistrationPageType.limitedPartnerChoice; export const NEXT_TEMPLATE = RegistrationPageType.next; @@ -21,7 +20,6 @@ const START_URL = `${BASE_URL}/start`; export const WHICH_TYPE_URL = `${BASE_URL}/${WHICH_TYPE_TEMPLATE}`; export const NAME_URL = `${BASE_URL}/${NAME_TEMPLATE}`; export const EMAIL_URL = `${BASE_WITH_IDS_URL}/${EMAIL_TEMPLATE}`; - export const GENERAL_PARTNERS_URL = `${BASE_WITH_IDS_URL}/${GENERAL_PARTNERS_TEMPLATE}`; export const LIMITED_PARTNER_CHOICE_URL = `${BASE_WITH_IDS_URL}/${LIMITED_PARTNER_CHOICE_TEMPLATE}`; export const NEXT_URL = `${BASE_WITH_IDS_URL}/${NEXT_TEMPLATE}`; diff --git a/src/presentation/test/integration/registration/limited-partner-choice.test.ts b/src/presentation/test/integration/registration/limited-partner-choice.test.ts index 0895315..4abe597 100644 --- a/src/presentation/test/integration/registration/limited-partner-choice.test.ts +++ b/src/presentation/test/integration/registration/limited-partner-choice.test.ts @@ -10,12 +10,6 @@ import { registrationRoutingLimitedPartnerChoice, } from "../../../controller/registration/Routing"; -const insertIdsInUrl = (url: string, transactionId: string, submissionId: string) => { - return url - .replace(`:${config.TRANSACTION_ID}`, transactionId) - .replace(`:${config.SUBMISSION_ID}`, submissionId); -}; - describe("Limited Partner Choice Page", () => { beforeEach(() => { setLocalesEnabled(false); @@ -26,6 +20,12 @@ describe("Limited Partner Choice Page", () => { LocalesService.getInstance().enabled = bool; }; + const insertIdsInUrl = (url: string, transactionId: string, submissionId: string) => { + return url + .replace(`:${config.TRANSACTION_ID}`, transactionId) + .replace(`:${config.SUBMISSION_ID}`, submissionId); + }; + it("should load the limited partner choice page with Welsh text", async () => { setLocalesEnabled(true); const res = await request(app).get(LIMITED_PARTNER_CHOICE_URL + "?lang=cy"); diff --git a/src/views/limited-partner-choice.njk b/src/views/limited-partner-choice.njk index d7f086f..dd6a4fc 100644 --- a/src/views/limited-partner-choice.njk +++ b/src/views/limited-partner-choice.njk @@ -1,6 +1,5 @@ {% extends "layout.njk" %} - {% block content %}
From f2033080b743f7e7eecba3aa51cfa7f426ffd198 Mon Sep 17 00:00:00 2001 From: markpit Date: Wed, 11 Dec 2024 09:37:31 +0000 Subject: [PATCH 3/3] LP-239 Use controller insertIds function --- .../controller/AbstractController.ts | 5 ++-- .../limited-partner-choice.test.ts | 25 +++++++++++-------- 2 files changed, 17 insertions(+), 13 deletions(-) diff --git a/src/presentation/controller/AbstractController.ts b/src/presentation/controller/AbstractController.ts index 3759a21..88b1fbd 100644 --- a/src/presentation/controller/AbstractController.ts +++ b/src/presentation/controller/AbstractController.ts @@ -1,3 +1,4 @@ +import { SUBMISSION_ID, TRANSACTION_ID } from "../../config/constants"; import { PageRouting, pageRoutingDefault, PagesRouting } from "./PageRouting"; import PageType from "./PageType"; @@ -41,11 +42,11 @@ abstract class AbstractController { } protected insertTransactionId(url: string, transactionId: string): string { - return transactionId ? url.replace(":transactionId", transactionId) : url; + return transactionId ? url.replace(`:${TRANSACTION_ID}`, transactionId) : url; } protected insertSubmissionId(url: string, submissionId: string): string { - return submissionId ? url.replace(":submissionId", submissionId) : url; + return submissionId ? url.replace(`:${SUBMISSION_ID}`, submissionId) : url; } protected insertIdsInAllUrl( diff --git a/src/presentation/test/integration/registration/limited-partner-choice.test.ts b/src/presentation/test/integration/registration/limited-partner-choice.test.ts index fd7f54d..e155f34 100644 --- a/src/presentation/test/integration/registration/limited-partner-choice.test.ts +++ b/src/presentation/test/integration/registration/limited-partner-choice.test.ts @@ -1,6 +1,7 @@ import request from "supertest"; import { LocalesService } from "@companieshouse/ch-node-utils"; -import * as config from "../../../../config/constants"; +import * as constants from "../../../../config/constants"; +import { appDevDependencies } from "../../../../config"; import enTranslationText from "../../../../../locales/en/translations.json"; import cyTranslationText from "../../../../../locales/cy/translations.json"; import app from "../app"; @@ -17,16 +18,10 @@ describe("Limited Partner Choice Page", () => { }); const setLocalesEnabled = (bool: boolean) => { - jest.spyOn(config, "isLocalesEnabled").mockReturnValue(bool); + jest.spyOn(constants, "isLocalesEnabled").mockReturnValue(bool); LocalesService.getInstance().enabled = bool; }; - const insertIdsInUrl = (url: string, transactionId: string, submissionId: string) => { - return url - .replace(`:${config.TRANSACTION_ID}`, transactionId) - .replace(`:${config.SUBMISSION_ID}`, submissionId); - }; - it("should load the limited partner choice page with Welsh text", async () => { setLocalesEnabled(true); const res = await request(app).get(LIMITED_PARTNER_CHOICE_URL + "?lang=cy"); @@ -48,7 +43,12 @@ describe("Limited Partner Choice Page", () => { const submissionId = "1543454"; const selectedChoice = "person"; - const url = insertIdsInUrl(LIMITED_PARTNER_CHOICE_URL, transactionId, submissionId); + const url = appDevDependencies.registrationController.insertIdsInUrl( + LIMITED_PARTNER_CHOICE_URL, + transactionId, + submissionId + ); + const res = await request(app) .post(url) .send({ @@ -57,8 +57,11 @@ describe("Limited Partner Choice Page", () => { }); expect(res.status).toBe(302); - const nextPageUrl = insertIdsInUrl(NEXT_URL, transactionId, submissionId) - + `?${RegistrationPageType.limitedPartnerChoice}=${selectedChoice}`; + const nextPageUrl = appDevDependencies.registrationController.insertIdsInUrl( + NEXT_URL, + transactionId, + submissionId + ) + `?${RegistrationPageType.limitedPartnerChoice}=${selectedChoice}`; expect(res.header.location).toEqual(nextPageUrl); }); });