@ukhomeoffice/cop-react-form-renderer 6.0.0 → 6.0.2-peter
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/CheckYourAnswers.scss +2 -2
- package/dist/components/CollectionSummary/BannerStrip.js +3 -1
- package/dist/components/CollectionSummary/BannerStrip.scss +7 -3
- package/dist/components/CollectionSummary/CollectionSummary.js +34 -7
- package/dist/components/CollectionSummary/CollectionSummary.scss +1 -1
- package/dist/components/CollectionSummary/CollectionSummary.test.js +82 -4
- package/dist/components/CollectionSummary/Confirmation.scss +1 -1
- package/dist/components/CollectionSummary/RenderListView.js +9 -5
- package/dist/components/CollectionSummary/RenderListView.scss +1 -1
- package/dist/components/CollectionSummary/RenderListView.test.js +24 -3
- package/dist/components/CollectionSummary/SummaryCard.js +18 -45
- package/dist/components/CollectionSummary/SummaryCard.scss +4 -147
- package/dist/components/CollectionSummary/SummaryCard.test.js +53 -191
- package/dist/components/CollectionSummary/SummaryCardDetails.js +117 -0
- package/dist/components/CollectionSummary/SummaryCardDetails.scss +158 -0
- package/dist/components/CollectionSummary/SummaryCardDetails.test.js +319 -0
- package/dist/components/FormPage/FormPage.scss +1 -1
- package/dist/components/FormRenderer/FormRenderer.scss +1 -1
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/component-used-in-multiple-pages-data.json +4 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/component-used-in-multiple-pages-form.json +61 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-collection-data-removed.json +4 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-collections.json +8 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-components-removed.json +3 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-components.json +5 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-entire-collection-removed.json +3 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-nested-component-removed.json +10 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/data-with-nested-components.json +11 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/form-for-nested-components.json +96 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/form-with-collections-delete-entire.json +47 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/form-with-collections.json +46 -0
- package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/form-with-components.json +48 -0
- package/dist/components/FormRenderer/helpers/clearOutUncompletedRoutes.js +139 -0
- package/dist/components/FormRenderer/helpers/clearOutUncompletedRoutes.test.js +113 -0
- package/dist/components/FormRenderer/helpers/deleteNodeByPath.js +20 -0
- package/dist/components/FormRenderer/helpers/deleteNodeByPath.test.js +56 -0
- package/dist/components/FormRenderer/helpers/index.js +3 -1
- package/dist/components/FormRenderer/onPageAction.js +8 -2
- package/dist/components/FormRenderer/onPageAction.test.js +5 -0
- package/dist/components/SummaryList/SummaryList.scss +2 -2
- package/dist/components/TaskList/TaskList.scss +1 -1
- package/dist/utils/CollectionPage/mergeCollectionPages.js +15 -5
- package/dist/utils/CollectionPage/mergeCollectionPages.test.js +48 -1
- package/dist/utils/CollectionPage/setCollectionPageData.js +2 -2
- package/dist/utils/CollectionPage/setCollectionPageData.test.js +31 -0
- package/dist/utils/FormPage/getConditionalText.js +54 -0
- package/dist/utils/FormPage/getConditionalText.test.js +162 -0
- package/dist/utils/FormPage/index.js +5 -2
- package/package.json +4 -4
- package/dist/utils/FormPage/getPageTitle.js +0 -32
- package/dist/utils/FormPage/getPageTitle.test.js +0 -138
package/dist/components/FormRenderer/clear-uncompleted-routes/test-data/form-with-components.json
ADDED
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "form-with-components",
|
|
3
|
+
"components": [
|
|
4
|
+
{
|
|
5
|
+
"id": "componentA",
|
|
6
|
+
"fieldId": "componentA"
|
|
7
|
+
},
|
|
8
|
+
{
|
|
9
|
+
"id": "componentB",
|
|
10
|
+
"fieldId": "componentB",
|
|
11
|
+
"show_when": [
|
|
12
|
+
{
|
|
13
|
+
"op": "=",
|
|
14
|
+
"field": "componentA",
|
|
15
|
+
"value": "show"
|
|
16
|
+
}
|
|
17
|
+
]
|
|
18
|
+
},
|
|
19
|
+
{
|
|
20
|
+
"id": "componentC",
|
|
21
|
+
"fieldId": "componentC",
|
|
22
|
+
"show_when": [
|
|
23
|
+
{
|
|
24
|
+
"op": "=",
|
|
25
|
+
"field": "componentA",
|
|
26
|
+
"value": "show"
|
|
27
|
+
}
|
|
28
|
+
]
|
|
29
|
+
}
|
|
30
|
+
],
|
|
31
|
+
"pages": [
|
|
32
|
+
{
|
|
33
|
+
"id": "pageA",
|
|
34
|
+
"name": "Page A",
|
|
35
|
+
"components": [
|
|
36
|
+
{
|
|
37
|
+
"use": "componentA"
|
|
38
|
+
},
|
|
39
|
+
{
|
|
40
|
+
"use": "componentB"
|
|
41
|
+
},
|
|
42
|
+
{
|
|
43
|
+
"use": "componentC"
|
|
44
|
+
}
|
|
45
|
+
]
|
|
46
|
+
}
|
|
47
|
+
]
|
|
48
|
+
}
|
|
@@ -0,0 +1,139 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.default = void 0;
|
|
7
|
+
var _showComponent = _interopRequireDefault(require("../../../utils/Component/showComponent"));
|
|
8
|
+
var _mergeCollectionPages = _interopRequireDefault(require("../../../utils/CollectionPage/mergeCollectionPages"));
|
|
9
|
+
var _deleteNodeByPath = _interopRequireDefault(require("./deleteNodeByPath"));
|
|
10
|
+
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
11
|
+
/* eslint-disable no-param-reassign */
|
|
12
|
+
|
|
13
|
+
var recurseCheckForHiddenComponents = function recurseCheckForHiddenComponents(component, formData, path, candidateComponentForDeletion) {
|
|
14
|
+
path = path ? "".concat(path, ".").concat(component.fieldId) : component.fieldId;
|
|
15
|
+
if (component) {
|
|
16
|
+
if (component.components) {
|
|
17
|
+
var _component$components;
|
|
18
|
+
(_component$components = component.components) === null || _component$components === void 0 || _component$components.forEach(function (c) {
|
|
19
|
+
recurseCheckForHiddenComponents(c, formData, path, candidateComponentForDeletion);
|
|
20
|
+
});
|
|
21
|
+
} else if (!(0, _showComponent.default)(component, formData)) {
|
|
22
|
+
candidateComponentForDeletion.set(path, component);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
var buildListOfComponentsUsedInVisiblePages = function buildListOfComponentsUsedInVisiblePages(page, form, formData, componentsUsedInVisiblePagesIds) {
|
|
27
|
+
var _page$components;
|
|
28
|
+
(_page$components = page.components) === null || _page$components === void 0 || _page$components.forEach(function (component) {
|
|
29
|
+
var _form$components$find;
|
|
30
|
+
var componentObj = (_form$components$find = form.components.find(function (c) {
|
|
31
|
+
return c.fieldId === component.use;
|
|
32
|
+
})) !== null && _form$components$find !== void 0 ? _form$components$find : component;
|
|
33
|
+
if (page && (0, _showComponent.default)(page, formData)) {
|
|
34
|
+
if (componentObj && (0, _showComponent.default)(componentObj, formData)) {
|
|
35
|
+
componentsUsedInVisiblePagesIds.push(componentObj.fieldId);
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
});
|
|
39
|
+
};
|
|
40
|
+
var recurseDeleteComponents = function recurseDeleteComponents(component, formData, path, checkIfComponentHidden) {
|
|
41
|
+
path = path ? "".concat(path, ".").concat(component.fieldId) : component.fieldId;
|
|
42
|
+
if (component) {
|
|
43
|
+
if (component.components) {
|
|
44
|
+
var _component$components2;
|
|
45
|
+
(_component$components2 = component.components) === null || _component$components2 === void 0 || _component$components2.forEach(function (c) {
|
|
46
|
+
recurseDeleteComponents(c, formData, path, checkIfComponentHidden);
|
|
47
|
+
});
|
|
48
|
+
} else if (checkIfComponentHidden) {
|
|
49
|
+
if (!(0, _showComponent.default)(component, formData)) {
|
|
50
|
+
delete formData[path];
|
|
51
|
+
}
|
|
52
|
+
} else {
|
|
53
|
+
delete formData[path];
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
var markComponentsForDeletion = function markComponentsForDeletion(page, form, formData, candidateComponentForDeletion, componentsUsedInVisiblePages) {
|
|
58
|
+
var _page$components2;
|
|
59
|
+
if (page.disableClearWhenHidden) {
|
|
60
|
+
return;
|
|
61
|
+
}
|
|
62
|
+
(_page$components2 = page.components) === null || _page$components2 === void 0 || _page$components2.forEach(function (component) {
|
|
63
|
+
var _form$components$find2;
|
|
64
|
+
var componentObj = (_form$components$find2 = form.components.find(function (c) {
|
|
65
|
+
return c.fieldId === component.use;
|
|
66
|
+
})) !== null && _form$components$find2 !== void 0 ? _form$components$find2 : component;
|
|
67
|
+
if (page && (0, _showComponent.default)(page, formData)) {
|
|
68
|
+
buildListOfComponentsUsedInVisiblePages(page, form, formData, componentsUsedInVisiblePages);
|
|
69
|
+
recurseCheckForHiddenComponents(componentObj, formData, null, candidateComponentForDeletion);
|
|
70
|
+
} else {
|
|
71
|
+
candidateComponentForDeletion.set(componentObj.fieldId, componentObj);
|
|
72
|
+
}
|
|
73
|
+
});
|
|
74
|
+
};
|
|
75
|
+
var deleteHiddenComponent = function deleteHiddenComponent(page, form, collectionData, formData) {
|
|
76
|
+
if (page.disableClearWhenHidden) {
|
|
77
|
+
return;
|
|
78
|
+
}
|
|
79
|
+
if (page && (0, _showComponent.default)(page, collectionData) || page && (0, _showComponent.default)(page, formData)) {
|
|
80
|
+
var _page$components3;
|
|
81
|
+
(_page$components3 = page.components) === null || _page$components3 === void 0 || _page$components3.forEach(function (component) {
|
|
82
|
+
var _form$components$find3;
|
|
83
|
+
var componentObj = (_form$components$find3 = form.components.find(function (c) {
|
|
84
|
+
return c.fieldId === component.use;
|
|
85
|
+
})) !== null && _form$components$find3 !== void 0 ? _form$components$find3 : component;
|
|
86
|
+
recurseDeleteComponents(componentObj, collectionData, null, true);
|
|
87
|
+
});
|
|
88
|
+
} else {
|
|
89
|
+
var _page$components4;
|
|
90
|
+
// recursively delete all components on the page
|
|
91
|
+
(_page$components4 = page.components) === null || _page$components4 === void 0 || _page$components4.forEach(function (component) {
|
|
92
|
+
var _form$components$find4;
|
|
93
|
+
var componentObj = (_form$components$find4 = form.components.find(function (c) {
|
|
94
|
+
return c.fieldId === component.use;
|
|
95
|
+
})) !== null && _form$components$find4 !== void 0 ? _form$components$find4 : component;
|
|
96
|
+
recurseDeleteComponents(componentObj, collectionData, null, false);
|
|
97
|
+
});
|
|
98
|
+
}
|
|
99
|
+
};
|
|
100
|
+
var clearOutUncompletedRoutes = function clearOutUncompletedRoutes(form, formData) {
|
|
101
|
+
if (form.disableClearWhenHidden) {
|
|
102
|
+
return formData;
|
|
103
|
+
}
|
|
104
|
+
var condensedPages = (0, _mergeCollectionPages.default)(form.pages);
|
|
105
|
+
var candidateComponentForDeletion = new Map();
|
|
106
|
+
var componentsUsedInVisiblePagesIds = [];
|
|
107
|
+
condensedPages === null || condensedPages === void 0 || condensedPages.forEach(function (page) {
|
|
108
|
+
var _page$collection;
|
|
109
|
+
if (page !== null && page !== void 0 && (_page$collection = page.collection) !== null && _page$collection !== void 0 && _page$collection.name) {
|
|
110
|
+
var _page$collection2;
|
|
111
|
+
var collectionDatas = formData[page === null || page === void 0 || (_page$collection2 = page.collection) === null || _page$collection2 === void 0 ? void 0 : _page$collection2.name];
|
|
112
|
+
if (collectionDatas) {
|
|
113
|
+
collectionDatas.forEach(function (collectionData) {
|
|
114
|
+
var _page$childPages;
|
|
115
|
+
/* eslint-disable consistent-return */
|
|
116
|
+
(_page$childPages = page.childPages) === null || _page$childPages === void 0 || _page$childPages.forEach(function (childPage) {
|
|
117
|
+
if (childPage.deleteCollectionWhenHidden) {
|
|
118
|
+
if (childPage && !(0, _showComponent.default)(childPage, collectionData) || childPage && !(0, _showComponent.default)(childPage, formData)) {
|
|
119
|
+
delete formData[childPage.collection.name];
|
|
120
|
+
return false;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
deleteHiddenComponent(childPage, form, collectionData, formData);
|
|
124
|
+
});
|
|
125
|
+
});
|
|
126
|
+
}
|
|
127
|
+
} else {
|
|
128
|
+
markComponentsForDeletion(page, form, formData, candidateComponentForDeletion, componentsUsedInVisiblePagesIds);
|
|
129
|
+
}
|
|
130
|
+
});
|
|
131
|
+
componentsUsedInVisiblePagesIds.forEach(function (componentId) {
|
|
132
|
+
return candidateComponentForDeletion.delete(componentId);
|
|
133
|
+
});
|
|
134
|
+
candidateComponentForDeletion.forEach(function (val, key) {
|
|
135
|
+
(0, _deleteNodeByPath.default)(formData, key);
|
|
136
|
+
});
|
|
137
|
+
return formData;
|
|
138
|
+
};
|
|
139
|
+
var _default = exports.default = clearOutUncompletedRoutes;
|
|
@@ -0,0 +1,113 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _index = _interopRequireDefault(require("./index"));
|
|
4
|
+
var _componentUsedInMultiplePagesForm = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/component-used-in-multiple-pages-form.json"));
|
|
5
|
+
var _componentUsedInMultiplePagesData = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/component-used-in-multiple-pages-data.json"));
|
|
6
|
+
var _formWithCollections = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/form-with-collections.json"));
|
|
7
|
+
var _formWithCollectionsDeleteEntire = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/form-with-collections-delete-entire.json"));
|
|
8
|
+
var _dataWithCollections = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-collections.json"));
|
|
9
|
+
var _dataWithEntireCollectionRemoved = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-entire-collection-removed.json"));
|
|
10
|
+
var _dataWithCollectionDataRemoved = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-collection-data-removed.json"));
|
|
11
|
+
var _formWithComponents = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/form-with-components.json"));
|
|
12
|
+
var _dataWithComponents = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-components.json"));
|
|
13
|
+
var _dataWithComponentsRemoved = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-components-removed.json"));
|
|
14
|
+
var _formForNestedComponents = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/form-for-nested-components.json"));
|
|
15
|
+
var _dataWithNestedComponents = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-nested-components.json"));
|
|
16
|
+
var _dataWithNestedComponentRemoved = _interopRequireDefault(require("../clear-uncompleted-routes/test-data/data-with-nested-component-removed.json"));
|
|
17
|
+
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
18
|
+
describe('FormRenderer', function () {
|
|
19
|
+
describe('helpers', function () {
|
|
20
|
+
describe('clearOutUncompletedRoutes', function () {
|
|
21
|
+
it('should not remove hidden component where it is visible in another page', function () {
|
|
22
|
+
var form = JSON.parse(JSON.stringify(_componentUsedInMultiplePagesForm.default));
|
|
23
|
+
var formData = JSON.parse(JSON.stringify(_componentUsedInMultiplePagesData.default));
|
|
24
|
+
expect(_index.default.clearOutUncompletedRoutes(form, formData)).toEqual(_componentUsedInMultiplePagesData.default);
|
|
25
|
+
});
|
|
26
|
+
it('should remove collection data when page hidden', function () {
|
|
27
|
+
var form = JSON.parse(JSON.stringify(_formWithCollections.default));
|
|
28
|
+
var formData = JSON.parse(JSON.stringify(_dataWithCollections.default));
|
|
29
|
+
var result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
30
|
+
expect(result).toEqual(_dataWithCollectionDataRemoved.default);
|
|
31
|
+
formData = JSON.parse(JSON.stringify(_dataWithCollections.default));
|
|
32
|
+
formData.componentA = true;
|
|
33
|
+
result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
34
|
+
var expected = JSON.parse(JSON.stringify(_dataWithCollections.default));
|
|
35
|
+
expected.componentA = true;
|
|
36
|
+
expect(result).toEqual(expected);
|
|
37
|
+
});
|
|
38
|
+
it('should remove entire collection data when page hidden', function () {
|
|
39
|
+
var form = JSON.parse(JSON.stringify(_formWithCollectionsDeleteEntire.default));
|
|
40
|
+
var formData = JSON.parse(JSON.stringify(_dataWithCollections.default));
|
|
41
|
+
var result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
42
|
+
expect(result).toEqual(_dataWithEntireCollectionRemoved.default);
|
|
43
|
+
});
|
|
44
|
+
it('should remove hidden component', function () {
|
|
45
|
+
var form = JSON.parse(JSON.stringify(_formWithComponents.default));
|
|
46
|
+
var formData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
47
|
+
var result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
48
|
+
expect(result).toEqual(_dataWithComponents.default);
|
|
49
|
+
formData.componentA = "hide";
|
|
50
|
+
result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
51
|
+
expect(result).toEqual(_dataWithComponentsRemoved.default);
|
|
52
|
+
});
|
|
53
|
+
it('should not remove hidden component when disableClearWhenHidden attribute is true on component', function () {
|
|
54
|
+
var formData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
55
|
+
formData.componentA = "hide";
|
|
56
|
+
var form = JSON.parse(JSON.stringify(_formWithComponents.default));
|
|
57
|
+
var result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
58
|
+
expect(result).toEqual(_dataWithComponentsRemoved.default);
|
|
59
|
+
form.components[1].disableClearWhenHidden = true;
|
|
60
|
+
form.components[2].disableClearWhenHidden = true;
|
|
61
|
+
formData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
62
|
+
result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
63
|
+
expect(result).toEqual(_dataWithComponents.default);
|
|
64
|
+
});
|
|
65
|
+
it('should not remove hidden component when disableClearWhenHidden attribute is true on page', function () {
|
|
66
|
+
var formData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
67
|
+
formData.componentA = "hide";
|
|
68
|
+
var form = JSON.parse(JSON.stringify(_formWithComponents.default));
|
|
69
|
+
var result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
70
|
+
expect(result).toEqual(_dataWithComponentsRemoved.default);
|
|
71
|
+
form.pages[0].disableClearWhenHidden = true;
|
|
72
|
+
formData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
73
|
+
result = _index.default.clearOutUncompletedRoutes(form, formData);
|
|
74
|
+
expect(result).toEqual(_dataWithComponents.default);
|
|
75
|
+
});
|
|
76
|
+
it('should not remove hidden component when disableClearWhenHidden attribute is true on form', function () {
|
|
77
|
+
var submissionData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
78
|
+
var form = JSON.parse(JSON.stringify(_formWithComponents.default));
|
|
79
|
+
submissionData.componentA = "hide";
|
|
80
|
+
var result = _index.default.clearOutUncompletedRoutes(form, submissionData);
|
|
81
|
+
expect(result).toEqual(_dataWithComponentsRemoved.default);
|
|
82
|
+
form.disableClearWhenHidden = true;
|
|
83
|
+
submissionData = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
84
|
+
submissionData.componentA = "hide";
|
|
85
|
+
result = _index.default.clearOutUncompletedRoutes(form, submissionData);
|
|
86
|
+
var expected = JSON.parse(JSON.stringify(_dataWithComponents.default));
|
|
87
|
+
expected.componentA = "hide";
|
|
88
|
+
expect(result).toEqual(expected);
|
|
89
|
+
});
|
|
90
|
+
it('should remove nested hidden component', function () {
|
|
91
|
+
var submissionData = JSON.parse(JSON.stringify(_dataWithNestedComponents.default));
|
|
92
|
+
var form = JSON.parse(JSON.stringify(_formForNestedComponents.default));
|
|
93
|
+
var result = _index.default.clearOutUncompletedRoutes(form, submissionData);
|
|
94
|
+
expect(result).toEqual(_dataWithNestedComponentRemoved.default);
|
|
95
|
+
submissionData = JSON.parse(JSON.stringify(_dataWithNestedComponents.default));
|
|
96
|
+
submissionData.bravo = "another";
|
|
97
|
+
result = _index.default.clearOutUncompletedRoutes(form, submissionData);
|
|
98
|
+
var expected = JSON.parse(JSON.stringify(_dataWithNestedComponents.default));
|
|
99
|
+
delete expected.person.charlie;
|
|
100
|
+
expected.bravo = "another";
|
|
101
|
+
expect(result).toEqual(expected);
|
|
102
|
+
submissionData = JSON.parse(JSON.stringify(_dataWithNestedComponents.default));
|
|
103
|
+
submissionData.bravo = "notMatchAnything";
|
|
104
|
+
result = _index.default.clearOutUncompletedRoutes(form, submissionData);
|
|
105
|
+
expected = JSON.parse(JSON.stringify(_dataWithNestedComponents.default));
|
|
106
|
+
delete expected.person.charlie;
|
|
107
|
+
delete expected.person.delta;
|
|
108
|
+
expected.bravo = "notMatchAnything";
|
|
109
|
+
expect(result).toEqual(expected);
|
|
110
|
+
});
|
|
111
|
+
});
|
|
112
|
+
});
|
|
113
|
+
});
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.default = void 0;
|
|
7
|
+
/* eslint-disable consistent-return */
|
|
8
|
+
var deleteNodeByPath = function deleteNodeByPath(obj, path) {
|
|
9
|
+
var keys = path.split('.');
|
|
10
|
+
var current = obj;
|
|
11
|
+
for (var i = 0; i < keys.length - 1; i += 1) {
|
|
12
|
+
current = current[keys[i]];
|
|
13
|
+
if (current === undefined) {
|
|
14
|
+
return;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
delete current[keys[keys.length - 1]];
|
|
18
|
+
return obj;
|
|
19
|
+
};
|
|
20
|
+
var _default = exports.default = deleteNodeByPath;
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
var _deleteNodeByPath = _interopRequireDefault(require("./deleteNodeByPath"));
|
|
4
|
+
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
5
|
+
describe('Delete node based on path', function () {
|
|
6
|
+
it('delete where node is at parent level', function () {
|
|
7
|
+
var nested = {
|
|
8
|
+
type: "Example form",
|
|
9
|
+
alpha: "alpha",
|
|
10
|
+
bravo: "bravo",
|
|
11
|
+
person: {
|
|
12
|
+
charlie: "Smith",
|
|
13
|
+
delta: "Acme Inc"
|
|
14
|
+
},
|
|
15
|
+
gamma: "gamma",
|
|
16
|
+
epsilon: "epsilon"
|
|
17
|
+
};
|
|
18
|
+
var path = 'type';
|
|
19
|
+
var result = (0, _deleteNodeByPath.default)(nested, path);
|
|
20
|
+
expect(result).toEqual({
|
|
21
|
+
alpha: "alpha",
|
|
22
|
+
bravo: "bravo",
|
|
23
|
+
person: {
|
|
24
|
+
charlie: "Smith",
|
|
25
|
+
delta: "Acme Inc"
|
|
26
|
+
},
|
|
27
|
+
gamma: "gamma",
|
|
28
|
+
epsilon: "epsilon"
|
|
29
|
+
});
|
|
30
|
+
});
|
|
31
|
+
it('delete where node is at child level', function () {
|
|
32
|
+
var nested = {
|
|
33
|
+
type: "Example form",
|
|
34
|
+
alpha: "alpha",
|
|
35
|
+
bravo: "bravo",
|
|
36
|
+
person: {
|
|
37
|
+
charlie: "Smith",
|
|
38
|
+
delta: "Acme Inc"
|
|
39
|
+
},
|
|
40
|
+
gamma: "gamma",
|
|
41
|
+
epsilon: "epsilon"
|
|
42
|
+
};
|
|
43
|
+
var path = 'person.charlie';
|
|
44
|
+
var result = (0, _deleteNodeByPath.default)(nested, path);
|
|
45
|
+
expect(result).toEqual({
|
|
46
|
+
type: "Example form",
|
|
47
|
+
alpha: "alpha",
|
|
48
|
+
bravo: "bravo",
|
|
49
|
+
person: {
|
|
50
|
+
delta: "Acme Inc"
|
|
51
|
+
},
|
|
52
|
+
gamma: "gamma",
|
|
53
|
+
epsilon: "epsilon"
|
|
54
|
+
});
|
|
55
|
+
});
|
|
56
|
+
});
|
|
@@ -13,6 +13,7 @@ var _getNextPageId = _interopRequireDefault(require("./getNextPageId"));
|
|
|
13
13
|
var _getPage = _interopRequireDefault(require("./getPage"));
|
|
14
14
|
var _getSubmissionStatus = _interopRequireDefault(require("./getSubmissionStatus"));
|
|
15
15
|
var _getUpdatedSectionStates = _interopRequireDefault(require("./getUpdatedSectionStates"));
|
|
16
|
+
var _clearOutUncompletedRoutes = _interopRequireDefault(require("./clearOutUncompletedRoutes"));
|
|
16
17
|
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
17
18
|
// Local imports
|
|
18
19
|
|
|
@@ -25,6 +26,7 @@ var helpers = {
|
|
|
25
26
|
getNextPageId: _getNextPageId.default,
|
|
26
27
|
getPage: _getPage.default,
|
|
27
28
|
getSubmissionStatus: _getSubmissionStatus.default,
|
|
28
|
-
getUpdatedSectionStates: _getUpdatedSectionStates.default
|
|
29
|
+
getUpdatedSectionStates: _getUpdatedSectionStates.default,
|
|
30
|
+
clearOutUncompletedRoutes: _clearOutUncompletedRoutes.default
|
|
29
31
|
};
|
|
30
32
|
var _default = exports.default = helpers;
|
|
@@ -56,6 +56,7 @@ var onPageAction = function onPageAction(action, patch, patchLabel, hooks, data,
|
|
|
56
56
|
_handlers.default.navigate(action, pageId, onPageChange);
|
|
57
57
|
setSubmitting(false);
|
|
58
58
|
} else {
|
|
59
|
+
var baseData = _objectSpread(_objectSpread(_objectSpread({}, data), patch), formState.page.formData);
|
|
59
60
|
var pageUpdate = function pageUpdate(next) {
|
|
60
61
|
return onPageChange(_helpers.default.getNextPageId(type, pages, pageId, action, next));
|
|
61
62
|
};
|
|
@@ -107,8 +108,13 @@ var onPageAction = function onPageAction(action, patch, patchLabel, hooks, data,
|
|
|
107
108
|
setData(submissionData);
|
|
108
109
|
}
|
|
109
110
|
;
|
|
110
|
-
|
|
111
|
-
|
|
111
|
+
if (action.type === _models.PageAction.TYPES.SUBMIT) {
|
|
112
|
+
_helpers.default.clearOutUncompletedRoutes({
|
|
113
|
+
pages: pages,
|
|
114
|
+
components: components
|
|
115
|
+
}, submissionData);
|
|
116
|
+
}
|
|
117
|
+
// In case of hub-and-spoke if patchLabel has changed then
|
|
112
118
|
// save name and value to variables for call to onSubmit hook
|
|
113
119
|
var changedFieldName;
|
|
114
120
|
var changedFieldValue;
|
|
@@ -50,6 +50,11 @@ jest.mock('./helpers', function () {
|
|
|
50
50
|
this.cleanHiddenNestedDataCalls += 1;
|
|
51
51
|
return patch;
|
|
52
52
|
},
|
|
53
|
+
clearOutUncompletedRoutesCalls: 0,
|
|
54
|
+
clearOutUncompletedRoutes: function clearOutUncompletedRoutes(pages, allComponents, formData) {
|
|
55
|
+
this.clearOutUncompletedRoutesCalls += 1;
|
|
56
|
+
return formData;
|
|
57
|
+
},
|
|
53
58
|
getNextPageIdCalls: 0,
|
|
54
59
|
getNextPageId: function getNextPageId() {
|
|
55
60
|
this.getNextPageIdCalls += 1;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
@import 'govuk-frontend/
|
|
2
|
-
@import 'govuk-frontend/
|
|
1
|
+
@import 'node_modules/govuk-frontend/govuk/_base';
|
|
2
|
+
@import 'node_modules/govuk-frontend/govuk/components/summary-list/_summary-list';
|
|
3
3
|
|
|
4
4
|
.govuk-summary-list__title {
|
|
5
5
|
width: 100%;
|
|
@@ -32,6 +32,7 @@ var createMasterPage = function createMasterPage(page) {
|
|
|
32
32
|
return {
|
|
33
33
|
id: page.id,
|
|
34
34
|
name: page.name,
|
|
35
|
+
deleteCollectionWhenHidden: page.deleteCollectionWhenHidden,
|
|
35
36
|
collection: _objectSpread({
|
|
36
37
|
masterPage: true
|
|
37
38
|
}, page.collection),
|
|
@@ -84,7 +85,7 @@ var nestUnderParent = function nestUnderParent(childPage, masterPages) {
|
|
|
84
85
|
*/
|
|
85
86
|
var mergeCollectionPages = function mergeCollectionPages(pages) {
|
|
86
87
|
var masterPages = {};
|
|
87
|
-
|
|
88
|
+
var pagesWithMasters = pages.map(function (page) {
|
|
88
89
|
var _page$collection;
|
|
89
90
|
if (page !== null && page !== void 0 && (_page$collection = page.collection) !== null && _page$collection !== void 0 && _page$collection.name) {
|
|
90
91
|
if (!masterPages[page.collection.name]) {
|
|
@@ -92,10 +93,7 @@ var mergeCollectionPages = function mergeCollectionPages(pages) {
|
|
|
92
93
|
// we kick one off using this page as a template.
|
|
93
94
|
var newMasterPage = createMasterPage(page);
|
|
94
95
|
masterPages[page.collection.name] = newMasterPage;
|
|
95
|
-
|
|
96
|
-
// if so then nest it under the parent master page and remove from
|
|
97
|
-
// the pages array. If not then treat it as a top-level collection.
|
|
98
|
-
return nestUnderParent(newMasterPage, masterPages) ? null : newMasterPage;
|
|
96
|
+
return newMasterPage;
|
|
99
97
|
}
|
|
100
98
|
// If a master page already exists for this collection.name
|
|
101
99
|
// then we just merge this page into it and remove this page
|
|
@@ -107,5 +105,17 @@ var mergeCollectionPages = function mergeCollectionPages(pages) {
|
|
|
107
105
|
}).filter(function (page) {
|
|
108
106
|
return !!page;
|
|
109
107
|
});
|
|
108
|
+
// We nest any child master pages under their parents here to
|
|
109
|
+
// ensure that all parent master pages have been created by the
|
|
110
|
+
// above code first.
|
|
111
|
+
return pagesWithMasters.map(function (page) {
|
|
112
|
+
var _page$collection2;
|
|
113
|
+
if ((_page$collection2 = page.collection) !== null && _page$collection2 !== void 0 && _page$collection2.masterPage) {
|
|
114
|
+
return nestUnderParent(page, masterPages) ? null : page;
|
|
115
|
+
}
|
|
116
|
+
return page;
|
|
117
|
+
}).filter(function (e) {
|
|
118
|
+
return !!e;
|
|
119
|
+
});
|
|
110
120
|
};
|
|
111
121
|
var _default = exports.default = mergeCollectionPages;
|
|
@@ -49,7 +49,7 @@ describe('utils.CollectionPage.mergeCollectionPages', function () {
|
|
|
49
49
|
childPages: PAGES
|
|
50
50
|
});
|
|
51
51
|
});
|
|
52
|
-
it('should correctly merge and
|
|
52
|
+
it('should correctly merge and nest child collection pages under their parents', function () {
|
|
53
53
|
var PAGES = [{
|
|
54
54
|
id: 'page1',
|
|
55
55
|
collection: {
|
|
@@ -95,6 +95,53 @@ describe('utils.CollectionPage.mergeCollectionPages', function () {
|
|
|
95
95
|
}]
|
|
96
96
|
});
|
|
97
97
|
});
|
|
98
|
+
it('should correctly merge and nest child collection pages under their parents, even if the child pages are created first', function () {
|
|
99
|
+
var PAGES = [{
|
|
100
|
+
id: 'page1',
|
|
101
|
+
collection: {
|
|
102
|
+
name: 'parent.child'
|
|
103
|
+
},
|
|
104
|
+
components: [TEXT_COMP]
|
|
105
|
+
}, {
|
|
106
|
+
id: 'page2',
|
|
107
|
+
collection: {
|
|
108
|
+
name: 'parent.child'
|
|
109
|
+
},
|
|
110
|
+
components: [DATE_COMP]
|
|
111
|
+
}, {
|
|
112
|
+
id: 'page3',
|
|
113
|
+
collection: {
|
|
114
|
+
name: 'parent'
|
|
115
|
+
},
|
|
116
|
+
components: [DATE_COMP]
|
|
117
|
+
}, {
|
|
118
|
+
id: 'page4',
|
|
119
|
+
collection: {
|
|
120
|
+
name: 'parent'
|
|
121
|
+
},
|
|
122
|
+
components: [DATE_COMP]
|
|
123
|
+
}];
|
|
124
|
+
var RESULT = (0, _mergeCollectionPages.default)(PAGES);
|
|
125
|
+
expect(RESULT.length).toEqual(1); // One master page for parent collection.
|
|
126
|
+
expect(RESULT[0].childPages.length).toEqual(3); // Two normal pages and the child collection's master page.
|
|
127
|
+
expect(RESULT[0]).toMatchObject({
|
|
128
|
+
id: 'page3',
|
|
129
|
+
collection: {
|
|
130
|
+
name: 'parent',
|
|
131
|
+
masterPage: true
|
|
132
|
+
},
|
|
133
|
+
formData: {},
|
|
134
|
+
childPages: [PAGES[2], PAGES[3], {
|
|
135
|
+
id: 'page1',
|
|
136
|
+
collection: {
|
|
137
|
+
name: 'parent.child',
|
|
138
|
+
masterPage: true
|
|
139
|
+
},
|
|
140
|
+
formData: {},
|
|
141
|
+
childPages: [PAGES[0], PAGES[1]]
|
|
142
|
+
}]
|
|
143
|
+
});
|
|
144
|
+
});
|
|
98
145
|
it('should leave non-collection pages unaffected', function () {
|
|
99
146
|
var PAGES = [{
|
|
100
147
|
id: 'page1',
|
|
@@ -33,9 +33,9 @@ var setCollectionPageData = function setCollectionPageData(collectionName, newDa
|
|
|
33
33
|
if (!data[name]) {
|
|
34
34
|
var newEntryId = Date.now().toString();
|
|
35
35
|
// eslint-disable-next-line no-param-reassign
|
|
36
|
-
formData["".concat(name, "ActiveId")] = newEntryId;
|
|
36
|
+
formData["".concat(name, "ActiveId")] = formData["".concat(name, "ActiveId")] || newEntryId;
|
|
37
37
|
data[name] = [{
|
|
38
|
-
id:
|
|
38
|
+
id: formData["".concat(name, "ActiveId")]
|
|
39
39
|
}];
|
|
40
40
|
}
|
|
41
41
|
// We're at the target collection's level, so
|
|
@@ -32,6 +32,37 @@ describe('Utils.CollectionPage.setCollectionPageData', function () {
|
|
|
32
32
|
value: 'Alpha'
|
|
33
33
|
});
|
|
34
34
|
});
|
|
35
|
+
it('should not overwrite existing entry IDs', function () {
|
|
36
|
+
var FORM_DATA = {
|
|
37
|
+
grandchildActiveId: 77
|
|
38
|
+
};
|
|
39
|
+
var NEW_DATA = [{
|
|
40
|
+
id: '123',
|
|
41
|
+
value: 'Alpha'
|
|
42
|
+
}];
|
|
43
|
+
(0, _setCollectionPageData.default)('parent.child.grandchild', NEW_DATA, FORM_DATA);
|
|
44
|
+
|
|
45
|
+
// Check active Ids have been added for all collections in
|
|
46
|
+
// the path.
|
|
47
|
+
expect(FORM_DATA.parentActiveId).toBeDefined();
|
|
48
|
+
expect(FORM_DATA.childActiveId).toBeDefined();
|
|
49
|
+
expect(FORM_DATA.grandchildActiveId).toEqual(77);
|
|
50
|
+
|
|
51
|
+
// Parent collection.
|
|
52
|
+
expect(FORM_DATA.parent.length).toEqual(1);
|
|
53
|
+
expect(FORM_DATA.parent[0].id).toBeTruthy();
|
|
54
|
+
|
|
55
|
+
// Child collection.
|
|
56
|
+
expect(FORM_DATA.parent[0].child.length).toEqual(1);
|
|
57
|
+
expect(FORM_DATA.parent[0].child[0].id).toBeTruthy();
|
|
58
|
+
|
|
59
|
+
// Child collection.
|
|
60
|
+
expect(FORM_DATA.parent[0].child[0].grandchild.length).toEqual(1);
|
|
61
|
+
expect(FORM_DATA.parent[0].child[0].grandchild[0]).toMatchObject({
|
|
62
|
+
id: '123',
|
|
63
|
+
value: 'Alpha'
|
|
64
|
+
});
|
|
65
|
+
});
|
|
35
66
|
describe('when failing to set data for a nested collection', function () {
|
|
36
67
|
it('should do nothing if one of the parent collections does not exist', function () {
|
|
37
68
|
var FORM_DATA = {
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
Object.defineProperty(exports, "__esModule", {
|
|
4
|
+
value: true
|
|
5
|
+
});
|
|
6
|
+
exports.default = void 0;
|
|
7
|
+
var _copReactComponents = require("@ukhomeoffice/cop-react-components");
|
|
8
|
+
var _meetsAllConditions = _interopRequireDefault(require("../Condition/meetsAllConditions"));
|
|
9
|
+
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
|
|
10
|
+
// Global imports.
|
|
11
|
+
|
|
12
|
+
// Local imports.
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* Gets the first options in an array of strings that passes all of it's conditions.
|
|
16
|
+
*
|
|
17
|
+
* Options is expected to be in the format:
|
|
18
|
+
* [
|
|
19
|
+
* {
|
|
20
|
+
* text: 'Option A',
|
|
21
|
+
* show_when: [ ... ]
|
|
22
|
+
* },
|
|
23
|
+
* {
|
|
24
|
+
* text: 'Option B',
|
|
25
|
+
* show_when: [ ... ]
|
|
26
|
+
* }
|
|
27
|
+
* ...
|
|
28
|
+
* ]
|
|
29
|
+
*
|
|
30
|
+
* @param {Array} options An array of options matching the above format.
|
|
31
|
+
* @param {Object} formData A formData object to use when evaluating the conditions.
|
|
32
|
+
* @param {String} key The key to use to find the text to use in each option, defaults to 'text'.
|
|
33
|
+
* @returns The first string that passes its' conditions, or null if something went wrong.
|
|
34
|
+
*/
|
|
35
|
+
var getConditionalText = function getConditionalText(options, formData) {
|
|
36
|
+
var key = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 'text';
|
|
37
|
+
if (typeof options === 'string') {
|
|
38
|
+
return _copReactComponents.Utils.interpolateString(options, formData);
|
|
39
|
+
}
|
|
40
|
+
if (!Array.isArray(options) || Object.keys(formData).length === 0) {
|
|
41
|
+
return null;
|
|
42
|
+
}
|
|
43
|
+
var shownOption = options.find(function (option) {
|
|
44
|
+
if (typeof option === 'string') {
|
|
45
|
+
// This is intended to allow a plain string 'fallback' option in the array.
|
|
46
|
+
// As such, it should be the last option in the array as any options after
|
|
47
|
+
// it will not be considered.
|
|
48
|
+
return true;
|
|
49
|
+
}
|
|
50
|
+
return (0, _meetsAllConditions.default)(option.show_when, formData);
|
|
51
|
+
});
|
|
52
|
+
return typeof shownOption === 'string' ? _copReactComponents.Utils.interpolateString(shownOption, formData) : _copReactComponents.Utils.interpolateString(shownOption[key], formData);
|
|
53
|
+
};
|
|
54
|
+
var _default = exports.default = getConditionalText;
|