@ukhomeoffice/cop-react-form-renderer 0.1.0-gamma → 1.0.0-alpha
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.
- package/dist/components/CheckYourAnswers/Answer.test.js +94 -0
- package/dist/components/CheckYourAnswers/CheckYourAnswers.js +79 -27
- package/dist/components/CheckYourAnswers/CheckYourAnswers.scss +0 -7
- package/dist/components/CheckYourAnswers/CheckYourAnswers.stories.mdx +78 -1
- package/dist/components/CheckYourAnswers/CheckYourAnswers.test.js +332 -0
- package/dist/components/FormPage/FormPage.test.js +3 -1
- package/dist/components/FormRenderer/FormRenderer.js +75 -54
- package/dist/components/FormRenderer/FormRenderer.stories.mdx +35 -7
- package/dist/components/FormRenderer/FormRenderer.test.js +471 -0
- package/dist/components/FormRenderer/handlers/cyaAction.js +28 -0
- package/dist/components/FormRenderer/handlers/getPageId.js +28 -0
- package/dist/components/FormRenderer/handlers/getPageId.test.js +61 -0
- package/dist/components/FormRenderer/handlers/handlers.test.js +97 -0
- package/dist/components/FormRenderer/handlers/index.js +23 -0
- package/dist/components/FormRenderer/handlers/navigate.js +28 -0
- package/dist/components/FormRenderer/handlers/submissionError.js +20 -0
- package/dist/components/FormRenderer/helpers/canCYASubmit.js +42 -0
- package/dist/components/FormRenderer/helpers/canCYASubmit.test.js +155 -0
- package/dist/components/FormRenderer/helpers/getCYA.js +2 -2
- package/dist/components/FormRenderer/helpers/getCYA.test.js +5 -5
- package/dist/components/FormRenderer/helpers/getFormState.test.js +7 -7
- package/dist/components/FormRenderer/helpers/getNextPageId.js +65 -0
- package/dist/components/FormRenderer/helpers/getNextPageId.test.js +90 -0
- package/dist/components/FormRenderer/helpers/getPage.js +1 -1
- package/dist/components/FormRenderer/helpers/getPage.test.js +3 -3
- package/dist/components/FormRenderer/helpers/index.js +17 -13
- package/dist/components/PageActions/ActionButton.js +5 -9
- package/dist/components/PageActions/ActionButton.test.js +3 -1
- package/dist/components/PageActions/PageActions.test.js +4 -2
- package/dist/components/SummaryList/RowAction.js +1 -1
- package/dist/components/SummaryList/RowAction.test.js +8 -18
- package/dist/components/SummaryList/SummaryList.js +4 -4
- package/dist/components/SummaryList/SummaryList.scss +7 -0
- package/dist/components/SummaryList/SummaryList.stories.mdx +36 -0
- package/dist/components/SummaryList/SummaryList.test.js +197 -0
- package/dist/hooks/useHooks.js +12 -15
- package/dist/index.js +3 -1
- package/dist/index.test.js +18 -0
- package/dist/models/EventTypes.js +14 -0
- package/dist/models/FormPages.js +14 -0
- package/dist/models/PageAction.js +40 -0
- package/dist/models/index.js +24 -0
- package/dist/utils/CheckYourAnswers/getCYAAction.js +9 -0
- package/dist/utils/CheckYourAnswers/getCYARow.js +10 -0
- package/dist/utils/CheckYourAnswers/getCYARowsForPage.js +9 -0
- package/dist/utils/CheckYourAnswers/showComponentCYA.js +6 -5
- package/dist/utils/Component/getComponent.test.js +1 -1
- package/dist/utils/Format/formatData.js +32 -0
- package/dist/utils/Format/formatData.test.js +46 -0
- package/dist/utils/Format/formatDataForComponent.js +41 -0
- package/dist/utils/Format/formatDataForComponent.test.js +161 -0
- package/dist/utils/Format/formatDataForForm.js +33 -0
- package/dist/utils/Format/formatDataForForm.test.js +78 -0
- package/dist/utils/Format/formatDataForPage.js +37 -0
- package/dist/utils/Format/formatDataForPage.test.js +96 -0
- package/dist/utils/Format/index.js +26 -0
- package/dist/utils/Hub/getFormHub.js +14 -0
- package/dist/utils/Validate/validatePage.test.js +1 -1
- package/dist/utils/index.js +3 -0
- package/package.json +6 -3
- package/dist/components/FormRenderer/helpers.js +0 -66
- package/dist/components/FormRenderer/helpers.test.js +0 -158
|
@@ -6,6 +6,8 @@ var _react = require("@testing-library/react");
|
|
|
6
6
|
|
|
7
7
|
var _react2 = _interopRequireDefault(require("react"));
|
|
8
8
|
|
|
9
|
+
var _models = require("../../models");
|
|
10
|
+
|
|
9
11
|
var _ActionButton = require("../PageActions/ActionButton");
|
|
10
12
|
|
|
11
13
|
var _FormPage = _interopRequireWildcard(require("./FormPage"));
|
|
@@ -171,7 +173,7 @@ describe('components', function () {
|
|
|
171
173
|
|
|
172
174
|
expect(ON_ACTION_CALLS.length).toEqual(1);
|
|
173
175
|
expect(PAGE.formData.text).toEqual(NEW_VALUE);
|
|
174
|
-
expect(ON_ACTION_CALLS[0].action).toEqual(
|
|
176
|
+
expect(ON_ACTION_CALLS[0].action).toEqual(_models.PageAction.DEFAULTS.submit);
|
|
175
177
|
expect(ON_ACTION_CALLS[0].patch).toEqual({
|
|
176
178
|
text: NEW_VALUE
|
|
177
179
|
});
|
|
@@ -5,7 +5,7 @@ function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "functi
|
|
|
5
5
|
Object.defineProperty(exports, "__esModule", {
|
|
6
6
|
value: true
|
|
7
7
|
});
|
|
8
|
-
exports.default = void 0;
|
|
8
|
+
exports.default = exports.DEFAULT_CLASS = void 0;
|
|
9
9
|
|
|
10
10
|
var _copReactComponents = require("@ukhomeoffice/cop-react-components");
|
|
11
11
|
|
|
@@ -23,7 +23,9 @@ var _CheckYourAnswers = _interopRequireDefault(require("../CheckYourAnswers"));
|
|
|
23
23
|
|
|
24
24
|
var _FormPage = _interopRequireDefault(require("../FormPage"));
|
|
25
25
|
|
|
26
|
-
var
|
|
26
|
+
var _handlers = _interopRequireDefault(require("./handlers"));
|
|
27
|
+
|
|
28
|
+
var _helpers = _interopRequireDefault(require("./helpers"));
|
|
27
29
|
|
|
28
30
|
require("./FormRenderer.scss");
|
|
29
31
|
|
|
@@ -54,6 +56,7 @@ function _iterableToArrayLimit(arr, i) { var _i = arr == null ? null : typeof Sy
|
|
|
54
56
|
function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
|
|
55
57
|
|
|
56
58
|
var DEFAULT_CLASS = 'hods-form';
|
|
59
|
+
exports.DEFAULT_CLASS = DEFAULT_CLASS;
|
|
57
60
|
|
|
58
61
|
var FormRenderer = function FormRenderer(_ref) {
|
|
59
62
|
var title = _ref.title,
|
|
@@ -61,7 +64,7 @@ var FormRenderer = function FormRenderer(_ref) {
|
|
|
61
64
|
components = _ref.components,
|
|
62
65
|
_pages = _ref.pages,
|
|
63
66
|
_hub = _ref.hub,
|
|
64
|
-
|
|
67
|
+
cya = _ref.cya,
|
|
65
68
|
_data = _ref.data,
|
|
66
69
|
_hooks = _ref.hooks,
|
|
67
70
|
classBlock = _ref.classBlock,
|
|
@@ -74,30 +77,25 @@ var FormRenderer = function FormRenderer(_ref) {
|
|
|
74
77
|
data = _useState2[0],
|
|
75
78
|
setData = _useState2[1];
|
|
76
79
|
|
|
77
|
-
var _useState3 = (0, _react.useState)(
|
|
80
|
+
var _useState3 = (0, _react.useState)([]),
|
|
78
81
|
_useState4 = _slicedToArray(_useState3, 2),
|
|
79
|
-
|
|
80
|
-
|
|
82
|
+
pages = _useState4[0],
|
|
83
|
+
setPages = _useState4[1];
|
|
81
84
|
|
|
82
|
-
var _useState5 = (0, _react.useState)(
|
|
85
|
+
var _useState5 = (0, _react.useState)(undefined),
|
|
83
86
|
_useState6 = _slicedToArray(_useState5, 2),
|
|
84
|
-
|
|
85
|
-
|
|
87
|
+
hub = _useState6[0],
|
|
88
|
+
setHub = _useState6[1];
|
|
86
89
|
|
|
87
|
-
var _useState7 = (0, _react.useState)(
|
|
90
|
+
var _useState7 = (0, _react.useState)(_helpers.default.getNextPageId(type, _pages)),
|
|
88
91
|
_useState8 = _slicedToArray(_useState7, 2),
|
|
89
|
-
|
|
90
|
-
|
|
92
|
+
pageId = _useState8[0],
|
|
93
|
+
setPageId = _useState8[1];
|
|
91
94
|
|
|
92
|
-
var _useState9 = (0, _react.useState)(
|
|
95
|
+
var _useState9 = (0, _react.useState)(_helpers.default.getFormState(pageId, pages, hub)),
|
|
93
96
|
_useState10 = _slicedToArray(_useState9, 2),
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
var _useState11 = (0, _react.useState)((0, _helpers.getFormState)(pageId, pages, hub)),
|
|
98
|
-
_useState12 = _slicedToArray(_useState11, 2),
|
|
99
|
-
formState = _useState12[0],
|
|
100
|
-
setFormState = _useState12[1]; // Set up hooks.
|
|
97
|
+
formState = _useState10[0],
|
|
98
|
+
setFormState = _useState10[1]; // Set up hooks.
|
|
101
99
|
|
|
102
100
|
|
|
103
101
|
var _useHooks = (0, _hooks2.useHooks)(),
|
|
@@ -118,75 +116,95 @@ var FormRenderer = function FormRenderer(_ref) {
|
|
|
118
116
|
|
|
119
117
|
(0, _react.useEffect)(function () {
|
|
120
118
|
setPages(_utils.default.FormPage.getAll(_pages, components, _objectSpread({}, data)));
|
|
121
|
-
}, [components, _pages, data,
|
|
119
|
+
}, [components, _pages, data, setPages]); // Setup hub.
|
|
122
120
|
|
|
123
121
|
(0, _react.useEffect)(function () {
|
|
124
122
|
setHub(_utils.default.Hub.get(type, _hub, components, _objectSpread({}, data)));
|
|
125
123
|
}, [type, _hub, data, components, setHub]); // Form state.
|
|
126
124
|
|
|
127
125
|
(0, _react.useEffect)(function () {
|
|
128
|
-
setFormState(
|
|
126
|
+
setFormState(_helpers.default.getFormState(pageId, pages, hub));
|
|
129
127
|
}, [pages, hub, pageId, setFormState]); // Call the onFormLoad hook just when this component first renders.
|
|
130
128
|
|
|
131
129
|
(0, _react.useEffect)(function () {
|
|
132
130
|
hooks.onFormLoad();
|
|
133
|
-
}, [hooks]);
|
|
131
|
+
}, [hooks]);
|
|
132
|
+
|
|
133
|
+
var onPageChange = function onPageChange(newPageId) {
|
|
134
|
+
setPageId(newPageId);
|
|
135
|
+
hooks.onPageChange(newPageId);
|
|
136
|
+
}; // Handle actions from pages.
|
|
134
137
|
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
+
|
|
139
|
+
var onPageAction = function onPageAction(action, patch, onError) {
|
|
140
|
+
// Check to see whether the action is able to proceed, which in
|
|
141
|
+
// in the case of a submission will validate the fields in the page.
|
|
142
|
+
if (_helpers.default.canActionProceed(action, formState.page, onError)) {
|
|
138
143
|
if (action.type === 'navigate') {
|
|
139
|
-
|
|
140
|
-
setPageId(newPageId);
|
|
141
|
-
hooks.onPageChange(newPageId);
|
|
142
|
-
} else if (action.type === 'cancel') {
|
|
143
|
-
setRedoPages(Date.now);
|
|
144
|
-
setPageId('hub');
|
|
145
|
-
hooks.onPageChange('hub');
|
|
144
|
+
_handlers.default.navigate(action, pageId, onPageChange);
|
|
146
145
|
} else {
|
|
147
146
|
// Submit.
|
|
147
|
+
var submissionData = _utils.default.Format.form({
|
|
148
|
+
pages: pages,
|
|
149
|
+
components: components
|
|
150
|
+
}, _objectSpread(_objectSpread({}, data), patch), _models.EventTypes.SUBMIT);
|
|
151
|
+
|
|
148
152
|
if (patch) {
|
|
149
|
-
setData(
|
|
150
|
-
return _objectSpread(_objectSpread({}, prev), patch);
|
|
151
|
-
});
|
|
153
|
+
setData(submissionData);
|
|
152
154
|
} // Now submit the data to the backend...
|
|
153
155
|
|
|
154
156
|
|
|
155
|
-
hooks.onSubmit(action.type,
|
|
156
|
-
|
|
157
|
-
|
|
157
|
+
hooks.onSubmit(action.type, submissionData, function () {
|
|
158
|
+
var nextPageId = _helpers.default.getNextPageId(type, pages, pageId, action);
|
|
159
|
+
|
|
160
|
+
onPageChange(nextPageId);
|
|
158
161
|
}, function (errors) {
|
|
159
|
-
|
|
160
|
-
console.error('Submission errors', errors);
|
|
162
|
+
_handlers.default.submissionError(errors, onError);
|
|
161
163
|
});
|
|
162
164
|
}
|
|
163
165
|
}
|
|
164
166
|
}; // Handle navigation from "Check your answers".
|
|
165
167
|
|
|
166
168
|
|
|
167
|
-
var
|
|
168
|
-
|
|
169
|
-
|
|
169
|
+
var onCYARowAction = function onCYARowAction(page) {
|
|
170
|
+
_handlers.default.cyaAction(page, pageId, onPageChange);
|
|
171
|
+
}; // Handle actions from "Check your answers".
|
|
170
172
|
|
|
171
|
-
if (action && action.href) {
|
|
172
|
-
newPageId = action.href.replace('/', '');
|
|
173
|
-
}
|
|
174
173
|
|
|
175
|
-
|
|
176
|
-
|
|
174
|
+
var onCYAAction = function onCYAAction(action, onError) {
|
|
175
|
+
// Check to see whether the action is able to proceed, which in
|
|
176
|
+
// in the case of a submission will validate the fields in the page.
|
|
177
|
+
if (action.type === _models.PageAction.TYPES.SUBMIT) {
|
|
178
|
+
if (_helpers.default.canCYASubmit(pages, onError)) {
|
|
179
|
+
// Submit.
|
|
180
|
+
var submissionData = _utils.default.Format.form({
|
|
181
|
+
pages: pages,
|
|
182
|
+
components: components
|
|
183
|
+
}, _objectSpread({}, data), _models.EventTypes.SUBMIT);
|
|
184
|
+
|
|
185
|
+
setData(submissionData); // Now submit the data to the backend...
|
|
186
|
+
|
|
187
|
+
hooks.onSubmit(action.type, submissionData, function () {
|
|
188
|
+
hooks.onFormComplete();
|
|
189
|
+
}, function (errors) {
|
|
190
|
+
_handlers.default.submissionError(errors, onError);
|
|
191
|
+
});
|
|
192
|
+
}
|
|
193
|
+
}
|
|
177
194
|
};
|
|
178
195
|
|
|
179
196
|
var classes = _utils.default.classBuilder(classBlock, classModifiers, className);
|
|
180
197
|
|
|
181
198
|
return /*#__PURE__*/_react.default.createElement("div", {
|
|
182
199
|
className: classes()
|
|
183
|
-
}, title && pageId ===
|
|
200
|
+
}, title && pageId === _models.FormPages.HUB && /*#__PURE__*/_react.default.createElement(_copReactComponents.LargeHeading, null, title), formState.cya && /*#__PURE__*/_react.default.createElement(_CheckYourAnswers.default, _extends({
|
|
184
201
|
pages: pages
|
|
185
|
-
},
|
|
186
|
-
onAction:
|
|
202
|
+
}, cya, formState.cya, {
|
|
203
|
+
onAction: onCYAAction,
|
|
204
|
+
onRowAction: onCYARowAction
|
|
187
205
|
})), formState.page && /*#__PURE__*/_react.default.createElement(_FormPage.default, {
|
|
188
206
|
page: formState.page,
|
|
189
|
-
onAction:
|
|
207
|
+
onAction: onPageAction
|
|
190
208
|
}));
|
|
191
209
|
};
|
|
192
210
|
|
|
@@ -201,7 +219,10 @@ FormRenderer.propTypes = {
|
|
|
201
219
|
cya: _propTypes.default.object,
|
|
202
220
|
data: _propTypes.default.object,
|
|
203
221
|
hooks: _propTypes.default.shape({
|
|
204
|
-
|
|
222
|
+
onFormLoad: _propTypes.default.func,
|
|
223
|
+
onPageChange: _propTypes.default.func,
|
|
224
|
+
onRequest: _propTypes.default.func,
|
|
225
|
+
onSubmit: _propTypes.default.func
|
|
205
226
|
}),
|
|
206
227
|
classBlock: _propTypes.default.string,
|
|
207
228
|
classModifiers: _propTypes.default.oneOfType([_propTypes.default.string, _propTypes.default.arrayOf(_propTypes.default.string)]),
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
<!-- Global imports -->
|
|
2
2
|
import { ArgsTable, Canvas, Meta, Story } from '@storybook/addon-docs';
|
|
3
|
-
import { Details, Heading, Link } from '@ukhomeoffice/cop-react-components';
|
|
3
|
+
import { Button, Details, Heading, Link, Panel } from '@ukhomeoffice/cop-react-components';
|
|
4
|
+
import { useState } from 'react';
|
|
4
5
|
import withMock from 'storybook-addon-mock';
|
|
5
6
|
|
|
6
7
|
<!-- Local imports -->
|
|
@@ -9,11 +10,11 @@ import FormRenderer from './FormRenderer';
|
|
|
9
10
|
|
|
10
11
|
<!-- JSON documents -->
|
|
11
12
|
import CIVIL_SERVANT from '../../json/areYouACivilServant.json';
|
|
13
|
+
import FIRST_FORM from '../../json/firstForm.json';
|
|
12
14
|
import GRADE from '../../json/grade.json';
|
|
13
15
|
import TEAMS from '../../json/team.json';
|
|
14
16
|
import USER_PROFILE_DATA from '../../json/userProfile.data.json';
|
|
15
17
|
import USER_PROFILE from '../../json/userProfile.json';
|
|
16
|
-
import SAVE_AND_CONTINUE from '../../json/saveAndContinue.json';
|
|
17
18
|
|
|
18
19
|
<Meta title="Components/Form renderer" id="D-FormRenderer" component={ FormRenderer } decorators={[withMock]} />
|
|
19
20
|
|
|
@@ -57,11 +58,13 @@ on the basis of a <Link href="/?path=/docs/f-json-form">JSON</Link> that describ
|
|
|
57
58
|
<ArgsTable of={ FormRenderer } />
|
|
58
59
|
</Details>
|
|
59
60
|
|
|
60
|
-
##
|
|
61
|
+
## CYA type
|
|
61
62
|
|
|
62
63
|
<Canvas>
|
|
63
|
-
<Story name="
|
|
64
|
+
<Story name="CYA">
|
|
64
65
|
{() => {
|
|
66
|
+
const [complete, setComplete] = useState(false);
|
|
67
|
+
const [returnLater, setReturnLater] = useState(false);
|
|
65
68
|
addHook('onRequest', (req) => {
|
|
66
69
|
// Do whatever you need to do to the request in here, such as adding an Authorization header.
|
|
67
70
|
console.log('onRequest hook called');
|
|
@@ -70,17 +73,42 @@ on the basis of a <Link href="/?path=/docs/f-json-form">JSON</Link> that describ
|
|
|
70
73
|
addHook('onFormLoad', () => {
|
|
71
74
|
console.log('onFormLoad called');
|
|
72
75
|
});
|
|
76
|
+
addHook('onFormComplete', () => {
|
|
77
|
+
console.log('onFormComplete called');
|
|
78
|
+
setComplete(true);
|
|
79
|
+
});
|
|
73
80
|
addHook('onPageChange', (pageId) => {
|
|
74
81
|
console.log('onPageChange called', pageId);
|
|
82
|
+
setReturnLater(!!pageId === false);
|
|
75
83
|
});
|
|
76
|
-
// In whatever consumes this, do it as:
|
|
77
|
-
// intercepts.add('onSubmit', (...) => { ... })
|
|
78
84
|
addHook('onSubmit', (type, payload, onSuccess, onError) => {
|
|
79
85
|
console.log('onSubmit called of type', type, 'called, with the payload', payload);
|
|
80
86
|
onSuccess();
|
|
81
87
|
});
|
|
88
|
+
const reset = () => {
|
|
89
|
+
setComplete(false);
|
|
90
|
+
setReturnLater(false);
|
|
91
|
+
};
|
|
82
92
|
return (
|
|
83
|
-
|
|
93
|
+
<>
|
|
94
|
+
{!complete && !returnLater && <FormRenderer {...FIRST_FORM} data={{}} />}
|
|
95
|
+
{complete &&
|
|
96
|
+
<div>
|
|
97
|
+
<Panel title="Submission successful">
|
|
98
|
+
Your submission was successful.
|
|
99
|
+
</Panel>
|
|
100
|
+
<Button onClick={() => reset()}>Start again</Button>
|
|
101
|
+
</div>
|
|
102
|
+
}
|
|
103
|
+
{!complete && returnLater &&
|
|
104
|
+
<div>
|
|
105
|
+
<Panel title="Saved to return later">
|
|
106
|
+
You clicked on "Save and return later".
|
|
107
|
+
</Panel>
|
|
108
|
+
<Button onClick={() => reset()}>Start again</Button>
|
|
109
|
+
</div>
|
|
110
|
+
}
|
|
111
|
+
</>
|
|
84
112
|
);
|
|
85
113
|
}}
|
|
86
114
|
</Story>
|