@oneblink/sdk-core 9.2.2 → 10.0.0-beta.2
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/LICENSE +21 -674
- package/dist/conditionalLogicService/conditionallyShowElement.d.ts +16 -8
- package/dist/conditionalLogicService/conditionallyShowElement.js +19 -11
- package/dist/conditionalLogicService/conditionallyShowElement.js.map +1 -1
- package/dist/conditionalLogicService/conditionallyShowOption.d.ts +6 -1
- package/dist/conditionalLogicService/conditionallyShowOption.js +43 -11
- package/dist/conditionalLogicService/conditionallyShowOption.js.map +1 -1
- package/dist/conditionalLogicService/evaluateConditionalSubmissionTimestampPredicate.d.ts +20 -0
- package/dist/conditionalLogicService/evaluateConditionalSubmissionTimestampPredicate.js +71 -0
- package/dist/conditionalLogicService/evaluateConditionalSubmissionTimestampPredicate.js.map +1 -0
- package/dist/conditionalLogicService/evaluateFormElementConditionalPredicate.d.ts +15 -0
- package/dist/conditionalLogicService/{evaluateConditionalPredicate.js → evaluateFormElementConditionalPredicate.js} +25 -12
- package/dist/conditionalLogicService/evaluateFormElementConditionalPredicate.js.map +1 -0
- package/dist/conditionalLogicService/generateFormElementsConditionallyShown.d.ts +21 -13
- package/dist/conditionalLogicService/generateFormElementsConditionallyShown.js +99 -23
- package/dist/conditionalLogicService/generateFormElementsConditionallyShown.js.map +1 -1
- package/dist/conditionalLogicService/types.d.ts +10 -0
- package/dist/conditionalLogicService/types.js.map +1 -1
- package/dist/conditionalLogicService.d.ts +15 -1
- package/dist/conditionalLogicService.js +24 -6
- package/dist/conditionalLogicService.js.map +1 -1
- package/dist/paymentService.d.ts +22 -4
- package/dist/paymentService.js +15 -4
- package/dist/paymentService.js.map +1 -1
- package/dist/schedulingService.d.ts +21 -6
- package/dist/schedulingService.js +14 -6
- package/dist/schedulingService.js.map +1 -1
- package/package.json +2 -2
- package/dist/conditionalLogicService/evaluateConditionalPredicate.d.ts +0 -6
- package/dist/conditionalLogicService/evaluateConditionalPredicate.js.map +0 -1
|
@@ -1,10 +1,18 @@
|
|
|
1
1
|
import { FormTypes, ConditionTypes } from '@oneblink/types';
|
|
2
2
|
import { FormElementsCtrl } from './types.js';
|
|
3
|
-
export declare function conditionallyShowByPredicate(formElementsCtrl
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
}
|
|
3
|
+
export declare function conditionallyShowByPredicate({ formElementsCtrl, predicate, elementsEvaluated, }: {
|
|
4
|
+
formElementsCtrl: FormElementsCtrl;
|
|
5
|
+
predicate: ConditionTypes.FormElementConditionalPredicate;
|
|
6
|
+
elementsEvaluated: Array<{
|
|
7
|
+
id: string;
|
|
8
|
+
label: string;
|
|
9
|
+
}>;
|
|
10
|
+
}): boolean;
|
|
11
|
+
export default function conditionallyShowElement({ formElementsCtrl, elementToEvaluate, elementsEvaluated, }: {
|
|
12
|
+
formElementsCtrl: FormElementsCtrl;
|
|
13
|
+
elementToEvaluate: FormTypes.FormElement;
|
|
14
|
+
elementsEvaluated: Array<{
|
|
15
|
+
id: string;
|
|
16
|
+
label: string;
|
|
17
|
+
}>;
|
|
18
|
+
}): boolean;
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import
|
|
1
|
+
import evaluateFormElementConditionalPredicate from './evaluateFormElementConditionalPredicate.js';
|
|
2
2
|
const getParentFormElements = (formElementsCtrl, childElement) => {
|
|
3
3
|
const parentElement = formElementsCtrl.flattenedElements.find((element) => {
|
|
4
4
|
return ((element.type === 'page' || element.type === 'section') &&
|
|
@@ -13,8 +13,8 @@ const getParentFormElements = (formElementsCtrl, childElement) => {
|
|
|
13
13
|
}
|
|
14
14
|
return [];
|
|
15
15
|
};
|
|
16
|
-
export function conditionallyShowByPredicate(formElementsCtrl, predicate, elementsEvaluated) {
|
|
17
|
-
const predicateElement =
|
|
16
|
+
export function conditionallyShowByPredicate({ formElementsCtrl, predicate, elementsEvaluated, }) {
|
|
17
|
+
const predicateElement = evaluateFormElementConditionalPredicate({
|
|
18
18
|
predicate,
|
|
19
19
|
formElementsCtrl,
|
|
20
20
|
});
|
|
@@ -27,16 +27,22 @@ export function conditionallyShowByPredicate(formElementsCtrl, predicate, elemen
|
|
|
27
27
|
// predicate element as hidden as well.
|
|
28
28
|
const parentFormElements = getParentFormElements(formElementsCtrl, predicateElement);
|
|
29
29
|
for (const parentFormElement of parentFormElements) {
|
|
30
|
-
if (!conditionallyShowElement(
|
|
31
|
-
|
|
32
|
-
|
|
30
|
+
if (!conditionallyShowElement({
|
|
31
|
+
formElementsCtrl,
|
|
32
|
+
elementToEvaluate: parentFormElement,
|
|
33
|
+
elementsEvaluated: [...elementsEvaluated],
|
|
34
|
+
})) {
|
|
33
35
|
return false;
|
|
34
36
|
}
|
|
35
37
|
}
|
|
36
38
|
// Check to see if the model has one of the valid values to show the element
|
|
37
|
-
return conditionallyShowElement(
|
|
39
|
+
return conditionallyShowElement({
|
|
40
|
+
formElementsCtrl,
|
|
41
|
+
elementToEvaluate: predicateElement,
|
|
42
|
+
elementsEvaluated,
|
|
43
|
+
});
|
|
38
44
|
}
|
|
39
|
-
export default function conditionallyShowElement(formElementsCtrl, elementToEvaluate, elementsEvaluated) {
|
|
45
|
+
export default function conditionallyShowElement({ formElementsCtrl, elementToEvaluate, elementsEvaluated, }) {
|
|
40
46
|
// If the element does not have the `conditionallyShow` flag set,
|
|
41
47
|
// we can always show the element.
|
|
42
48
|
if (!elementToEvaluate ||
|
|
@@ -64,9 +70,11 @@ export default function conditionallyShowElement(formElementsCtrl, elementToEval
|
|
|
64
70
|
// Spread the array of elements evaluated so that each predicate can
|
|
65
71
|
// evaluate the tree without causing false positives for infinite
|
|
66
72
|
// loop conditional logic
|
|
67
|
-
return conditionallyShowByPredicate(
|
|
68
|
-
|
|
69
|
-
|
|
73
|
+
return conditionallyShowByPredicate({
|
|
74
|
+
formElementsCtrl,
|
|
75
|
+
predicate,
|
|
76
|
+
elementsEvaluated: [...elementsEvaluated],
|
|
77
|
+
});
|
|
70
78
|
};
|
|
71
79
|
if (elementToEvaluate.requiresAllConditionallyShowPredicates) {
|
|
72
80
|
return conditionallyShowPredicates.every(predicateFunction);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"conditionallyShowElement.js","sourceRoot":"","sources":["../../src/conditionalLogicService/conditionallyShowElement.ts"],"names":[],"mappings":"AAEA,OAAO,
|
|
1
|
+
{"version":3,"file":"conditionallyShowElement.js","sourceRoot":"","sources":["../../src/conditionalLogicService/conditionallyShowElement.ts"],"names":[],"mappings":"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","sourcesContent":["import { FormTypes, ConditionTypes } from '@oneblink/types'\nimport { FormElementsCtrl } from './types.js'\nimport evaluateFormElementConditionalPredicate from './evaluateFormElementConditionalPredicate.js'\n\nconst getParentFormElements = (\n formElementsCtrl: FormElementsCtrl,\n childElement: FormTypes.FormElement,\n): Array<FormTypes.SectionElement | FormTypes.PageElement> => {\n const parentElement = formElementsCtrl.flattenedElements.find((element) => {\n return (\n (element.type === 'page' || element.type === 'section') &&\n element.elements.some(({ id }) => id === childElement.id)\n )\n })\n if (\n parentElement &&\n (parentElement.type === 'page' || parentElement.type === 'section')\n ) {\n return [\n parentElement,\n ...getParentFormElements(formElementsCtrl, parentElement),\n ]\n }\n return []\n}\n\nexport function conditionallyShowByPredicate({\n formElementsCtrl,\n predicate,\n elementsEvaluated,\n}: {\n formElementsCtrl: FormElementsCtrl\n predicate: ConditionTypes.FormElementConditionalPredicate\n elementsEvaluated: Array<{ id: string; label: string }>\n}): boolean {\n const predicateElement = evaluateFormElementConditionalPredicate({\n predicate,\n formElementsCtrl,\n })\n\n if (!predicateElement) {\n return false\n }\n\n // Here we will also need to check if the predicate element\n // is on a page/section element and the page/section element\n // is also hidden. If it is hidden we will treat this\n // predicate element as hidden as well.\n const parentFormElements = getParentFormElements(\n formElementsCtrl,\n predicateElement,\n )\n for (const parentFormElement of parentFormElements) {\n if (\n !conditionallyShowElement({\n formElementsCtrl,\n elementToEvaluate: parentFormElement,\n elementsEvaluated: [...elementsEvaluated],\n })\n ) {\n return false\n }\n }\n\n // Check to see if the model has one of the valid values to show the element\n return conditionallyShowElement({\n formElementsCtrl,\n elementToEvaluate: predicateElement,\n elementsEvaluated,\n })\n}\n\nexport default function conditionallyShowElement({\n formElementsCtrl,\n elementToEvaluate,\n elementsEvaluated,\n}: {\n formElementsCtrl: FormElementsCtrl\n elementToEvaluate: FormTypes.FormElement\n elementsEvaluated: Array<{ id: string; label: string }>\n}): boolean {\n // If the element does not have the `conditionallyShow` flag set,\n // we can always show the element.\n if (\n !elementToEvaluate ||\n !elementToEvaluate.conditionallyShow ||\n !Array.isArray(elementToEvaluate.conditionallyShowPredicates) ||\n !elementToEvaluate.conditionallyShowPredicates.length\n ) {\n return true\n }\n const conditionallyShowPredicates =\n elementToEvaluate.conditionallyShowPredicates\n\n // Check to see if this element has already been used to evaluate\n // if the element should be shown based on parent element conditional logic\n const elementAlreadyEvaluated = elementsEvaluated.find(\n ({ id }) => id === elementToEvaluate.id,\n )\n if (elementAlreadyEvaluated) {\n throw new Error(\n `Your conditional logic has caused an infinite loop. Check the \"${elementAlreadyEvaluated.label}\" form element to ensure element A does not rely on element B if element B also relies on element A.`,\n )\n } else {\n elementsEvaluated.push({\n id: elementToEvaluate.id,\n label:\n 'label' in elementToEvaluate\n ? elementToEvaluate.label\n : elementToEvaluate.name,\n })\n }\n\n const predicateFunction = (\n predicate: ConditionTypes.FormElementConditionalPredicate,\n ) => {\n // Spread the array of elements evaluated so that each predicate can\n // evaluate the tree without causing false positives for infinite\n // loop conditional logic\n return conditionallyShowByPredicate({\n formElementsCtrl,\n predicate,\n elementsEvaluated: [...elementsEvaluated],\n })\n }\n\n if (elementToEvaluate.requiresAllConditionallyShowPredicates) {\n return conditionallyShowPredicates.every(predicateFunction)\n } else {\n return conditionallyShowPredicates.some(predicateFunction)\n }\n}\n"]}
|
|
@@ -1,4 +1,9 @@
|
|
|
1
1
|
import { FormTypes } from '@oneblink/types';
|
|
2
2
|
import { FormElementsCtrl } from './types.js';
|
|
3
3
|
export type ShouldShowOption = 'SHOW' | 'HIDE' | 'LOADING_DYNAMIC_DEPENDENCY' | 'LOADING_STATIC_DEPENDENCY';
|
|
4
|
-
export default function conditionallyShowOption(formElementsCtrl
|
|
4
|
+
export default function conditionallyShowOption({ formElementsCtrl, elementToEvaluate, optionToEvaluate, optionsEvaluated, }: {
|
|
5
|
+
formElementsCtrl: FormElementsCtrl;
|
|
6
|
+
elementToEvaluate: FormTypes.FormElementWithOptions;
|
|
7
|
+
optionToEvaluate: FormTypes.ChoiceElementOption;
|
|
8
|
+
optionsEvaluated: string[];
|
|
9
|
+
}): ShouldShowOption;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import evaluateConditionalOptionsPredicate from './evaluateConditionalOptionsPredicate.js';
|
|
2
2
|
import { typeCastService } from '../index.js';
|
|
3
3
|
import conditionallyShowElement from './conditionallyShowElement.js';
|
|
4
|
-
const handleAttributePredicate = (predicate, model, predicateElement) => {
|
|
4
|
+
const handleAttributePredicate = ({ predicate, model, predicateElement, }) => {
|
|
5
5
|
const values = model?.[predicateElement.name];
|
|
6
6
|
if (!values)
|
|
7
7
|
return true;
|
|
@@ -20,7 +20,7 @@ const handleAttributePredicate = (predicate, model, predicateElement) => {
|
|
|
20
20
|
predicateElement,
|
|
21
21
|
});
|
|
22
22
|
};
|
|
23
|
-
const conditionallyShowOptionByPredicate = (formElementsCtrl, predicate, elementsEvaluated) => {
|
|
23
|
+
const conditionallyShowOptionByPredicate = ({ formElementsCtrl, predicate, elementsEvaluated, }) => {
|
|
24
24
|
// Validate the predicate data, if it is invalid,
|
|
25
25
|
// we will always show the field
|
|
26
26
|
if (!predicate ||
|
|
@@ -38,7 +38,11 @@ const conditionallyShowOptionByPredicate = (formElementsCtrl, predicate, element
|
|
|
38
38
|
// in a parent list of elements.
|
|
39
39
|
if (!predicateElement) {
|
|
40
40
|
if (formElementsCtrl.parentFormElementsCtrl) {
|
|
41
|
-
return conditionallyShowOptionByPredicate(
|
|
41
|
+
return conditionallyShowOptionByPredicate({
|
|
42
|
+
formElementsCtrl: formElementsCtrl.parentFormElementsCtrl,
|
|
43
|
+
predicate,
|
|
44
|
+
elementsEvaluated,
|
|
45
|
+
});
|
|
42
46
|
}
|
|
43
47
|
else {
|
|
44
48
|
return 'HIDE';
|
|
@@ -65,16 +69,28 @@ const conditionallyShowOptionByPredicate = (formElementsCtrl, predicate, element
|
|
|
65
69
|
const predicateOption = optionsPredicateElement.options?.find((o) => o.id === id);
|
|
66
70
|
if (!predicateOption)
|
|
67
71
|
return 'HIDE';
|
|
68
|
-
return conditionallyShowOption({
|
|
72
|
+
return conditionallyShowOption({
|
|
73
|
+
formElementsCtrl: {
|
|
74
|
+
model: formElementsCtrl.model,
|
|
75
|
+
flattenedElements: [],
|
|
76
|
+
},
|
|
77
|
+
elementToEvaluate: optionsPredicateElement,
|
|
78
|
+
optionToEvaluate: predicateOption,
|
|
79
|
+
optionsEvaluated: elementsEvaluated,
|
|
80
|
+
});
|
|
69
81
|
});
|
|
70
82
|
if (!everyOptionIsShowing) {
|
|
71
83
|
return 'HIDE';
|
|
72
84
|
}
|
|
73
85
|
// Check to see if the model has one of the valid values to show the element
|
|
74
|
-
const shouldShow = handleAttributePredicate(
|
|
86
|
+
const shouldShow = handleAttributePredicate({
|
|
87
|
+
predicate,
|
|
88
|
+
model: formElementsCtrl.model,
|
|
89
|
+
predicateElement: optionsPredicateElement,
|
|
90
|
+
});
|
|
75
91
|
return shouldShow ? 'SHOW' : 'HIDE';
|
|
76
92
|
};
|
|
77
|
-
const isAttributeFilterValid = (formElementsCtrl, predicate, elementsEvaluated) => {
|
|
93
|
+
const isAttributeFilterValid = ({ formElementsCtrl, predicate, elementsEvaluated, }) => {
|
|
78
94
|
const predicateElement = formElementsCtrl.flattenedElements.find((element) => {
|
|
79
95
|
return element.id === predicate.elementId;
|
|
80
96
|
});
|
|
@@ -84,7 +100,11 @@ const isAttributeFilterValid = (formElementsCtrl, predicate, elementsEvaluated)
|
|
|
84
100
|
// in a parent list of elements.
|
|
85
101
|
if (!predicateElement) {
|
|
86
102
|
if (formElementsCtrl.parentFormElementsCtrl) {
|
|
87
|
-
return isAttributeFilterValid(
|
|
103
|
+
return isAttributeFilterValid({
|
|
104
|
+
formElementsCtrl: formElementsCtrl.parentFormElementsCtrl,
|
|
105
|
+
predicate,
|
|
106
|
+
elementsEvaluated,
|
|
107
|
+
});
|
|
88
108
|
}
|
|
89
109
|
else {
|
|
90
110
|
return false;
|
|
@@ -96,7 +116,11 @@ const isAttributeFilterValid = (formElementsCtrl, predicate, elementsEvaluated)
|
|
|
96
116
|
// Will never be a page, just making typescript happy :)
|
|
97
117
|
predicateElement.type === 'page' ||
|
|
98
118
|
predicateElement.type === 'section' ||
|
|
99
|
-
!conditionallyShowElement(
|
|
119
|
+
!conditionallyShowElement({
|
|
120
|
+
formElementsCtrl,
|
|
121
|
+
elementToEvaluate: predicateElement,
|
|
122
|
+
elementsEvaluated: [],
|
|
123
|
+
})) {
|
|
100
124
|
return false;
|
|
101
125
|
}
|
|
102
126
|
// verify that at least one option is selected
|
|
@@ -111,7 +135,7 @@ const isAttributeFilterValid = (formElementsCtrl, predicate, elementsEvaluated)
|
|
|
111
135
|
}
|
|
112
136
|
return true;
|
|
113
137
|
};
|
|
114
|
-
export default function conditionallyShowOption(formElementsCtrl, elementToEvaluate, optionToEvaluate, optionsEvaluated) {
|
|
138
|
+
export default function conditionallyShowOption({ formElementsCtrl, elementToEvaluate, optionToEvaluate, optionsEvaluated, }) {
|
|
115
139
|
// If the element does not have the `conditionallyShow` flag set,
|
|
116
140
|
// we can always show the option.
|
|
117
141
|
if (!elementToEvaluate.conditionallyShowOptions ||
|
|
@@ -130,7 +154,11 @@ export default function conditionallyShowOption(formElementsCtrl, elementToEvalu
|
|
|
130
154
|
optionsEvaluated.push(optionToEvaluate.id);
|
|
131
155
|
}
|
|
132
156
|
const validPredicates = (optionToEvaluate.attributes || []).filter((predicate) => {
|
|
133
|
-
return isAttributeFilterValid(
|
|
157
|
+
return isAttributeFilterValid({
|
|
158
|
+
formElementsCtrl,
|
|
159
|
+
predicate,
|
|
160
|
+
elementsEvaluated: optionsEvaluated,
|
|
161
|
+
});
|
|
134
162
|
});
|
|
135
163
|
if (!validPredicates.length)
|
|
136
164
|
return 'SHOW';
|
|
@@ -139,7 +167,11 @@ export default function conditionallyShowOption(formElementsCtrl, elementToEvalu
|
|
|
139
167
|
const showResults = Array(validPredicates.length).fill(false);
|
|
140
168
|
for (let i = 0; i < validPredicates.length; i++) {
|
|
141
169
|
const predicate = validPredicates[i];
|
|
142
|
-
const predicateResult = conditionallyShowOptionByPredicate(
|
|
170
|
+
const predicateResult = conditionallyShowOptionByPredicate({
|
|
171
|
+
formElementsCtrl,
|
|
172
|
+
predicate,
|
|
173
|
+
elementsEvaluated: optionsEvaluated,
|
|
174
|
+
});
|
|
143
175
|
switch (predicateResult) {
|
|
144
176
|
case 'SHOW': {
|
|
145
177
|
if (elementToEvaluate.requiresAllConditionallyShowOptionsPredicates) {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"conditionallyShowOption.js","sourceRoot":"","sources":["../../src/conditionalLogicService/conditionallyShowOption.ts"],"names":[],"mappings":"AACA,OAAO,mCAAmC,MAAM,0CAA0C,CAAA;AAE1F,OAAO,EAAE,eAAe,EAAE,MAAM,aAAa,CAAA;AAC7C,OAAO,wBAAwB,MAAM,+BAA+B,CAAA;AAQpE,MAAM,wBAAwB,GAAG,CAC/B,SAAiD,EACjD,KAAiE,EACjE,gBAAkD,EAClD,EAAE;IACF,MAAM,MAAM,GAAG,KAAK,EAAE,CAAC,gBAAgB,CAAC,IAAI,CAAC,CAAA;IAC7C,IAAI,CAAC,MAAM;QAAE,OAAO,IAAI,CAAA;IAExB,IACE,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC;QACrB,CAAC,CAAC,MAAM,CAAC,MAAM;YACb,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,OAAO,KAAK,KAAK,WAAW,CAAC,CAAC,MAAM,CAAC,EACjE,CAAC;QACD,OAAO,IAAI,CAAA;IACb,CAAC;IAED,OAAO,mCAAmC,CAAC;QACzC,SAAS,EAAE;YACT,IAAI,EAAE,SAAS;YACf,SAAS,EAAE,SAAS,CAAC,SAAS;YAC9B,SAAS,EAAE,SAAS,CAAC,SAAS;SAC/B;QACD,cAAc,EAAE,MAAM;QACtB,gBAAgB;KACjB,CAAC,CAAA;AACJ,CAAC,CAAA;AAED,MAAM,kCAAkC,GAAG,CACzC,gBAAkC,EAClC,SAAiD,EACjD,iBAA2B,EACT,EAAE;IACpB,iDAAiD;IACjD,gCAAgC;IAChC,IACE,CAAC,SAAS;QACV,CAAC,SAAS,CAAC,SAAS;QACpB,CAAC,SAAS,CAAC,SAAS;QACpB,CAAC,SAAS,CAAC,SAAS,CAAC,MAAM,EAC3B,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IACD,MAAM,gBAAgB,GAAG,gBAAgB,CAAC,iBAAiB,CAAC,IAAI,CAC9D,CAAC,OAAO,EAAE,EAAE;QACV,OAAO,OAAO,CAAC,EAAE,KAAK,SAAS,CAAC,SAAS,CAAA;IAC3C,CAAC,CACF,CAAA;IAED,sDAAsD;IACtD,qDAAqD;IACrD,sDAAsD;IACtD,gCAAgC;IAChC,IAAI,CAAC,gBAAgB,EAAE,CAAC;QACtB,IAAI,gBAAgB,CAAC,sBAAsB,EAAE,CAAC;YAC5C,OAAO,kCAAkC,CACvC,gBAAgB,CAAC,sBAAsB,EACvC,SAAS,EACT,iBAAiB,CAClB,CAAA;QACH,CAAC;aAAM,CAAC;YACN,OAAO,MAAM,CAAA;QACf,CAAC;IACH,CAAC;IAED,MAAM,uBAAuB,GAC3B,eAAe,CAAC,YAAY,CAAC,gBAAgB,CAAC,gBAAgB,CAAC,CAAA;IACjE,IAAI,CAAC,uBAAuB,EAAE,CAAC;QAC7B,OAAO,MAAM,CAAA;IACf,CAAC;IACD,kEAAkE;IAClE,4BAA4B;IAC5B,uDAAuD;IACvD,qCAAqC;IACrC,MAAM,iCAAiC,GAAG,CAAC,KAAK,CAAC,OAAO,CACtD,uBAAuB,CAAC,OAAO,CAChC,CAAA;IACD,IAAI,iCAAiC,EAAE,CAAC;QACtC,IAAI,uBAAuB,CAAC,WAAW,KAAK,SAAS,EAAE,CAAC;YACtD,OAAO,4BAA4B,CAAA;QACrC,CAAC;aAAM,CAAC;YACN,OAAO,2BAA2B,CAAA;QACpC,CAAC;IACH,CAAC;IAED,MAAM,oBAAoB,GAAG,SAAS,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,EAAE;QAC5D,MAAM,eAAe,GAAG,uBAAuB,CAAC,OAAO,EAAE,IAAI,CAC3D,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CACnB,CAAA;QACD,IAAI,CAAC,eAAe;YAAE,OAAO,MAAM,CAAA;QAEnC,OAAO,uBAAuB,CAC5B,EAAE,KAAK,EAAE,gBAAgB,CAAC,KAAK,EAAE,iBAAiB,EAAE,EAAE,EAAE,EACxD,uBAAuB,EACvB,eAAe,EACf,iBAAiB,CAClB,CAAA;IACH,CAAC,CAAC,CAAA;IAEF,IAAI,CAAC,oBAAoB,EAAE,CAAC;QAC1B,OAAO,MAAM,CAAA;IACf,CAAC;IAED,4EAA4E;IAC5E,MAAM,UAAU,GAAG,wBAAwB,CACzC,SAAS,EACT,gBAAgB,CAAC,KAAK,EACtB,uBAAuB,CACxB,CAAA;IACD,OAAO,UAAU,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,MAAM,CAAA;AACrC,CAAC,CAAA;AAED,MAAM,sBAAsB,GAAG,CAC7B,gBAAkC,EAClC,SAAiD,EACjD,iBAA2B,EAClB,EAAE;IACX,MAAM,gBAAgB,GAAG,gBAAgB,CAAC,iBAAiB,CAAC,IAAI,CAC9D,CAAC,OAAO,EAAE,EAAE;QACV,OAAO,OAAO,CAAC,EAAE,KAAK,SAAS,CAAC,SAAS,CAAA;IAC3C,CAAC,CACF,CAAA;IAED,sDAAsD;IACtD,qDAAqD;IACrD,sDAAsD;IACtD,gCAAgC;IAChC,IAAI,CAAC,gBAAgB,EAAE,CAAC;QACtB,IAAI,gBAAgB,CAAC,sBAAsB,EAAE,CAAC;YAC5C,OAAO,sBAAsB,CAC3B,gBAAgB,CAAC,sBAAsB,EACvC,SAAS,EACT,iBAAiB,CAClB,CAAA;QACH,CAAC;aAAM,CAAC;YACN,OAAO,KAAK,CAAA;QACd,CAAC;IACH,CAAC;IAED,iFAAiF;IACjF,gBAAgB;IAChB;IACE,wDAAwD;IACxD,gBAAgB,CAAC,IAAI,KAAK,MAAM;QAChC,gBAAgB,CAAC,IAAI,KAAK,SAAS;QACnC,CAAC,wBAAwB,CAAC,gBAAgB,EAAE,gBAAgB,EAAE,EAAE,CAAC,EACjE,CAAC;QACD,OAAO,KAAK,CAAA;IACd,CAAC;IAED,8CAA8C;IAC9C,MAAM,MAAM,GAAG,gBAAgB,CAAC,KAAK,EAAE,CAAC,gBAAgB,CAAC,IAAI,CAAC,CAAA;IAC9D,IAAI,CAAC,MAAM;QAAE,OAAO,KAAK,CAAA;IACzB,iEAAiE;IACjE,IACE,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC;QACrB,CAAC,CAAC,MAAM,CAAC,MAAM;YACb,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,OAAO,KAAK,KAAK,WAAW,CAAC,CAAC,MAAM,CAAC,EACjE,CAAC;QACD,OAAO,KAAK,CAAA;IACd,CAAC;IAED,OAAO,IAAI,CAAA;AACb,CAAC,CAAA;AAED,MAAM,CAAC,OAAO,UAAU,uBAAuB,CAC7C,gBAAkC,EAClC,iBAAmD,EACnD,gBAA+C,EAC/C,gBAA0B;IAE1B,iEAAiE;IACjE,iCAAiC;IAEjC,IACE,CAAC,iBAAiB,CAAC,wBAAwB;QAC3C,CAAC,gBAAgB;QACjB,CAAC,gBAAgB,CAAC,UAAU;QAC5B,CAAC,KAAK,CAAC,OAAO,CAAC,gBAAgB,CAAC,UAAU,CAAC;QAC3C,CAAC,gBAAgB,CAAC,UAAU,CAAC,MAAM,EACnC,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IAED,iEAAiE;IACjE,0EAA0E;IAC1E,IAAI,gBAAgB,CAAC,IAAI,CAAC,CAAC,QAAQ,EAAE,EAAE,CAAC,QAAQ,KAAK,gBAAgB,CAAC,EAAE,CAAC,EAAE,CAAC;QAC1E,MAAM,IAAI,KAAK,CACb,sKAAsK,CACvK,CAAA;IACH,CAAC;SAAM,CAAC;QACN,gBAAgB,CAAC,IAAI,CAAC,gBAAgB,CAAC,EAAE,CAAC,CAAA;IAC5C,CAAC;IACD,MAAM,eAAe,GAAG,CAAC,gBAAgB,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC,MAAM,CAChE,CAAC,SAAS,EAAE,EAAE;QACZ,OAAO,sBAAsB,CAC3B,gBAAgB,EAChB,SAAS,EACT,gBAAgB,CACjB,CAAA;IACH,CAAC,CACF,CAAA;IACD,IAAI,CAAC,eAAe,CAAC,MAAM;QAAE,OAAO,MAAM,CAAA;IAE1C,IAAI,0BAA0B,GAAG,KAAK,CAAA;IACtC,IAAI,yBAAyB,GAAG,KAAK,CAAA;IACrC,MAAM,WAAW,GAAG,KAAK,CAAC,eAAe,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,CAAA;IAC7D,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,eAAe,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE,CAAC;QAChD,MAAM,SAAS,GAAG,eAAe,CAAC,CAAC,CAAC,CAAA;QACpC,MAAM,eAAe,GAAG,kCAAkC,CACxD,gBAAgB,EAChB,SAAS,EACT,gBAAgB,CACjB,CAAA;QACD,QAAQ,eAAe,EAAE,CAAC;YACxB,KAAK,MAAM,CAAC,CAAC,CAAC;gBACZ,IAAI,iBAAiB,CAAC,6CAA6C,EAAE,CAAC;oBACpE,WAAW,CAAC,CAAC,CAAC,GAAG,IAAI,CAAA;oBACrB,MAAK;gBACP,CAAC;gBACD,2BAA2B;gBAC3B,OAAO,MAAM,CAAA;YACf,CAAC;YACD,KAAK,4BAA4B,CAAC,CAAC,CAAC;gBAClC,0BAA0B,GAAG,IAAI,CAAA;gBACjC,MAAK;YACP,CAAC;YACD,KAAK,2BAA2B,CAAC,CAAC,CAAC;gBACjC,yBAAyB,GAAG,IAAI,CAAA;gBAChC,MAAK;YACP,CAAC;QACH,CAAC;IACH,CAAC;IACD,IACE,iBAAiB,CAAC,6CAA6C;QAC/D,WAAW,CAAC,KAAK,CAAC,CAAC,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,EACrC,CAAC;QACD,OAAO,MAAM,CAAA;IACf,CAAC;IACD,IAAI,0BAA0B,EAAE,CAAC;QAC/B,OAAO,4BAA4B,CAAA;IACrC,CAAC;SAAM,IAAI,yBAAyB,EAAE,CAAC;QACrC,OAAO,2BAA2B,CAAA;IACpC,CAAC;SAAM,CAAC;QACN,OAAO,MAAM,CAAA;IACf,CAAC;AACH,CAAC","sourcesContent":["import { FormTypes, SubmissionTypes } from '@oneblink/types'\nimport evaluateConditionalOptionsPredicate from './evaluateConditionalOptionsPredicate.js'\nimport { FormElementsCtrl } from './types.js'\nimport { typeCastService } from '../index.js'\nimport conditionallyShowElement from './conditionallyShowElement.js'\n\nexport type ShouldShowOption =\n | 'SHOW'\n | 'HIDE'\n | 'LOADING_DYNAMIC_DEPENDENCY'\n | 'LOADING_STATIC_DEPENDENCY'\n\nconst handleAttributePredicate = (\n predicate: FormTypes.ChoiceElementOptionAttribute,\n model: SubmissionTypes.S3SubmissionData['submission'] | undefined,\n predicateElement: FormTypes.FormElementWithOptions,\n) => {\n const values = model?.[predicateElement.name]\n if (!values) return true\n\n if (\n Array.isArray(values) &&\n (!values.length ||\n !values.filter((value) => typeof value !== 'undefined').length)\n ) {\n return true\n }\n\n return evaluateConditionalOptionsPredicate({\n predicate: {\n type: 'OPTIONS',\n elementId: predicate.elementId,\n optionIds: predicate.optionIds,\n },\n predicateValue: values,\n predicateElement,\n })\n}\n\nconst conditionallyShowOptionByPredicate = (\n formElementsCtrl: FormElementsCtrl,\n predicate: FormTypes.ChoiceElementOptionAttribute,\n elementsEvaluated: string[],\n): ShouldShowOption => {\n // Validate the predicate data, if it is invalid,\n // we will always show the field\n if (\n !predicate ||\n !predicate.elementId ||\n !predicate.optionIds ||\n !predicate.optionIds.length\n ) {\n return 'SHOW'\n }\n const predicateElement = formElementsCtrl.flattenedElements.find(\n (element) => {\n return element.id === predicate.elementId\n },\n )\n\n // If we cant find the element used for the predicate,\n // we can check to see if the element being evaluated\n // is in a repeatable set and the predicate element is\n // in a parent list of elements.\n if (!predicateElement) {\n if (formElementsCtrl.parentFormElementsCtrl) {\n return conditionallyShowOptionByPredicate(\n formElementsCtrl.parentFormElementsCtrl,\n predicate,\n elementsEvaluated,\n )\n } else {\n return 'HIDE'\n }\n }\n\n const optionsPredicateElement =\n typeCastService.formElements.toOptionsElement(predicateElement)\n if (!optionsPredicateElement) {\n return 'HIDE'\n }\n // If the predicate element does not have any options to evaluate,\n // we will show the element.\n // Unless the predicate element has dynamic options and\n // options have not been fetched yet.\n const isLoadingPredicateElementsOptions = !Array.isArray(\n optionsPredicateElement.options,\n )\n if (isLoadingPredicateElementsOptions) {\n if (optionsPredicateElement.optionsType === 'DYNAMIC') {\n return 'LOADING_DYNAMIC_DEPENDENCY'\n } else {\n return 'LOADING_STATIC_DEPENDENCY'\n }\n }\n\n const everyOptionIsShowing = predicate.optionIds.every((id) => {\n const predicateOption = optionsPredicateElement.options?.find(\n (o) => o.id === id,\n )\n if (!predicateOption) return 'HIDE'\n\n return conditionallyShowOption(\n { model: formElementsCtrl.model, flattenedElements: [] },\n optionsPredicateElement,\n predicateOption,\n elementsEvaluated,\n )\n })\n\n if (!everyOptionIsShowing) {\n return 'HIDE'\n }\n\n // Check to see if the model has one of the valid values to show the element\n const shouldShow = handleAttributePredicate(\n predicate,\n formElementsCtrl.model,\n optionsPredicateElement,\n )\n return shouldShow ? 'SHOW' : 'HIDE'\n}\n\nconst isAttributeFilterValid = (\n formElementsCtrl: FormElementsCtrl,\n predicate: FormTypes.ChoiceElementOptionAttribute,\n elementsEvaluated: string[],\n): boolean => {\n const predicateElement = formElementsCtrl.flattenedElements.find(\n (element) => {\n return element.id === predicate.elementId\n },\n )\n\n // If we cant find the element used for the predicate,\n // we can check to see if the element being evaluated\n // is in a repeatable set and the predicate element is\n // in a parent list of elements.\n if (!predicateElement) {\n if (formElementsCtrl.parentFormElementsCtrl) {\n return isAttributeFilterValid(\n formElementsCtrl.parentFormElementsCtrl,\n predicate,\n elementsEvaluated,\n )\n } else {\n return false\n }\n }\n\n // now we have the model and predicate element, verify that the predicate element\n // is not hidden\n if (\n // Will never be a page, just making typescript happy :)\n predicateElement.type === 'page' ||\n predicateElement.type === 'section' ||\n !conditionallyShowElement(formElementsCtrl, predicateElement, [])\n ) {\n return false\n }\n\n // verify that at least one option is selected\n const values = formElementsCtrl.model?.[predicateElement.name]\n if (!values) return false\n // if the model value is an array, verify that it has a selection\n if (\n Array.isArray(values) &&\n (!values.length ||\n !values.filter((value) => typeof value !== 'undefined').length)\n ) {\n return false\n }\n\n return true\n}\n\nexport default function conditionallyShowOption(\n formElementsCtrl: FormElementsCtrl,\n elementToEvaluate: FormTypes.FormElementWithOptions,\n optionToEvaluate: FormTypes.ChoiceElementOption,\n optionsEvaluated: string[],\n): ShouldShowOption {\n // If the element does not have the `conditionallyShow` flag set,\n // we can always show the option.\n\n if (\n !elementToEvaluate.conditionallyShowOptions ||\n !optionToEvaluate ||\n !optionToEvaluate.attributes ||\n !Array.isArray(optionToEvaluate.attributes) ||\n !optionToEvaluate.attributes.length\n ) {\n return 'SHOW'\n }\n\n // Check to see if this element has already been used to evaluate\n // if the option should be shown based on parent element conditional logic\n if (optionsEvaluated.some((optionId) => optionId === optionToEvaluate.id)) {\n throw new Error(\n 'Your conditional logic has caused an infinite loop. Check the following Fields to ensure element A does not rely on element B if element B also relies on element A.',\n )\n } else {\n optionsEvaluated.push(optionToEvaluate.id)\n }\n const validPredicates = (optionToEvaluate.attributes || []).filter(\n (predicate) => {\n return isAttributeFilterValid(\n formElementsCtrl,\n predicate,\n optionsEvaluated,\n )\n },\n )\n if (!validPredicates.length) return 'SHOW'\n\n let isLoadingDynamicDEPENDENCY = false\n let isLoadingStaticDEPENDENCY = false\n const showResults = Array(validPredicates.length).fill(false)\n for (let i = 0; i < validPredicates.length; i++) {\n const predicate = validPredicates[i]\n const predicateResult = conditionallyShowOptionByPredicate(\n formElementsCtrl,\n predicate,\n optionsEvaluated,\n )\n switch (predicateResult) {\n case 'SHOW': {\n if (elementToEvaluate.requiresAllConditionallyShowOptionsPredicates) {\n showResults[i] = true\n break\n }\n // if match any return show\n return 'SHOW'\n }\n case 'LOADING_DYNAMIC_DEPENDENCY': {\n isLoadingDynamicDEPENDENCY = true\n break\n }\n case 'LOADING_STATIC_DEPENDENCY': {\n isLoadingStaticDEPENDENCY = true\n break\n }\n }\n }\n if (\n elementToEvaluate.requiresAllConditionallyShowOptionsPredicates &&\n showResults.every((result) => result)\n ) {\n return 'SHOW'\n }\n if (isLoadingDynamicDEPENDENCY) {\n return 'LOADING_DYNAMIC_DEPENDENCY'\n } else if (isLoadingStaticDEPENDENCY) {\n return 'LOADING_STATIC_DEPENDENCY'\n } else {\n return 'HIDE'\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"conditionallyShowOption.js","sourceRoot":"","sources":["../../src/conditionalLogicService/conditionallyShowOption.ts"],"names":[],"mappings":"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","sourcesContent":["import { FormTypes, SubmissionTypes } from '@oneblink/types'\nimport evaluateConditionalOptionsPredicate from './evaluateConditionalOptionsPredicate.js'\nimport { FormElementsCtrl } from './types.js'\nimport { typeCastService } from '../index.js'\nimport conditionallyShowElement from './conditionallyShowElement.js'\n\nexport type ShouldShowOption =\n | 'SHOW'\n | 'HIDE'\n | 'LOADING_DYNAMIC_DEPENDENCY'\n | 'LOADING_STATIC_DEPENDENCY'\n\nconst handleAttributePredicate = ({\n predicate,\n model,\n predicateElement,\n}: {\n predicate: FormTypes.ChoiceElementOptionAttribute\n model: SubmissionTypes.S3SubmissionData['submission'] | undefined\n predicateElement: FormTypes.FormElementWithOptions\n}) => {\n const values = model?.[predicateElement.name]\n if (!values) return true\n\n if (\n Array.isArray(values) &&\n (!values.length ||\n !values.filter((value) => typeof value !== 'undefined').length)\n ) {\n return true\n }\n\n return evaluateConditionalOptionsPredicate({\n predicate: {\n type: 'OPTIONS',\n elementId: predicate.elementId,\n optionIds: predicate.optionIds,\n },\n predicateValue: values,\n predicateElement,\n })\n}\n\nconst conditionallyShowOptionByPredicate = ({\n formElementsCtrl,\n predicate,\n elementsEvaluated,\n}: {\n formElementsCtrl: FormElementsCtrl\n predicate: FormTypes.ChoiceElementOptionAttribute\n elementsEvaluated: string[]\n}): ShouldShowOption => {\n // Validate the predicate data, if it is invalid,\n // we will always show the field\n if (\n !predicate ||\n !predicate.elementId ||\n !predicate.optionIds ||\n !predicate.optionIds.length\n ) {\n return 'SHOW'\n }\n const predicateElement = formElementsCtrl.flattenedElements.find(\n (element) => {\n return element.id === predicate.elementId\n },\n )\n\n // If we cant find the element used for the predicate,\n // we can check to see if the element being evaluated\n // is in a repeatable set and the predicate element is\n // in a parent list of elements.\n if (!predicateElement) {\n if (formElementsCtrl.parentFormElementsCtrl) {\n return conditionallyShowOptionByPredicate({\n formElementsCtrl: formElementsCtrl.parentFormElementsCtrl,\n predicate,\n elementsEvaluated,\n })\n } else {\n return 'HIDE'\n }\n }\n\n const optionsPredicateElement =\n typeCastService.formElements.toOptionsElement(predicateElement)\n if (!optionsPredicateElement) {\n return 'HIDE'\n }\n // If the predicate element does not have any options to evaluate,\n // we will show the element.\n // Unless the predicate element has dynamic options and\n // options have not been fetched yet.\n const isLoadingPredicateElementsOptions = !Array.isArray(\n optionsPredicateElement.options,\n )\n if (isLoadingPredicateElementsOptions) {\n if (optionsPredicateElement.optionsType === 'DYNAMIC') {\n return 'LOADING_DYNAMIC_DEPENDENCY'\n } else {\n return 'LOADING_STATIC_DEPENDENCY'\n }\n }\n\n const everyOptionIsShowing = predicate.optionIds.every((id) => {\n const predicateOption = optionsPredicateElement.options?.find(\n (o) => o.id === id,\n )\n if (!predicateOption) return 'HIDE'\n\n return conditionallyShowOption({\n formElementsCtrl: {\n model: formElementsCtrl.model,\n flattenedElements: [],\n },\n elementToEvaluate: optionsPredicateElement,\n optionToEvaluate: predicateOption,\n optionsEvaluated: elementsEvaluated,\n })\n })\n\n if (!everyOptionIsShowing) {\n return 'HIDE'\n }\n\n // Check to see if the model has one of the valid values to show the element\n const shouldShow = handleAttributePredicate({\n predicate,\n model: formElementsCtrl.model,\n predicateElement: optionsPredicateElement,\n })\n return shouldShow ? 'SHOW' : 'HIDE'\n}\n\nconst isAttributeFilterValid = ({\n formElementsCtrl,\n predicate,\n elementsEvaluated,\n}: {\n formElementsCtrl: FormElementsCtrl\n predicate: FormTypes.ChoiceElementOptionAttribute\n elementsEvaluated: string[]\n}): boolean => {\n const predicateElement = formElementsCtrl.flattenedElements.find(\n (element) => {\n return element.id === predicate.elementId\n },\n )\n\n // If we cant find the element used for the predicate,\n // we can check to see if the element being evaluated\n // is in a repeatable set and the predicate element is\n // in a parent list of elements.\n if (!predicateElement) {\n if (formElementsCtrl.parentFormElementsCtrl) {\n return isAttributeFilterValid({\n formElementsCtrl: formElementsCtrl.parentFormElementsCtrl,\n predicate,\n elementsEvaluated,\n })\n } else {\n return false\n }\n }\n\n // now we have the model and predicate element, verify that the predicate element\n // is not hidden\n if (\n // Will never be a page, just making typescript happy :)\n predicateElement.type === 'page' ||\n predicateElement.type === 'section' ||\n !conditionallyShowElement({\n formElementsCtrl,\n elementToEvaluate: predicateElement,\n elementsEvaluated: [],\n })\n ) {\n return false\n }\n\n // verify that at least one option is selected\n const values = formElementsCtrl.model?.[predicateElement.name]\n if (!values) return false\n // if the model value is an array, verify that it has a selection\n if (\n Array.isArray(values) &&\n (!values.length ||\n !values.filter((value) => typeof value !== 'undefined').length)\n ) {\n return false\n }\n\n return true\n}\n\nexport default function conditionallyShowOption({\n formElementsCtrl,\n elementToEvaluate,\n optionToEvaluate,\n optionsEvaluated,\n}: {\n formElementsCtrl: FormElementsCtrl\n elementToEvaluate: FormTypes.FormElementWithOptions\n optionToEvaluate: FormTypes.ChoiceElementOption\n optionsEvaluated: string[]\n}): ShouldShowOption {\n // If the element does not have the `conditionallyShow` flag set,\n // we can always show the option.\n\n if (\n !elementToEvaluate.conditionallyShowOptions ||\n !optionToEvaluate ||\n !optionToEvaluate.attributes ||\n !Array.isArray(optionToEvaluate.attributes) ||\n !optionToEvaluate.attributes.length\n ) {\n return 'SHOW'\n }\n\n // Check to see if this element has already been used to evaluate\n // if the option should be shown based on parent element conditional logic\n if (optionsEvaluated.some((optionId) => optionId === optionToEvaluate.id)) {\n throw new Error(\n 'Your conditional logic has caused an infinite loop. Check the following Fields to ensure element A does not rely on element B if element B also relies on element A.',\n )\n } else {\n optionsEvaluated.push(optionToEvaluate.id)\n }\n const validPredicates = (optionToEvaluate.attributes || []).filter(\n (predicate) => {\n return isAttributeFilterValid({\n formElementsCtrl,\n predicate,\n elementsEvaluated: optionsEvaluated,\n })\n },\n )\n if (!validPredicates.length) return 'SHOW'\n\n let isLoadingDynamicDEPENDENCY = false\n let isLoadingStaticDEPENDENCY = false\n const showResults = Array(validPredicates.length).fill(false)\n for (let i = 0; i < validPredicates.length; i++) {\n const predicate = validPredicates[i]\n const predicateResult = conditionallyShowOptionByPredicate({\n formElementsCtrl,\n predicate,\n elementsEvaluated: optionsEvaluated,\n })\n switch (predicateResult) {\n case 'SHOW': {\n if (elementToEvaluate.requiresAllConditionallyShowOptionsPredicates) {\n showResults[i] = true\n break\n }\n // if match any return show\n return 'SHOW'\n }\n case 'LOADING_DYNAMIC_DEPENDENCY': {\n isLoadingDynamicDEPENDENCY = true\n break\n }\n case 'LOADING_STATIC_DEPENDENCY': {\n isLoadingStaticDEPENDENCY = true\n break\n }\n }\n }\n if (\n elementToEvaluate.requiresAllConditionallyShowOptionsPredicates &&\n showResults.every((result) => result)\n ) {\n return 'SHOW'\n }\n if (isLoadingDynamicDEPENDENCY) {\n return 'LOADING_DYNAMIC_DEPENDENCY'\n } else if (isLoadingStaticDEPENDENCY) {\n return 'LOADING_STATIC_DEPENDENCY'\n } else {\n return 'HIDE'\n }\n}\n"]}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { ConditionTypes } from '@oneblink/types';
|
|
2
|
+
import { AddOffsetToDate, FormElementsCtrl, ParseDate } from './types.js';
|
|
3
|
+
/**
|
|
4
|
+
* Evaluate a `SUBMISSION_TIMESTAMP` conditional predicate against the form
|
|
5
|
+
* submission timestamp.
|
|
6
|
+
*
|
|
7
|
+
* - `AFTER` — submission timestamp is after (exclusive) the comparison date
|
|
8
|
+
* - `BEFORE` — submission timestamp is before (exclusive) the comparison date
|
|
9
|
+
* - `BETWEEN` — submission timestamp is between `min` and `max` (inclusive)
|
|
10
|
+
*
|
|
11
|
+
* Date strings are parsed via `parseDate`. Day offsets are applied via
|
|
12
|
+
* `addDaysToDate(date, offset)`.
|
|
13
|
+
*/
|
|
14
|
+
export default function evaluateConditionalSubmissionTimestampPredicate({ predicate, formElementsCtrl, submissionTimestamp, parseDate, addDaysToDate, }: {
|
|
15
|
+
predicate: ConditionTypes.ConditionalPredicateSubmissionTimestamp;
|
|
16
|
+
formElementsCtrl: FormElementsCtrl;
|
|
17
|
+
submissionTimestamp: string;
|
|
18
|
+
parseDate: ParseDate;
|
|
19
|
+
addDaysToDate: AddOffsetToDate;
|
|
20
|
+
}): boolean;
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
import { getElementAndValue } from './evaluateFormElementConditionalPredicate.js';
|
|
2
|
+
function resolveDateValue(dateValue, formElementsCtrl, parseDate, addDaysToDate) {
|
|
3
|
+
let dateString;
|
|
4
|
+
if (dateValue.compareWith === 'ELEMENT') {
|
|
5
|
+
const elementAndValue = getElementAndValue(formElementsCtrl, dateValue.elementId);
|
|
6
|
+
if (typeof elementAndValue.value === 'string' && elementAndValue.value) {
|
|
7
|
+
dateString = elementAndValue.value;
|
|
8
|
+
}
|
|
9
|
+
if (!dateString) {
|
|
10
|
+
return undefined;
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
else {
|
|
14
|
+
dateString = dateValue.value;
|
|
15
|
+
}
|
|
16
|
+
const date = parseDate(dateString);
|
|
17
|
+
if (Number.isNaN(date.getTime())) {
|
|
18
|
+
return undefined;
|
|
19
|
+
}
|
|
20
|
+
if (typeof dateValue.daysOffset !== 'number' ||
|
|
21
|
+
Number.isNaN(dateValue.daysOffset)) {
|
|
22
|
+
return date;
|
|
23
|
+
}
|
|
24
|
+
return addDaysToDate(date, dateValue.daysOffset);
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Evaluate a `SUBMISSION_TIMESTAMP` conditional predicate against the form
|
|
28
|
+
* submission timestamp.
|
|
29
|
+
*
|
|
30
|
+
* - `AFTER` — submission timestamp is after (exclusive) the comparison date
|
|
31
|
+
* - `BEFORE` — submission timestamp is before (exclusive) the comparison date
|
|
32
|
+
* - `BETWEEN` — submission timestamp is between `min` and `max` (inclusive)
|
|
33
|
+
*
|
|
34
|
+
* Date strings are parsed via `parseDate`. Day offsets are applied via
|
|
35
|
+
* `addDaysToDate(date, offset)`.
|
|
36
|
+
*/
|
|
37
|
+
export default function evaluateConditionalSubmissionTimestampPredicate({ predicate, formElementsCtrl, submissionTimestamp, parseDate, addDaysToDate, }) {
|
|
38
|
+
const submissionDate = new Date(submissionTimestamp);
|
|
39
|
+
if (Number.isNaN(submissionDate.getTime())) {
|
|
40
|
+
return false;
|
|
41
|
+
}
|
|
42
|
+
const submissionTime = submissionDate.getTime();
|
|
43
|
+
switch (predicate.operator) {
|
|
44
|
+
case 'BETWEEN': {
|
|
45
|
+
const min = resolveDateValue(predicate.min, formElementsCtrl, parseDate, addDaysToDate);
|
|
46
|
+
const max = resolveDateValue(predicate.max, formElementsCtrl, parseDate, addDaysToDate);
|
|
47
|
+
if (!min || !max) {
|
|
48
|
+
return false;
|
|
49
|
+
}
|
|
50
|
+
return submissionTime >= min.getTime() && submissionTime <= max.getTime();
|
|
51
|
+
}
|
|
52
|
+
default: {
|
|
53
|
+
const compareDate = resolveDateValue(predicate, formElementsCtrl, parseDate, addDaysToDate);
|
|
54
|
+
if (!compareDate) {
|
|
55
|
+
return false;
|
|
56
|
+
}
|
|
57
|
+
switch (predicate.operator) {
|
|
58
|
+
case 'AFTER':
|
|
59
|
+
return submissionTime > compareDate.getTime();
|
|
60
|
+
case 'BEFORE':
|
|
61
|
+
return submissionTime < compareDate.getTime();
|
|
62
|
+
default: {
|
|
63
|
+
const n = predicate;
|
|
64
|
+
console.warn('Unhandled predicate operator', n);
|
|
65
|
+
return false;
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
//# sourceMappingURL=evaluateConditionalSubmissionTimestampPredicate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"evaluateConditionalSubmissionTimestampPredicate.js","sourceRoot":"","sources":["../../src/conditionalLogicService/evaluateConditionalSubmissionTimestampPredicate.ts"],"names":[],"mappings":"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","sourcesContent":["import { ConditionTypes } from '@oneblink/types'\nimport { AddOffsetToDate, FormElementsCtrl, ParseDate } from './types.js'\nimport { getElementAndValue } from './evaluateFormElementConditionalPredicate.js'\n\nfunction resolveDateValue(\n dateValue: ConditionTypes.ConditionalPredicateDateValue,\n formElementsCtrl: FormElementsCtrl,\n parseDate: ParseDate,\n addDaysToDate: AddOffsetToDate,\n): Date | undefined {\n let dateString: string | undefined\n\n if (dateValue.compareWith === 'ELEMENT') {\n const elementAndValue = getElementAndValue(\n formElementsCtrl,\n dateValue.elementId,\n )\n if (typeof elementAndValue.value === 'string' && elementAndValue.value) {\n dateString = elementAndValue.value\n }\n if (!dateString) {\n return undefined\n }\n } else {\n dateString = dateValue.value\n }\n\n const date = parseDate(dateString)\n if (Number.isNaN(date.getTime())) {\n return undefined\n }\n\n if (\n typeof dateValue.daysOffset !== 'number' ||\n Number.isNaN(dateValue.daysOffset)\n ) {\n return date\n }\n\n return addDaysToDate(date, dateValue.daysOffset)\n}\n\n/**\n * Evaluate a `SUBMISSION_TIMESTAMP` conditional predicate against the form\n * submission timestamp.\n *\n * - `AFTER` — submission timestamp is after (exclusive) the comparison date\n * - `BEFORE` — submission timestamp is before (exclusive) the comparison date\n * - `BETWEEN` — submission timestamp is between `min` and `max` (inclusive)\n *\n * Date strings are parsed via `parseDate`. Day offsets are applied via\n * `addDaysToDate(date, offset)`.\n */\nexport default function evaluateConditionalSubmissionTimestampPredicate({\n predicate,\n formElementsCtrl,\n submissionTimestamp,\n parseDate,\n addDaysToDate,\n}: {\n predicate: ConditionTypes.ConditionalPredicateSubmissionTimestamp\n formElementsCtrl: FormElementsCtrl\n submissionTimestamp: string\n parseDate: ParseDate\n addDaysToDate: AddOffsetToDate\n}): boolean {\n const submissionDate = new Date(submissionTimestamp)\n if (Number.isNaN(submissionDate.getTime())) {\n return false\n }\n\n const submissionTime = submissionDate.getTime()\n\n switch (predicate.operator) {\n case 'BETWEEN': {\n const min = resolveDateValue(\n predicate.min,\n formElementsCtrl,\n parseDate,\n addDaysToDate,\n )\n const max = resolveDateValue(\n predicate.max,\n formElementsCtrl,\n parseDate,\n addDaysToDate,\n )\n if (!min || !max) {\n return false\n }\n return submissionTime >= min.getTime() && submissionTime <= max.getTime()\n }\n default: {\n const compareDate = resolveDateValue(\n predicate,\n formElementsCtrl,\n parseDate,\n addDaysToDate,\n )\n if (!compareDate) {\n return false\n }\n\n switch (predicate.operator) {\n case 'AFTER':\n return submissionTime > compareDate.getTime()\n case 'BEFORE':\n return submissionTime < compareDate.getTime()\n default: {\n const n: never = predicate\n console.warn('Unhandled predicate operator', n)\n return false\n }\n }\n }\n }\n}\n"]}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { ConditionTypes, FormTypes } from '@oneblink/types';
|
|
2
|
+
import { FormElementsCtrl } from './types.js';
|
|
3
|
+
export declare function getElementAndValue(formElementsCtrl: FormElementsCtrl, elementId: string): {
|
|
4
|
+
formElementWithName?: FormTypes.FormElementWithName;
|
|
5
|
+
value?: unknown;
|
|
6
|
+
};
|
|
7
|
+
/**
|
|
8
|
+
* Evaluate an element-based conditional predicate. When the predicate is
|
|
9
|
+
* satisfied, returns the predicate form element so callers can also check
|
|
10
|
+
* whether that element (and its parents) are themselves shown.
|
|
11
|
+
*/
|
|
12
|
+
export default function evaluateFormElementConditionalPredicate({ predicate, formElementsCtrl, }: {
|
|
13
|
+
predicate: ConditionTypes.FormElementConditionalPredicate;
|
|
14
|
+
formElementsCtrl: FormElementsCtrl;
|
|
15
|
+
}): FormTypes.FormElementWithName | undefined;
|
|
@@ -10,7 +10,7 @@ const fnMap = {
|
|
|
10
10
|
'<=': (lhs, rhs) => lhs <= rhs,
|
|
11
11
|
'<': (lhs, rhs) => lhs < rhs,
|
|
12
12
|
};
|
|
13
|
-
function getElementAndValue(formElementsCtrl, elementId) {
|
|
13
|
+
export function getElementAndValue(formElementsCtrl, elementId) {
|
|
14
14
|
const formElement = formElementsCtrl.flattenedElements.find((formElement) => formElement.id === elementId);
|
|
15
15
|
if (formElement) {
|
|
16
16
|
const formElementWithName = typeCastService.formElements.toNamedElement(formElement);
|
|
@@ -26,7 +26,12 @@ function getElementAndValue(formElementsCtrl, elementId) {
|
|
|
26
26
|
}
|
|
27
27
|
return {};
|
|
28
28
|
}
|
|
29
|
-
|
|
29
|
+
/**
|
|
30
|
+
* Evaluate an element-based conditional predicate. When the predicate is
|
|
31
|
+
* satisfied, returns the predicate form element so callers can also check
|
|
32
|
+
* whether that element (and its parents) are themselves shown.
|
|
33
|
+
*/
|
|
34
|
+
export default function evaluateFormElementConditionalPredicate({ predicate, formElementsCtrl, }) {
|
|
30
35
|
const { formElementWithName: predicateElement, value: predicateValue } = getElementAndValue(formElementsCtrl, predicate.elementId);
|
|
31
36
|
if (!predicateElement) {
|
|
32
37
|
return;
|
|
@@ -93,10 +98,14 @@ export default function evaluateConditionalPredicate({ predicate, formElementsCt
|
|
|
93
98
|
}
|
|
94
99
|
for (const entry of repeatableSetValue) {
|
|
95
100
|
const result = conditionallyShowByPredicate({
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
101
|
+
formElementsCtrl: {
|
|
102
|
+
model: entry,
|
|
103
|
+
flattenedElements: formElementsService.flattenFormElements(repeatableSetElement.elements),
|
|
104
|
+
parentFormElementsCtrl: formElementsCtrl,
|
|
105
|
+
},
|
|
106
|
+
predicate: predicate.repeatableSetPredicate,
|
|
107
|
+
elementsEvaluated: [],
|
|
108
|
+
});
|
|
100
109
|
if (result) {
|
|
101
110
|
return predicateElement;
|
|
102
111
|
}
|
|
@@ -112,10 +121,14 @@ export default function evaluateConditionalPredicate({ predicate, formElementsCt
|
|
|
112
121
|
}
|
|
113
122
|
const formModel = formElementsCtrl.model?.[predicateElement.name];
|
|
114
123
|
const result = conditionallyShowByPredicate({
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
124
|
+
formElementsCtrl: {
|
|
125
|
+
model: formModel,
|
|
126
|
+
flattenedElements: flattenFormElements(predicateElement.elements),
|
|
127
|
+
parentFormElementsCtrl: formElementsCtrl,
|
|
128
|
+
},
|
|
129
|
+
predicate: predicate.predicate,
|
|
130
|
+
elementsEvaluated: [],
|
|
131
|
+
});
|
|
119
132
|
if (result) {
|
|
120
133
|
return predicateElement;
|
|
121
134
|
}
|
|
@@ -205,7 +218,7 @@ export default function evaluateConditionalPredicate({ predicate, formElementsCt
|
|
|
205
218
|
break;
|
|
206
219
|
}
|
|
207
220
|
case 'OPTIONS':
|
|
208
|
-
|
|
221
|
+
case undefined: {
|
|
209
222
|
const optionsPredicateElement = typeCastService.formElements.toOptionsElement(predicateElement);
|
|
210
223
|
if (!optionsPredicateElement) {
|
|
211
224
|
return undefined;
|
|
@@ -231,4 +244,4 @@ export default function evaluateConditionalPredicate({ predicate, formElementsCt
|
|
|
231
244
|
}
|
|
232
245
|
}
|
|
233
246
|
}
|
|
234
|
-
//# sourceMappingURL=
|
|
247
|
+
//# sourceMappingURL=evaluateFormElementConditionalPredicate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"evaluateFormElementConditionalPredicate.js","sourceRoot":"","sources":["../../src/conditionalLogicService/evaluateFormElementConditionalPredicate.ts"],"names":[],"mappings":"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","sourcesContent":["import { ConditionTypes, FormTypes, SubmissionTypes } from '@oneblink/types'\nimport { FormElementsCtrl } from './types.js'\nimport { typeCastService, formElementsService } from '../index.js'\nimport evaluateConditionalOptionsPredicate from './evaluateConditionalOptionsPredicate.js'\nimport { conditionallyShowByPredicate } from './conditionallyShowElement.js'\nimport { flattenFormElements } from '../formElementsService.js'\n\nconst fnMap = {\n '>': (lhs: number, rhs: number) => lhs > rhs,\n '>=': (lhs: number, rhs: number) => lhs >= rhs,\n '===': (lhs: number, rhs: number) => lhs === rhs,\n '!==': (lhs: number, rhs: number) => lhs !== rhs,\n '<=': (lhs: number, rhs: number) => lhs <= rhs,\n '<': (lhs: number, rhs: number) => lhs < rhs,\n}\n\nexport function getElementAndValue(\n formElementsCtrl: FormElementsCtrl,\n elementId: string,\n): { formElementWithName?: FormTypes.FormElementWithName; value?: unknown } {\n const formElement = formElementsCtrl.flattenedElements.find(\n (formElement) => formElement.id === elementId,\n )\n if (formElement) {\n const formElementWithName =\n typeCastService.formElements.toNamedElement(formElement)\n if (formElementWithName) {\n return {\n formElementWithName,\n value: formElementsCtrl.model?.[formElementWithName.name],\n }\n }\n } else if (formElementsCtrl.parentFormElementsCtrl) {\n return getElementAndValue(\n formElementsCtrl.parentFormElementsCtrl,\n elementId,\n )\n }\n return {}\n}\n\n/**\n * Evaluate an element-based conditional predicate. When the predicate is\n * satisfied, returns the predicate form element so callers can also check\n * whether that element (and its parents) are themselves shown.\n */\nexport default function evaluateFormElementConditionalPredicate({\n predicate,\n formElementsCtrl,\n}: {\n predicate: ConditionTypes.FormElementConditionalPredicate\n formElementsCtrl: FormElementsCtrl\n}): FormTypes.FormElementWithName | undefined {\n const { formElementWithName: predicateElement, value: predicateValue } =\n getElementAndValue(formElementsCtrl, predicate.elementId)\n if (!predicateElement) {\n return\n }\n switch (predicate.type) {\n case 'VALUE': {\n if (Array.isArray(predicateValue)) {\n return !predicate.hasValue === !predicateValue.length\n ? predicateElement\n : undefined\n }\n return !predicate.hasValue === !predicateValue\n ? predicateElement\n : undefined\n }\n case 'NUMERIC': {\n // if the operator fn doesn't exist, hide the control\n const operatorFn = fnMap[predicate.operator]\n if (!operatorFn) return undefined\n\n const lhs = Number.parseFloat(predicateValue as string)\n // if left is not a number, hide the control\n if (isNaN(lhs)) return undefined\n\n let rhsValue = NaN\n switch (predicate.compareWith) {\n case 'ELEMENT': {\n const { value: comparisonValue } = getElementAndValue(\n formElementsCtrl,\n predicate.value,\n )\n rhsValue =\n comparisonValue === 'string'\n ? Number.parseFloat(comparisonValue)\n : (comparisonValue as number)\n break\n }\n case 'VALUE':\n default: {\n rhsValue = predicate.value\n break\n }\n }\n\n const rhs =\n typeof rhsValue === 'string' ? Number.parseFloat(rhsValue) : rhsValue\n\n // if right is not a number, hide the control\n if (isNaN(rhs)) return undefined\n\n return operatorFn(lhs, rhs) ? predicateElement : undefined\n }\n case 'BETWEEN': {\n const value = Number.parseFloat(predicateValue as string)\n if (Number.isNaN(value)) {\n return undefined\n }\n\n return value >= predicate.min && value <= predicate.max\n ? predicateElement\n : undefined\n }\n case 'REPEATABLESET': {\n const {\n formElementWithName: repeatableSetElement,\n value: repeatableSetValue,\n } = getElementAndValue(formElementsCtrl, predicate.elementId)\n\n if (!repeatableSetElement) {\n return\n }\n\n if (\n repeatableSetElement.type !== 'repeatableSet' ||\n !Array.isArray(repeatableSetValue)\n ) {\n return\n }\n\n for (const entry of repeatableSetValue) {\n const result = conditionallyShowByPredicate({\n formElementsCtrl: {\n model: entry,\n flattenedElements: formElementsService.flattenFormElements(\n repeatableSetElement.elements,\n ),\n parentFormElementsCtrl: formElementsCtrl,\n },\n predicate: predicate.repeatableSetPredicate,\n elementsEvaluated: [],\n })\n\n if (result) {\n return predicateElement\n }\n }\n return\n }\n case 'FORM':\n if (predicate.predicate) {\n if (\n !predicateElement ||\n predicateElement.type !== 'form' ||\n !predicateElement.elements\n ) {\n return\n }\n const formModel = formElementsCtrl.model?.[predicateElement.name] as\n | SubmissionTypes.S3SubmissionData['submission']\n | undefined\n\n const result = conditionallyShowByPredicate({\n formElementsCtrl: {\n model: formModel,\n flattenedElements: flattenFormElements(predicateElement.elements),\n parentFormElementsCtrl: formElementsCtrl,\n },\n predicate: predicate.predicate,\n elementsEvaluated: [],\n })\n\n if (result) {\n return predicateElement\n }\n }\n return\n case 'ADDRESS_PROPERTY': {\n // Only element types that should work as predicate element should be Point, Point V3 or Geoscape.\n if (\n predicateElement.type === 'pointAddress' ||\n predicateElement.type === 'geoscapeAddress' ||\n predicateElement.type === 'pointAddressV3'\n ) {\n if (predicateValue && typeof predicateValue === 'object') {\n if (predicate.definition.property === 'STATE_EQUALITY') {\n switch (predicateElement.type) {\n case 'pointAddressV3': {\n if (\n 'properties' in predicateValue &&\n predicateValue.properties &&\n typeof predicateValue.properties === 'object' &&\n 'stateTerritory' in predicateValue.properties &&\n typeof predicateValue.properties.stateTerritory === 'string'\n ) {\n // Validate that it has the properties we want, in case submission data\n // is incorrect but has the right element reference.\n const result =\n predicateValue.properties.stateTerritory ===\n predicate.definition.value\n if (result) {\n return predicateElement\n }\n return\n }\n break\n }\n case 'geoscapeAddress':\n case 'pointAddress': {\n // Validate that it has the properties we want, in case submission data\n // is incorrect but has the right element reference.\n if (\n 'addressDetails' in predicateValue &&\n predicateValue.addressDetails &&\n typeof predicateValue.addressDetails === 'object' &&\n 'stateTerritory' in predicateValue.addressDetails &&\n typeof predicateValue.addressDetails.stateTerritory ===\n 'string'\n ) {\n const result =\n predicateValue.addressDetails.stateTerritory ===\n predicate.definition.value\n if (result) {\n return predicateElement\n }\n return\n }\n }\n }\n }\n // If the property isn't State Equality, we are checking Physical addresses. This only exists for Point and Point V3.\n switch (predicateElement.type) {\n case 'pointAddressV3': {\n // If the value is true, we only want to return the element for PO Boxes. If it's false, then we only want\n // to return element for non mail address addresses.\n if (\n 'properties' in predicateValue &&\n predicateValue.properties &&\n typeof predicateValue.properties === 'object' &&\n 'dataset' in predicateValue.properties &&\n typeof predicateValue.properties.dataset === 'string'\n ) {\n const result = predicate.definition.value\n ? predicateValue.properties.dataset.startsWith('mailAddress')\n : predicateValue.properties.dataset.startsWith('gnaf')\n if (result) {\n return predicateElement\n }\n }\n break\n }\n case 'pointAddress': {\n // If the value is true, we only want to return the element for PO Boxes. If it's false, then we only want\n // to return element for non mail address addresses.\n if (\n 'dataset' in predicateValue &&\n typeof predicateValue.dataset === 'string'\n ) {\n const result = predicate.definition.value\n ? predicateValue.dataset === 'mailAddress'\n : predicateValue.dataset === 'GNAF'\n if (result) {\n return predicateElement\n }\n }\n break\n }\n }\n }\n }\n break\n }\n case 'OPTIONS':\n case undefined: {\n const optionsPredicateElement =\n typeCastService.formElements.toOptionsElement(predicateElement)\n if (!optionsPredicateElement) {\n return undefined\n }\n\n // If the predicate element does not have any options to evaluate,\n // we will show the element.\n // Unless the predicate element has dynamic options and\n // options have not been fetched yet.\n if (!Array.isArray(optionsPredicateElement.options)) {\n return optionsPredicateElement.optionsType !== 'DYNAMIC'\n ? predicateElement\n : undefined\n } else {\n return evaluateConditionalOptionsPredicate({\n predicate,\n predicateValue,\n predicateElement: optionsPredicateElement,\n })\n ? predicateElement\n : undefined\n }\n }\n }\n}\n"]}
|