@defra/forms-engine-plugin 0.1.19 → 0.1.21

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (108) hide show
  1. package/.server/client/javascripts/application.d.ts +1 -0
  2. package/.server/client/javascripts/file-upload.d.ts +9 -0
  3. package/.server/config/index.d.ts +45 -0
  4. package/.server/index.d.ts +1 -0
  5. package/.server/server/common/helpers/logging/logger-options.d.ts +80 -0
  6. package/.server/server/common/helpers/logging/logger.d.ts +1 -0
  7. package/.server/server/common/helpers/logging/request-logger.d.ts +83 -0
  8. package/.server/server/common/helpers/logging/request-tracing.d.ts +7 -0
  9. package/.server/server/common/helpers/redis-client.d.ts +9 -0
  10. package/.server/server/constants.d.ts +3 -0
  11. package/.server/server/index.d.ts +3 -0
  12. package/.server/server/plugins/crumb.d.ts +4 -0
  13. package/.server/server/plugins/engine/components/AutocompleteField.d.ts +55 -0
  14. package/.server/server/plugins/engine/components/CheckboxesField.d.ts +15 -0
  15. package/.server/server/plugins/engine/components/ComponentBase.d.ts +33 -0
  16. package/.server/server/plugins/engine/components/ComponentCollection.d.ts +60 -0
  17. package/.server/server/plugins/engine/components/DatePartsField.d.ts +76 -0
  18. package/.server/server/plugins/engine/components/Details.d.ts +53 -0
  19. package/.server/server/plugins/engine/components/EmailAddressField.d.ts +59 -0
  20. package/.server/server/plugins/engine/components/FileUploadField.d.ts +79 -0
  21. package/.server/server/plugins/engine/components/FormComponent.d.ts +95 -0
  22. package/.server/server/plugins/engine/components/Html.d.ts +53 -0
  23. package/.server/server/plugins/engine/components/InsetText.d.ts +52 -0
  24. package/.server/server/plugins/engine/components/List.d.ts +56 -0
  25. package/.server/server/plugins/engine/components/ListFormComponent.d.ts +71 -0
  26. package/.server/server/plugins/engine/components/Markdown.d.ts +53 -0
  27. package/.server/server/plugins/engine/components/MonthYearField.d.ts +75 -0
  28. package/.server/server/plugins/engine/components/MultilineTextField.d.ts +67 -0
  29. package/.server/server/plugins/engine/components/NumberField.d.ts +68 -0
  30. package/.server/server/plugins/engine/components/RadiosField.d.ts +6 -0
  31. package/.server/server/plugins/engine/components/SelectField.d.ts +55 -0
  32. package/.server/server/plugins/engine/components/SelectionControlField.d.ts +60 -0
  33. package/.server/server/plugins/engine/components/TelephoneNumberField.d.ts +62 -0
  34. package/.server/server/plugins/engine/components/TextField.d.ts +19 -0
  35. package/.server/server/plugins/engine/components/UkAddressField.d.ts +80 -0
  36. package/.server/server/plugins/engine/components/YesNoField.d.ts +19 -0
  37. package/.server/server/plugins/engine/components/YesNoField.js +7 -0
  38. package/.server/server/plugins/engine/components/YesNoField.js.map +1 -1
  39. package/.server/server/plugins/engine/components/constants.d.ts +1 -0
  40. package/.server/server/plugins/engine/components/helpers.d.ts +40 -0
  41. package/.server/server/plugins/engine/components/index.d.ts +24 -0
  42. package/.server/server/plugins/engine/components/types.d.ts +100 -0
  43. package/.server/server/plugins/engine/configureEnginePlugin.d.ts +8 -0
  44. package/.server/server/plugins/engine/helpers.d.ts +74 -0
  45. package/.server/server/plugins/engine/index.d.ts +10 -0
  46. package/.server/server/plugins/engine/models/FormModel.d.ts +59 -0
  47. package/.server/server/plugins/engine/models/RepeatingSummaryViewModel.d.ts +1 -0
  48. package/.server/server/plugins/engine/models/Section.d.ts +1 -0
  49. package/.server/server/plugins/engine/models/SummaryViewModel.d.ts +25 -0
  50. package/.server/server/plugins/engine/models/index.d.ts +2 -0
  51. package/.server/server/plugins/engine/models/types.d.ts +87 -0
  52. package/.server/server/plugins/engine/outputFormatters/human/v1.d.ts +5 -0
  53. package/.server/server/plugins/engine/outputFormatters/index.d.ts +7 -0
  54. package/.server/server/plugins/engine/outputFormatters/machine/v1.d.ts +5 -0
  55. package/.server/server/plugins/engine/outputFormatters/machine/v2.d.ts +5 -0
  56. package/.server/server/plugins/engine/pageControllers/FileUploadPageController.d.ts +61 -0
  57. package/.server/server/plugins/engine/pageControllers/PageController.d.ts +43 -0
  58. package/.server/server/plugins/engine/pageControllers/QuestionPageController.d.ts +58 -0
  59. package/.server/server/plugins/engine/pageControllers/RepeatPageController.d.ts +35 -0
  60. package/.server/server/plugins/engine/pageControllers/StartPageController.d.ts +50 -0
  61. package/.server/server/plugins/engine/pageControllers/StatusPageController.d.ts +12 -0
  62. package/.server/server/plugins/engine/pageControllers/SummaryPageController.d.ts +26 -0
  63. package/.server/server/plugins/engine/pageControllers/TerminalPageController.d.ts +9 -0
  64. package/.server/server/plugins/engine/pageControllers/helpers.d.ts +19 -0
  65. package/.server/server/plugins/engine/pageControllers/index.d.ts +8 -0
  66. package/.server/server/plugins/engine/pageControllers/validationOptions.d.ts +8 -0
  67. package/.server/server/plugins/engine/plugin.d.ts +33 -0
  68. package/.server/server/plugins/engine/referenceNumbers.d.ts +5 -0
  69. package/.server/server/plugins/engine/services/formSubmissionService.d.ts +24 -0
  70. package/.server/server/plugins/engine/services/formsService.d.ts +16 -0
  71. package/.server/server/plugins/engine/services/index.d.ts +3 -0
  72. package/.server/server/plugins/engine/services/localFormsService.d.ts +1 -0
  73. package/.server/server/plugins/engine/services/notifyService.d.ts +5 -0
  74. package/.server/server/plugins/engine/services/uploadService.d.ts +14 -0
  75. package/.server/server/plugins/engine/types.d.ts +256 -0
  76. package/.server/server/plugins/errorPages.d.ts +7 -0
  77. package/.server/server/plugins/nunjucks/context.d.ts +16 -0
  78. package/.server/server/plugins/nunjucks/environment.d.ts +21 -0
  79. package/.server/server/plugins/nunjucks/filters/answer.d.ts +7 -0
  80. package/.server/server/plugins/nunjucks/filters/evaluate.d.ts +8 -0
  81. package/.server/server/plugins/nunjucks/filters/field.d.ts +7 -0
  82. package/.server/server/plugins/nunjucks/filters/highlight.d.ts +7 -0
  83. package/.server/server/plugins/nunjucks/filters/href.d.ts +7 -0
  84. package/.server/server/plugins/nunjucks/filters/index.d.ts +8 -0
  85. package/.server/server/plugins/nunjucks/filters/inspect.d.ts +6 -0
  86. package/.server/server/plugins/nunjucks/filters/page.d.ts +7 -0
  87. package/.server/server/plugins/nunjucks/index.d.ts +3 -0
  88. package/.server/server/plugins/nunjucks/plugin.d.ts +6 -0
  89. package/.server/server/plugins/nunjucks/render.d.ts +21 -0
  90. package/.server/server/plugins/nunjucks/types.d.ts +56 -0
  91. package/.server/server/plugins/pulse.d.ts +11 -0
  92. package/.server/server/plugins/session.d.ts +24 -0
  93. package/.server/server/routes/index.d.ts +1 -0
  94. package/.server/server/routes/public.d.ts +15 -0
  95. package/.server/server/routes/types.d.ts +38 -0
  96. package/.server/server/schemas/index.d.ts +10 -0
  97. package/.server/server/secure-context.d.ts +12 -0
  98. package/.server/server/services/cacheService.d.ts +49 -0
  99. package/.server/server/services/httpService.d.ts +57 -0
  100. package/.server/server/services/index.d.ts +1 -0
  101. package/.server/server/types.d.ts +31 -0
  102. package/.server/server/utils/file-form-service.d.ts +50 -0
  103. package/.server/server/utils/notify.d.ts +17 -0
  104. package/.server/server/utils/secure-context/get-trust-store-certs.d.ts +1 -0
  105. package/.server/server/utils/type-utils.d.ts +3 -0
  106. package/.server/server/utils/utils.d.ts +7 -0
  107. package/package.json +3 -2
  108. package/src/server/plugins/engine/components/YesNoField.ts +7 -0
@@ -0,0 +1,59 @@
1
+ import { Engine, type ComponentDef, type ConditionWrapper, type ConditionsModelData, type FormDefinition, type List, type Page } from '@defra/forms-model';
2
+ import { Parser, type Value } from 'expr-eval';
3
+ import joi from 'joi';
4
+ import { type Component } from '~/src/server/plugins/engine/components/helpers.js';
5
+ import { type ExecutableCondition } from '~/src/server/plugins/engine/models/types.js';
6
+ import { type PageController } from '~/src/server/plugins/engine/pageControllers/PageController.js';
7
+ import { type PageControllerClass } from '~/src/server/plugins/engine/pageControllers/helpers.js';
8
+ import { type FormContext, type FormContextRequest, type FormState, type FormSubmissionError, type FormSubmissionState } from '~/src/server/plugins/engine/types.js';
9
+ import { type Services } from '~/src/server/types.js';
10
+ export declare class FormModel {
11
+ /** The runtime engine that should be used */
12
+ engine?: Engine;
13
+ /** the entire form JSON as an object */
14
+ def: FormDefinition;
15
+ lists: FormDefinition['lists'];
16
+ sections: FormDefinition['sections'];
17
+ name: string;
18
+ values: FormDefinition;
19
+ basePath: string;
20
+ conditions: Partial<Record<string, ExecutableCondition>>;
21
+ pages: PageControllerClass[];
22
+ services: Services;
23
+ controllers?: Record<string, typeof PageController>;
24
+ pageDefMap: Map<string, Page>;
25
+ listDefMap: Map<string, List>;
26
+ componentDefMap: Map<string, ComponentDef>;
27
+ pageMap: Map<string, PageControllerClass>;
28
+ componentMap: Map<string, Component>;
29
+ constructor(def: typeof this.def, options: {
30
+ basePath: string;
31
+ }, services?: Services, controllers?: Record<string, typeof PageController>);
32
+ /**
33
+ * build the entire model schema from individual pages/sections
34
+ */
35
+ makeSchema(): joi.ObjectSchema<FormSubmissionState>;
36
+ /**
37
+ * build the entire model schema from individual pages/sections and filter out answers
38
+ * for pages which are no longer accessible due to an answer that has been changed
39
+ */
40
+ makeFilteredSchema(relevantPages: PageControllerClass[]): joi.ObjectSchema<FormSubmissionState>;
41
+ /**
42
+ * Instantiates a Condition based on {@link ConditionWrapper}
43
+ * @param condition
44
+ */
45
+ makeCondition(condition: ConditionWrapper): ExecutableCondition;
46
+ toConditionContext(evaluationState: FormState, conditions: Partial<Record<string, ExecutableCondition>>): Extract<Value, Record<string, Value>>;
47
+ toConditionExpression(value: ConditionsModelData, parser: Parser): import("expr-eval").Expression;
48
+ getList(name: string): List | undefined;
49
+ /**
50
+ * Form context for the current page
51
+ */
52
+ getFormContext(request: FormContextRequest, state: FormState, errors?: FormSubmissionError[]): FormContext;
53
+ private initialiseContext;
54
+ private assignEvaluationState;
55
+ private assignRelevantState;
56
+ private pageStateIsInvalid;
57
+ private fieldStateIsInvalid;
58
+ private assignPaths;
59
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,25 @@
1
+ import { type BackLink, type ComponentViewModel } from '~/src/server/plugins/engine/components/types.js';
2
+ import { type Detail } from '~/src/server/plugins/engine/models/types.js';
3
+ import { type PageControllerClass } from '~/src/server/plugins/engine/pageControllers/helpers.js';
4
+ import { type CheckAnswers, type FormContext, type FormContextRequest, type FormSubmissionError } from '~/src/server/plugins/engine/types.js';
5
+ export declare class SummaryViewModel {
6
+ /**
7
+ * Responsible for parsing state values to the govuk-frontend summary list template
8
+ */
9
+ page: PageControllerClass;
10
+ pageTitle: string;
11
+ declaration?: string;
12
+ details: Detail[];
13
+ checkAnswers: CheckAnswers[];
14
+ context: FormContext;
15
+ name: string | undefined;
16
+ backLink?: BackLink;
17
+ feedbackLink?: string;
18
+ phaseTag?: string;
19
+ errors?: FormSubmissionError[];
20
+ serviceUrl: string;
21
+ hasMissingNotificationEmail?: boolean;
22
+ components?: ComponentViewModel[];
23
+ constructor(request: FormContextRequest, page: PageControllerClass, context: FormContext);
24
+ private summaryDetails;
25
+ }
@@ -0,0 +1,2 @@
1
+ export { FormModel } from '~/src/server/plugins/engine/models/FormModel.js';
2
+ export { SummaryViewModel } from '~/src/server/plugins/engine/models/SummaryViewModel.js';
@@ -0,0 +1,87 @@
1
+ import { type ConditionWrapper, type Section } from '@defra/forms-model';
2
+ import { type Expression } from 'expr-eval';
3
+ import { type Field } from '~/src/server/plugins/engine/components/helpers.js';
4
+ import { type RepeatPageController } from '~/src/server/plugins/engine/pageControllers/RepeatPageController.js';
5
+ import { type PageControllerClass } from '~/src/server/plugins/engine/pageControllers/helpers.js';
6
+ import { type FormState, type FormSubmissionError } from '~/src/server/plugins/engine/types.js';
7
+ export type ExecutableCondition = ConditionWrapper & {
8
+ expr: Expression;
9
+ fn: (evaluationState: FormState) => boolean;
10
+ };
11
+ /**
12
+ * Used to render a row on a Summary List (check your answers)
13
+ */
14
+ export interface DetailItemBase {
15
+ /**
16
+ * Name of the component defined in the JSON
17
+ * @see {@link FormComponentsDef.name}
18
+ */
19
+ name: string;
20
+ /**
21
+ * Field label, used for change link visually hidden text
22
+ * @see {@link FormComponentsDef.title}
23
+ */
24
+ label: string;
25
+ /**
26
+ * Field change link
27
+ */
28
+ href: string;
29
+ /**
30
+ * Form submission state (or repeat state for sub items)
31
+ */
32
+ state: FormState;
33
+ /**
34
+ * Field submission state error, used to flag unanswered questions
35
+ * Shown as 'Complete all unanswered questions before submitting the form'
36
+ */
37
+ error?: FormSubmissionError;
38
+ }
39
+ export interface DetailItemField extends DetailItemBase {
40
+ /**
41
+ * Field page controller instance
42
+ */
43
+ page: Exclude<PageControllerClass, RepeatPageController>;
44
+ /**
45
+ * Check answers summary list key
46
+ * For example, 'Date of birth'
47
+ */
48
+ title: string;
49
+ /**
50
+ * Check answers summary list value, formatted by {@link getAnswer}
51
+ * For example, date fields formatted as '25 December 2022'
52
+ */
53
+ value: string;
54
+ /**
55
+ * Field component instance
56
+ */
57
+ field: Field;
58
+ }
59
+ export interface DetailItemRepeat extends DetailItemBase {
60
+ /**
61
+ * Repeat page controller instance
62
+ */
63
+ page: RepeatPageController;
64
+ /**
65
+ * Check answers summary list key
66
+ * For example, 'Pizza' or 'Pizza added'
67
+ */
68
+ title: string;
69
+ /**
70
+ * Check answers summary list value
71
+ * For example, 'You added 2 Pizzas'
72
+ */
73
+ value: string;
74
+ /**
75
+ * Repeater field detail items
76
+ */
77
+ subItems: DetailItemField[][];
78
+ }
79
+ export type DetailItem = DetailItemField | DetailItemRepeat;
80
+ /**
81
+ * Used to render a row on a Summary List (check your answers)
82
+ */
83
+ export interface Detail {
84
+ name?: Section['name'];
85
+ title?: Section['title'];
86
+ items: DetailItem[];
87
+ }
@@ -0,0 +1,5 @@
1
+ import { type SubmitResponsePayload } from '@defra/forms-model';
2
+ import { type checkFormStatus } from '~/src/server/plugins/engine/helpers.js';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type DetailItem } from '~/src/server/plugins/engine/models/types.js';
5
+ export declare function format(items: DetailItem[], model: FormModel, submitResponse: SubmitResponsePayload, formStatus: ReturnType<typeof checkFormStatus>): string;
@@ -0,0 +1,7 @@
1
+ import { type SubmitResponsePayload } from '@defra/forms-model';
2
+ import { type checkFormStatus } from '~/src/server/plugins/engine/helpers.js';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type DetailItem } from '~/src/server/plugins/engine/models/types.js';
5
+ type Formatter = (items: DetailItem[], model: FormModel, submitResponse: SubmitResponsePayload, formStatus: ReturnType<typeof checkFormStatus>) => string;
6
+ export declare function getFormatter(audience: string, version: string): Formatter;
7
+ export {};
@@ -0,0 +1,5 @@
1
+ import { type SubmitResponsePayload } from '@defra/forms-model';
2
+ import { type checkFormStatus } from '~/src/server/plugins/engine/helpers.js';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type DetailItem } from '~/src/server/plugins/engine/models/types.js';
5
+ export declare function format(items: DetailItem[], model: FormModel, _submitResponse: SubmitResponsePayload, _formStatus: ReturnType<typeof checkFormStatus>): string;
@@ -0,0 +1,5 @@
1
+ import { type SubmitResponsePayload } from '@defra/forms-model';
2
+ import { type checkFormStatus } from '~/src/server/plugins/engine/helpers.js';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type DetailItem } from '~/src/server/plugins/engine/models/types.js';
5
+ export declare function format(items: DetailItem[], model: FormModel, _submitResponse: SubmitResponsePayload, _formStatus: ReturnType<typeof checkFormStatus>): string;
@@ -0,0 +1,61 @@
1
+ import { type PageFileUpload } from '@defra/forms-model';
2
+ import { type ResponseToolkit } from '@hapi/hapi';
3
+ import { type ValidationErrorItem } from 'joi';
4
+ import { type FileUploadField } from '~/src/server/plugins/engine/components/FileUploadField.js';
5
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
6
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
7
+ import { type FeaturedFormPageViewModel, type FormContext, type FormContextRequest, type FormSubmissionError, type FormSubmissionState, type UploadInitiateResponse, type UploadStatusFileResponse } from '~/src/server/plugins/engine/types.js';
8
+ import { type FormRequest, type FormRequestPayload } from '~/src/server/routes/types.js';
9
+ export declare function prepareStatus(status: UploadStatusFileResponse): UploadStatusFileResponse;
10
+ export declare class FileUploadPageController extends QuestionPageController {
11
+ pageDef: PageFileUpload;
12
+ fileUpload: FileUploadField;
13
+ fileDeleteViewName: string;
14
+ constructor(model: FormModel, pageDef: PageFileUpload);
15
+ getFormDataFromState(request: FormContextRequest | undefined, state: FormSubmissionState): import("~/src/server/plugins/engine/types.js").FormPayload;
16
+ getState(request: FormRequest | FormRequestPayload): Promise<FormSubmissionState>;
17
+ /**
18
+ * Get the uploaded files from state.
19
+ */
20
+ getFilesFromState(state: FormSubmissionState): import("~/src/server/plugins/engine/types.js").UploadState;
21
+ /**
22
+ * Get the initiated upload from state.
23
+ */
24
+ getUploadFromState(state: FormSubmissionState): UploadInitiateResponse | undefined;
25
+ makeGetItemDeleteRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => import("@hapi/hapi").ResponseObject;
26
+ makePostItemDeleteRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
27
+ getErrors(details?: ValidationErrorItem[]): FormSubmissionError[] | undefined;
28
+ getViewModel(request: FormContextRequest, context: FormContext): FeaturedFormPageViewModel;
29
+ /**
30
+ * Refreshes the CDP upload and files in the
31
+ * state and checks for any removed files.
32
+ *
33
+ * If an upload exists and hasn't been consumed
34
+ * it gets re-used, otherwise we initiate a new one.
35
+ * @param request - the hapi request
36
+ * @param state - the form state
37
+ */
38
+ private refreshUpload;
39
+ /**
40
+ * If an upload exists and hasn't been consumed
41
+ * it gets re-used, otherwise a new one is initiated.
42
+ * @param request - the hapi request
43
+ * @param state - the form state
44
+ * @param depth - the number of retries so far
45
+ */
46
+ private checkUploadStatus;
47
+ /**
48
+ * Checks the payload for a file getting removed
49
+ * and removes it from the upload files if found
50
+ * @param request - the hapi request
51
+ * @param state - the form state
52
+ * @returns updated state if any files have been removed
53
+ */
54
+ private checkRemovedFiles;
55
+ /**
56
+ * Initiates a CDP file upload and stores in the upload state
57
+ * @param request - the hapi request
58
+ * @param state - the form state
59
+ */
60
+ private initiateAndStoreNewUpload;
61
+ }
@@ -0,0 +1,43 @@
1
+ import { type Events, type FormDefinition, type Page, type Section } from '@defra/forms-model';
2
+ import { type Lifecycle, type ResponseToolkit, type RouteOptions } from '@hapi/hapi';
3
+ import { type ComponentCollection } from '~/src/server/plugins/engine/components/ComponentCollection.js';
4
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
5
+ import { type ExecutableCondition } from '~/src/server/plugins/engine/models/types.js';
6
+ import { type FormContext, type PageViewModelBase } from '~/src/server/plugins/engine/types.js';
7
+ import { type FormRequest, type FormRequestPayload, type FormRequestPayloadRefs, type FormRequestRefs } from '~/src/server/routes/types.js';
8
+ export declare class PageController {
9
+ /**
10
+ * The base class for all page controllers. Page controllers are responsible for generating the get and post route handlers when a user navigates to `/{id}/{path*}`.
11
+ */
12
+ def: FormDefinition;
13
+ name?: string;
14
+ model: FormModel;
15
+ pageDef: Page;
16
+ title: string;
17
+ section?: Section;
18
+ condition?: ExecutableCondition;
19
+ events?: Events;
20
+ collection?: ComponentCollection;
21
+ viewName: string;
22
+ constructor(model: FormModel, pageDef: Page);
23
+ get path(): string;
24
+ get href(): string;
25
+ get keys(): string[];
26
+ /**
27
+ * {@link https://hapi.dev/api/?v=20.1.2#route-options}
28
+ */
29
+ get getRouteOptions(): RouteOptions<FormRequestRefs>;
30
+ /**
31
+ * {@link https://hapi.dev/api/?v=20.1.2#route-options}
32
+ */
33
+ get postRouteOptions(): RouteOptions<FormRequestPayloadRefs>;
34
+ get viewModel(): PageViewModelBase;
35
+ get feedbackLink(): string | undefined;
36
+ get phaseTag(): "beta" | "alpha" | undefined;
37
+ getHref(path: string): string;
38
+ getStartPath(): string;
39
+ getSummaryPath(): string;
40
+ getStatusPath(): string;
41
+ makeGetRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, 'redirect' | 'view'>) => ReturnType<Lifecycle.Method<FormRequestRefs>>;
42
+ makePostRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, 'redirect' | 'view'>) => ReturnType<Lifecycle.Method<FormRequestPayloadRefs>>;
43
+ }
@@ -0,0 +1,58 @@
1
+ import { type Link, type Page } from '@defra/forms-model';
2
+ import { type ResponseToolkit, type RouteOptions } from '@hapi/hapi';
3
+ import { type ValidationErrorItem } from 'joi';
4
+ import { ComponentCollection } from '~/src/server/plugins/engine/components/ComponentCollection.js';
5
+ import { type BackLink } from '~/src/server/plugins/engine/components/types.js';
6
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
7
+ import { PageController } from '~/src/server/plugins/engine/pageControllers/PageController.js';
8
+ import { type FormContext, type FormContextRequest, type FormPageViewModel, type FormParams, type FormPayload, type FormState, type FormStateValue, type FormSubmissionState } from '~/src/server/plugins/engine/types.js';
9
+ import { type FormRequest, type FormRequestPayload, type FormRequestPayloadRefs, type FormRequestRefs } from '~/src/server/routes/types.js';
10
+ export declare class QuestionPageController extends PageController {
11
+ collection: ComponentCollection;
12
+ errorSummaryTitle: string;
13
+ constructor(model: FormModel, pageDef: Page);
14
+ get next(): Link[];
15
+ get allowContinue(): boolean;
16
+ getItemId(request?: FormContextRequest): string | undefined;
17
+ /**
18
+ * Used for mapping form payloads and errors to govuk-frontend's template api, so a page can be rendered
19
+ * @param request - the hapi request
20
+ * @param context - the form context
21
+ */
22
+ getViewModel(request: FormContextRequest, context: FormContext): FormPageViewModel;
23
+ getRelevantPath(request: FormRequest | FormRequestPayload, context: FormContext): string;
24
+ /**
25
+ * Apply conditions to evaluation state to determine next page path
26
+ */
27
+ getNextPath(context: FormContext): string | undefined;
28
+ /**
29
+ * Gets the form payload (from state) for this page only
30
+ */
31
+ getFormDataFromState(request: FormContextRequest | undefined, state: FormSubmissionState): FormPayload;
32
+ /**
33
+ * Gets form params (from payload) for this page only
34
+ */
35
+ getFormParams(request?: FormContextRequest): FormParams;
36
+ getStateFromValidForm(request: FormContextRequest, state: FormSubmissionState, payload: FormPayload): FormState;
37
+ getErrors(details?: ValidationErrorItem[]): import("~/src/server/plugins/engine/types.js").FormSubmissionError[] | undefined;
38
+ getState(request: FormRequest | FormRequestPayload): Promise<FormSubmissionState>;
39
+ setState(request: FormRequest | FormRequestPayload, state: FormSubmissionState): Promise<FormSubmissionState>;
40
+ mergeState(request: FormRequest | FormRequestPayload, state: FormSubmissionState, update: object): Promise<FormSubmissionState>;
41
+ filterConditionalComponents(viewModel: FormPageViewModel, model: FormModel, evaluationState: Partial<Record<string, FormStateValue>>): import("~/src/server/plugins/engine/components/types.js").ComponentViewModel[];
42
+ makeGetRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
43
+ hasMissingNotificationEmail(request: FormRequest, context: FormContext): Promise<boolean>;
44
+ /**
45
+ * Get the back link for a given progress.
46
+ */
47
+ protected getBackLink(request: FormContextRequest, context: FormContext): BackLink | undefined;
48
+ makePostRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
49
+ proceed(request: FormContextRequest, h: Pick<ResponseToolkit, 'redirect' | 'view'>, nextPath?: string): import("@hapi/hapi").ResponseObject;
50
+ /**
51
+ * {@link https://hapi.dev/api/?v=20.1.2#route-options}
52
+ */
53
+ get getRouteOptions(): RouteOptions<FormRequestRefs>;
54
+ /**
55
+ * {@link https://hapi.dev/api/?v=20.1.2#route-options}
56
+ */
57
+ get postRouteOptions(): RouteOptions<FormRequestPayloadRefs>;
58
+ }
@@ -0,0 +1,35 @@
1
+ import { type PageRepeat, type Repeat } from '@defra/forms-model';
2
+ import { type ResponseToolkit } from '@hapi/hapi';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
5
+ import { type FormContext, type FormContextRequest, type FormPageViewModel, type FormPayload, type FormSubmissionState, type RepeatItemState, type RepeatListState, type RepeaterSummaryPageViewModel } from '~/src/server/plugins/engine/types.js';
6
+ import { FormAction, type FormRequest, type FormRequestPayload } from '~/src/server/routes/types.js';
7
+ export declare class RepeatPageController extends QuestionPageController {
8
+ pageDef: PageRepeat;
9
+ listSummaryViewName: string;
10
+ listDeleteViewName: string;
11
+ repeat: Repeat;
12
+ constructor(model: FormModel, pageDef: PageRepeat);
13
+ get keys(): string[];
14
+ getFormParams(request?: FormContextRequest): import("~/src/server/plugins/engine/types.js").FormParams;
15
+ getFormDataFromState(request: FormContextRequest | undefined, state: FormSubmissionState): {
16
+ action?: FormAction;
17
+ confirm?: true;
18
+ crumb?: string;
19
+ itemId?: string;
20
+ };
21
+ getStateFromValidForm(request: FormContextRequest, state: FormSubmissionState, payload: FormPayload): {
22
+ [x: string]: RepeatItemState[];
23
+ };
24
+ proceed(request: FormContextRequest, h: Pick<ResponseToolkit, 'redirect' | 'view'>): import("@hapi/hapi").ResponseObject;
25
+ getItemFromList(list: RepeatListState, itemId?: string): RepeatItemState | undefined;
26
+ getListFromState(state: FormSubmissionState): RepeatListState;
27
+ makeGetRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
28
+ makeGetListSummaryRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => import("@hapi/hapi").ResponseObject;
29
+ makePostListSummaryRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => import("@hapi/hapi").ResponseObject;
30
+ makeGetItemDeleteRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => import("@hapi/hapi").ResponseObject;
31
+ makePostItemDeleteRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
32
+ getViewModel(request: FormContextRequest, context: FormContext): FormPageViewModel;
33
+ getListSummaryViewModel(request: FormContextRequest, context: FormContext, list: RepeatListState): RepeaterSummaryPageViewModel;
34
+ getSummaryPath(request?: FormContextRequest): string;
35
+ }
@@ -0,0 +1,50 @@
1
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
2
+ import { type FormContext } from '~/src/server/plugins/engine/types.js';
3
+ import { type FormRequest } from '~/src/server/routes/types.js';
4
+ export declare class StartPageController extends QuestionPageController {
5
+ /**
6
+ * The controller which is used when Page["controller"] is defined as "./pages/start.js"
7
+ * This page should not be used in production. This page is helpful for prototyping start pages within the app,
8
+ * but start pages should really live on gov.uk (whitehall publisher) so a user can be properly signposted.
9
+ */
10
+ getViewModel(request: FormRequest, context: FormContext): {
11
+ isStartPage: boolean;
12
+ components: import("../components/types.js").ComponentViewModel[];
13
+ context: FormContext;
14
+ errors?: import("~/src/server/plugins/engine/types.js").FormSubmissionError[];
15
+ hasMissingNotificationEmail?: boolean;
16
+ page: import("./PageController.js").PageController;
17
+ name?: string;
18
+ pageTitle: string;
19
+ sectionTitle?: string;
20
+ showTitle: boolean;
21
+ backLink?: import("../components/types.js").BackLink;
22
+ feedbackLink?: string;
23
+ serviceUrl: string;
24
+ phaseTag?: string;
25
+ /**
26
+ * - Base layout path
27
+ */
28
+ baseLayoutPath?: string | undefined;
29
+ /**
30
+ * - Cross-Site Request Forgery (CSRF) token
31
+ */
32
+ crumb?: string | undefined;
33
+ /**
34
+ * - Content Security Policy (CSP) nonce
35
+ */
36
+ cspNonce?: string | undefined;
37
+ /**
38
+ * - Current path
39
+ */
40
+ currentPath?: string | undefined;
41
+ /**
42
+ * - Preview mode
43
+ */
44
+ previewMode?: string | undefined;
45
+ /**
46
+ * - Form slug
47
+ */
48
+ slug?: string | undefined;
49
+ };
50
+ }
@@ -0,0 +1,12 @@
1
+ import { type PageStatus } from '@defra/forms-model';
2
+ import { type ResponseToolkit } from '@hapi/hapi';
3
+ import { type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
5
+ import { type FormContext } from '~/src/server/plugins/engine/types.js';
6
+ import { type FormRequest } from '~/src/server/routes/types.js';
7
+ export declare class StatusPageController extends QuestionPageController {
8
+ pageDef: PageStatus;
9
+ constructor(model: FormModel, pageDef: PageStatus);
10
+ getRelevantPath(): string;
11
+ makeGetRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
12
+ }
@@ -0,0 +1,26 @@
1
+ import { type Page } from '@defra/forms-model';
2
+ import { type ResponseToolkit, type RouteOptions } from '@hapi/hapi';
3
+ import { SummaryViewModel, type FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type Detail, type DetailItem } from '~/src/server/plugins/engine/models/types.js';
5
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
6
+ import { type FormContext, type FormContextRequest } from '~/src/server/plugins/engine/types.js';
7
+ import { type FormRequest, type FormRequestPayload, type FormRequestPayloadRefs } from '~/src/server/routes/types.js';
8
+ export declare class SummaryPageController extends QuestionPageController {
9
+ pageDef: Page;
10
+ /**
11
+ * The controller which is used when Page["controller"] is defined as "./pages/summary.js"
12
+ */
13
+ constructor(model: FormModel, pageDef: Page);
14
+ getSummaryViewModel(request: FormContextRequest, context: FormContext): SummaryViewModel;
15
+ /**
16
+ * Returns an async function. This is called in plugin.ts when there is a GET request at `/{id}/{path*}`,
17
+ */
18
+ makeGetRouteHandler(): (request: FormRequest, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
19
+ /**
20
+ * Returns an async function. This is called in plugin.ts when there is a POST request at `/{id}/{path*}`.
21
+ * If a form is incomplete, a user will be redirected to the start page.
22
+ */
23
+ makePostRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, "redirect" | "view">) => Promise<import("@hapi/hapi").ResponseObject>;
24
+ get postRouteOptions(): RouteOptions<FormRequestPayloadRefs>;
25
+ }
26
+ export declare function getFormSubmissionData(context: FormContext, details: Detail[]): DetailItem[];
@@ -0,0 +1,9 @@
1
+ import { type PageTerminal } from '@defra/forms-model';
2
+ import { type ResponseObject, type ResponseToolkit } from '@hapi/hapi';
3
+ import { QuestionPageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
4
+ import { type FormContext } from '~/src/server/plugins/engine/types.js';
5
+ import { type FormRequestPayload } from '~/src/server/routes/types.js';
6
+ export declare class TerminalPageController extends QuestionPageController {
7
+ pageDef: PageTerminal;
8
+ makePostRouteHandler(): (request: FormRequestPayload, context: FormContext, h: Pick<ResponseToolkit, 'redirect' | 'view'>) => Promise<ResponseObject>;
9
+ }
@@ -0,0 +1,19 @@
1
+ import { ControllerType, type Page } from '@defra/forms-model';
2
+ import { type FormModel } from '~/src/server/plugins/engine/models/FormModel.js';
3
+ import * as PageControllers from '~/src/server/plugins/engine/pageControllers/index.js';
4
+ export declare function isPageController(controllerName?: string | ControllerType): controllerName is keyof typeof PageControllers;
5
+ export type PageControllerClass = InstanceType<PageControllerType>;
6
+ export type PageControllerType = (typeof PageControllers)[keyof typeof PageControllers];
7
+ /**
8
+ * Creates page instance for each {@link Page} type
9
+ */
10
+ export declare function createPage(model: FormModel, pageDef: Page): PageControllerClass;
11
+ /**
12
+ * In local development environments, we sometimes need to rewrite the
13
+ * CDP upload URL to work with CSP/CORS restrictions.
14
+ * This helper function rewrites localhost URLs to use the sslip.io proxy
15
+ * This is only used when running locally with a development proxy.
16
+ * In non-local environments, this function returns null
17
+ * @param uploadUrl - The original upload URL from CDP
18
+ */
19
+ export declare function getProxyUrlForLocalDevelopment(uploadUrl?: string): string | null;
@@ -0,0 +1,8 @@
1
+ export { StartPageController } from '~/src/server/plugins/engine/pageControllers/StartPageController.js';
2
+ export { QuestionPageController, // Export alongside alias
3
+ QuestionPageController as PageController } from '~/src/server/plugins/engine/pageControllers/QuestionPageController.js';
4
+ export { TerminalPageController } from '~/src/server/plugins/engine/pageControllers/TerminalPageController.js';
5
+ export { SummaryPageController } from '~/src/server/plugins/engine/pageControllers/SummaryPageController.js';
6
+ export { StatusPageController } from '~/src/server/plugins/engine/pageControllers/StatusPageController.js';
7
+ export { FileUploadPageController } from '~/src/server/plugins/engine/pageControllers/FileUploadPageController.js';
8
+ export { RepeatPageController } from '~/src/server/plugins/engine/pageControllers/RepeatPageController.js';
@@ -0,0 +1,8 @@
1
+ import { type JoiExpression, type LanguageMessages, type LanguageMessagesExt, type ValidationOptions } from 'joi';
2
+ /**
3
+ * see @link https://joi.dev/api/?v=17.4.2#template-syntax for template syntax
4
+ */
5
+ export declare const messageTemplate: Record<string, JoiExpression>;
6
+ export declare const messages: LanguageMessagesExt;
7
+ export declare const messagesPre: LanguageMessages;
8
+ export declare const validationOptions: ValidationOptions;
@@ -0,0 +1,33 @@
1
+ import { type PluginProperties, type Server } from '@hapi/hapi';
2
+ import { type Environment } from 'nunjucks';
3
+ import { FormModel } from '~/src/server/plugins/engine/models/index.js';
4
+ import { type PageController } from '~/src/server/plugins/engine/pageControllers/PageController.js';
5
+ import { type FilterFunction } from '~/src/server/plugins/engine/types.js';
6
+ import { type Services } from '~/src/server/types.js';
7
+ export declare function findPackageRoot(): string;
8
+ export interface PluginOptions {
9
+ model?: FormModel;
10
+ services?: Services;
11
+ controllers?: Record<string, typeof PageController>;
12
+ cacheName?: string;
13
+ filters?: Record<string, FilterFunction>;
14
+ pluginPath?: string;
15
+ nunjucks: {
16
+ baseLayoutPath: string;
17
+ paths: string[];
18
+ };
19
+ viewContext: PluginProperties['forms-engine-plugin']['viewContext'];
20
+ }
21
+ export declare const plugin: {
22
+ name: string;
23
+ dependencies: string[];
24
+ multiple: true;
25
+ register(server: Server, options: PluginOptions): Promise<void>;
26
+ };
27
+ interface CompileOptions {
28
+ environment: Environment;
29
+ }
30
+ export interface EngineConfigurationObject {
31
+ compileOptions: CompileOptions;
32
+ }
33
+ export {};
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Generates a reference number in the format of `XXX-XXX-XXX`, or `PREFIX-XXX-XXX` if a prefix is provided.
3
+ * Provides no guarantee on uniqueness.
4
+ */
5
+ export declare function generateUniqueReference(prefix?: string): string;
@@ -0,0 +1,24 @@
1
+ /**
2
+ * Persist files by extending the time-to-live to 30 days
3
+ * @param {{fileId: string, initiatedRetrievalKey: string}[]} files - batch of files to persist
4
+ * @param {string} persistedRetrievalKey - final retrieval key when submitting
5
+ */
6
+ export function persistFiles(files: {
7
+ fileId: string;
8
+ initiatedRetrievalKey: string;
9
+ }[], persistedRetrievalKey: string): Promise<{
10
+ res: import("http").IncomingMessage;
11
+ error: object | Error;
12
+ payload?: undefined;
13
+ } | {
14
+ res: import("http").IncomingMessage;
15
+ payload: object;
16
+ error?: undefined;
17
+ }>;
18
+ /**
19
+ * Submit form
20
+ * @param {SubmitPayload} data - submission data
21
+ */
22
+ export function submit(data: SubmitPayload): Promise<SubmitResponsePayload | undefined>;
23
+ import type { SubmitPayload } from '@defra/forms-model';
24
+ import type { SubmitResponsePayload } from '@defra/forms-model';