@pega/react-sdk-overrides 0.25.2 → 0.25.4
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/lib/designSystemExtension/Banner/Banner.css +1 -1
- package/lib/designSystemExtension/Banner/Banner.tsx +7 -7
- package/lib/designSystemExtension/CaseSummaryFields/CaseSummaryFields.tsx +8 -10
- package/lib/designSystemExtension/DetailsFields/DetailsFields.tsx +11 -13
- package/lib/designSystemExtension/FieldGroup/FieldGroup.tsx +7 -8
- package/lib/designSystemExtension/FieldGroupList/FieldGroupList.tsx +9 -9
- package/lib/designSystemExtension/FieldValueList/FieldValueList.tsx +7 -8
- package/lib/designSystemExtension/Operator/Operator.tsx +11 -12
- package/lib/designSystemExtension/RichTextEditor/RichTextEditor.tsx +28 -3
- package/lib/designSystemExtension/WssQuickCreate/WssQuickCreate.css +4 -4
- package/lib/designSystemExtension/WssQuickCreate/WssQuickCreate.tsx +1 -1
- package/lib/field/CancelAlert/CancelAlert.css +4 -4
- package/lib/field/CancelAlert/CancelAlert.tsx +5 -5
- package/lib/field/Checkbox/Checkbox.tsx +96 -3
- package/lib/field/Currency/currency-utils.ts +1 -2
- package/lib/field/Dropdown/Dropdown.tsx +0 -2
- package/lib/field/Group/Group.tsx +5 -5
- package/lib/field/Location/Location.tsx +256 -0
- package/lib/field/Location/config-ext.json +8 -0
- package/lib/field/Location/index.tsx +1 -0
- package/lib/field/ObjectReference/ObjectReference.tsx +235 -0
- package/lib/field/ObjectReference/index.tsx +1 -0
- package/lib/field/ObjectReference/utils.ts +111 -0
- package/lib/field/RadioButtons/RadioButtons.tsx +46 -1
- package/lib/field/ScalarList/ScalarList.tsx +1 -2
- package/lib/field/SelectableCard/SelectableCard.tsx +175 -0
- package/lib/field/SelectableCard/index.tsx +1 -0
- package/lib/field/SelectableCard/utils.tsx +226 -0
- package/lib/field/SemanticLink/SemanticLink.tsx +159 -27
- package/lib/field/SemanticLink/utils.ts +1 -1
- package/lib/field/TextContent/TextContent.tsx +0 -1
- package/lib/field/UserReference/UserReference.tsx +0 -1
- package/lib/helpers/attachmentHelpers.ts +56 -35
- package/lib/helpers/common-utils.ts +2 -2
- package/lib/helpers/data_page.ts +0 -1
- package/lib/helpers/formatters/CurrencyMap.ts +0 -2
- package/lib/helpers/simpleTableHelpers.ts +117 -5
- package/lib/helpers/utils.ts +8 -1
- package/lib/helpers/versionHelpers.ts +0 -1
- package/lib/infra/ActionButtons/ActionButtons.tsx +28 -21
- package/lib/infra/Assignment/Assignment.tsx +2 -2
- package/lib/infra/Containers/FlowContainer/FlowContainer.tsx +14 -93
- package/lib/infra/Containers/ModalViewContainer/ListViewActionButtons/ListViewActionButtons.tsx +0 -1
- package/lib/infra/Containers/ModalViewContainer/ModalViewContainer.tsx +2 -2
- package/lib/infra/Containers/ViewContainer/ViewContainer.tsx +3 -4
- package/lib/infra/Containers/container-helpers.ts +47 -1
- package/lib/infra/DashboardFilter/DashboardFilter.tsx +0 -2
- package/lib/infra/DashboardFilter/filterUtils.tsx +3 -4
- package/lib/infra/DeferLoad/DeferLoad.tsx +1 -3
- package/lib/infra/ErrorBoundary/ErrorBoundary.tsx +0 -2
- package/lib/infra/MultiStep/MultiStep.css +8 -8
- package/lib/infra/NavBar/NavBar.css +1 -1
- package/lib/infra/NavBar/NavBar.tsx +3 -4
- package/lib/infra/Reference/Reference.tsx +2 -3
- package/lib/infra/RootContainer/RootContainer.tsx +0 -1
- package/lib/template/AdvancedSearch/AdvancedSearch.tsx +0 -1
- package/lib/template/AdvancedSearch/SearchGroup/persistUtils.ts +3 -9
- package/lib/template/AdvancedSearch/SearchGroups/SearchGroups.tsx +3 -4
- package/lib/template/AdvancedSearch/SearchGroups/hooks.ts +1 -1
- package/lib/template/AppShell/AppShell.css +1 -1
- package/lib/template/AppShell/AppShell.tsx +4 -8
- package/lib/template/CaseSummary/CaseSummary.tsx +0 -1
- package/lib/template/CaseView/CaseView.tsx +13 -19
- package/lib/template/Confirmation/Confirmation.tsx +0 -1
- package/lib/template/DataReference/DataReference.tsx +7 -10
- package/lib/template/DataReference/SearchForm.tsx +6 -5
- package/lib/template/DataReference/{utils.js → utils.ts} +3 -3
- package/lib/template/DefaultForm/DefaultForm.tsx +1 -1
- package/lib/template/DefaultPage/DefaultPage.tsx +88 -0
- package/lib/template/DefaultPage/index.tsx +1 -0
- package/lib/template/Details/Details/Details.tsx +10 -10
- package/lib/template/Details/DetailsThreeColumn/DetailsThreeColumn.tsx +10 -10
- package/lib/template/Details/DetailsTwoColumn/DetailsTwoColumn.tsx +10 -10
- package/lib/template/FieldGroupTemplate/FieldGroupTemplate.tsx +1 -2
- package/lib/template/InlineDashboard/InlineDashboard.tsx +12 -14
- package/lib/template/ListView/ListView.tsx +8 -20
- package/lib/template/ListView/hooks.ts +1 -5
- package/lib/template/ListView/utils.ts +1 -1
- package/lib/template/NarrowWide/NarrowWide/NarrowWide.tsx +3 -3
- package/lib/template/NarrowWide/NarrowWideDetails/NarrowWideDetails.tsx +10 -10
- package/lib/template/OneColumn/OneColumn/OneColumn.tsx +5 -5
- package/lib/template/PromotedFilters/PromotedFilters.tsx +0 -1
- package/lib/template/SelfServiceCaseView/SelfServiceCaseView.tsx +3 -0
- package/lib/template/SelfServiceCaseView/index.tsx +1 -0
- package/lib/template/SimpleTable/SimpleTable/SimpleTable.tsx +1 -2
- package/lib/template/SimpleTable/SimpleTableManual/SimpleTableManual.tsx +33 -30
- package/lib/template/TwoColumn/TwoColumn/TwoColumn.tsx +1 -2
- package/lib/template/TwoColumn/TwoColumnTab/TwoColumnTab.tsx +1 -2
- package/lib/template/WideNarrow/WideNarrow/WideNarrow.tsx +3 -3
- package/lib/template/WideNarrow/WideNarrowDetails/WideNarrowDetails.tsx +10 -10
- package/lib/template/WssNavBar/WssNavBar.css +1 -1
- package/lib/template/WssNavBar/WssNavBar.tsx +4 -4
- package/lib/widget/Attachment/Attachment.css +6 -8
- package/lib/widget/Attachment/Attachment.tsx +61 -57
- package/lib/widget/CaseHistory/CaseHistory.tsx +3 -3
- package/lib/widget/FileUtility/ActionButtonsForFileUtil/ActionButtonsForFileUtil.css +0 -14
- package/lib/widget/FileUtility/ActionButtonsForFileUtil/ActionButtonsForFileUtil.tsx +2 -2
- package/lib/widget/FileUtility/FileUtility/FileUtility.css +7 -6
- package/lib/widget/FileUtility/FileUtility/FileUtility.tsx +4 -6
- package/lib/widget/Followers/Followers.tsx +0 -2
- package/lib/widget/QuickCreate/QuickCreate.tsx +0 -1
- package/lib/widget/SummaryItem/SummaryItem.css +9 -11
- package/lib/widget/SummaryItem/SummaryItem.tsx +1 -1
- package/lib/widget/ToDo/ToDo.css +1 -13
- package/lib/widget/ToDo/ToDo.tsx +15 -7
- package/package.json +1 -1
- /package/lib/template/DataReference/{DataReferenceAdvancedSearchContext.js → DataReferenceAdvancedSearchContext.ts} +0 -0
|
@@ -1,13 +1,11 @@
|
|
|
1
|
-
import
|
|
2
|
-
import Grid from '@mui/material/Grid';
|
|
1
|
+
import { Link } from '@mui/material';
|
|
3
2
|
import makeStyles from '@mui/styles/makeStyles';
|
|
4
3
|
|
|
5
|
-
import { getComponentFromMap } from '@pega/react-sdk-components/lib/bridge/helpers/sdk_component_map';
|
|
6
4
|
import type { PConnFieldProps } from '@pega/react-sdk-components/lib/types/PConnProps';
|
|
7
5
|
|
|
8
|
-
|
|
9
|
-
SemanticLink in SDK and only showing the value as a read only text field. */
|
|
6
|
+
import semanticUtils from './utils';
|
|
10
7
|
|
|
8
|
+
// eslint-disable-next-line
|
|
11
9
|
const useStyles = makeStyles(theme => ({
|
|
12
10
|
root: {
|
|
13
11
|
paddingRight: theme.spacing(1),
|
|
@@ -41,36 +39,170 @@ const useStyles = makeStyles(theme => ({
|
|
|
41
39
|
|
|
42
40
|
interface SemanticLinkProps extends PConnFieldProps {
|
|
43
41
|
// If any, enter additional props that only exist on SemanticLink here
|
|
44
|
-
// from previous PropTypes
|
|
45
42
|
text: string;
|
|
43
|
+
resourcePayload: any;
|
|
44
|
+
resourceParams: any;
|
|
45
|
+
previewKey: string | null;
|
|
46
|
+
onClick: (event: any) => void;
|
|
47
|
+
testId: string;
|
|
48
|
+
referenceType: string | null;
|
|
49
|
+
dataRelationshipContext: string | null;
|
|
50
|
+
contextPage: any;
|
|
46
51
|
}
|
|
47
52
|
|
|
48
53
|
export default function SemanticLink(props: SemanticLinkProps) {
|
|
49
|
-
|
|
50
|
-
|
|
54
|
+
const {
|
|
55
|
+
text,
|
|
56
|
+
resourcePayload = {},
|
|
57
|
+
resourceParams = {},
|
|
58
|
+
getPConnect,
|
|
59
|
+
previewKey,
|
|
60
|
+
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
|
61
|
+
onClick,
|
|
62
|
+
testId = '',
|
|
63
|
+
referenceType,
|
|
64
|
+
dataRelationshipContext = null,
|
|
65
|
+
contextPage,
|
|
66
|
+
...restProps
|
|
67
|
+
} = props;
|
|
68
|
+
const { ACTION_OPENWORKBYHANDLE, ACTION_SHOWDATA }: any = PCore.getSemanticUrlUtils().getActions();
|
|
69
|
+
const pConnect = getPConnect();
|
|
70
|
+
const dataResourcePayLoad = resourcePayload?.resourceType === 'DATA' ? resourcePayload : null;
|
|
51
71
|
|
|
52
|
-
const {
|
|
53
|
-
|
|
72
|
+
const {
|
|
73
|
+
RESOURCE_TYPES: { DATA },
|
|
74
|
+
WORKCLASS,
|
|
75
|
+
CASE_INFO: { CASE_INFO_CLASSID }
|
|
76
|
+
} = PCore.getConstants();
|
|
54
77
|
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
78
|
+
let linkURL = '';
|
|
79
|
+
let payload = {};
|
|
80
|
+
let dataViewName;
|
|
81
|
+
let linkComponentProps = {
|
|
82
|
+
href: linkURL
|
|
83
|
+
};
|
|
84
|
+
if (text) {
|
|
85
|
+
(linkComponentProps as any).href = linkURL;
|
|
86
|
+
}
|
|
87
|
+
let isData = false;
|
|
88
|
+
const shouldTreatAsDataReference = !previewKey && resourcePayload.caseClassName;
|
|
89
|
+
if (contextPage?.classID) {
|
|
90
|
+
resourcePayload.caseClassName = contextPage.classID;
|
|
91
|
+
}
|
|
92
|
+
/* TODO : In case of duplicate search case the classID is Work- need to set it to
|
|
93
|
+
the current case class ID */
|
|
94
|
+
if (resourcePayload.caseClassName === WORKCLASS) {
|
|
95
|
+
resourcePayload.caseClassName = pConnect.getValue(CASE_INFO_CLASSID);
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
function showDataAction() {
|
|
99
|
+
if (dataResourcePayLoad && dataResourcePayLoad.resourceType === 'DATA') {
|
|
100
|
+
const { content } = dataResourcePayLoad;
|
|
101
|
+
const lookUpDataPageInfo = PCore.getDataTypeUtils().getLookUpDataPageInfo(dataResourcePayLoad?.className);
|
|
102
|
+
const lookUpDataPage = PCore.getDataTypeUtils().getLookUpDataPage(dataResourcePayLoad?.className);
|
|
103
|
+
if (lookUpDataPageInfo) {
|
|
104
|
+
const { parameters }: any = lookUpDataPageInfo;
|
|
105
|
+
payload = Object.keys(parameters).reduce((acc, param) => {
|
|
106
|
+
const paramValue = parameters[param];
|
|
107
|
+
return {
|
|
108
|
+
...acc,
|
|
109
|
+
[param]: PCore.getAnnotationUtils().isProperty(paramValue) ? content[PCore.getAnnotationUtils().getPropertyName(paramValue)] : paramValue
|
|
110
|
+
};
|
|
111
|
+
}, {});
|
|
112
|
+
}
|
|
113
|
+
getPConnect()
|
|
114
|
+
.getActionsApi()
|
|
115
|
+
.showData('pyDetails', lookUpDataPage, {
|
|
116
|
+
...payload
|
|
117
|
+
});
|
|
118
|
+
}
|
|
119
|
+
if ((referenceType && referenceType.toUpperCase() === DATA) || shouldTreatAsDataReference) {
|
|
120
|
+
getPConnect()
|
|
121
|
+
.getActionsApi()
|
|
122
|
+
.showData('pyDetails', dataViewName, {
|
|
123
|
+
...payload
|
|
124
|
+
});
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
function openLinkClick(e) {
|
|
129
|
+
if (!e.metaKey && !e.ctrlKey) {
|
|
130
|
+
e.preventDefault();
|
|
131
|
+
if (
|
|
132
|
+
(dataResourcePayLoad && dataResourcePayLoad.resourceType === 'DATA') ||
|
|
133
|
+
(referenceType && referenceType.toUpperCase() === DATA) ||
|
|
134
|
+
shouldTreatAsDataReference
|
|
135
|
+
) {
|
|
136
|
+
showDataAction();
|
|
137
|
+
} else if (previewKey) {
|
|
138
|
+
getPConnect().getActionsApi().openWorkByHandle(previewKey, resourcePayload.caseClassName);
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
if ((referenceType && referenceType.toUpperCase() === DATA) || shouldTreatAsDataReference) {
|
|
144
|
+
try {
|
|
145
|
+
isData = true;
|
|
146
|
+
// @ts-expect-error
|
|
147
|
+
const dataRefContext = semanticUtils.getDataReferenceInfo(pConnect, dataRelationshipContext, contextPage);
|
|
148
|
+
dataViewName = dataRefContext.dataContext;
|
|
149
|
+
payload = dataRefContext.dataContextParameters as any;
|
|
150
|
+
} catch (error) {
|
|
151
|
+
console.log('Error in getting the data reference info', error);
|
|
152
|
+
}
|
|
153
|
+
} else if (resourcePayload && resourcePayload.resourceType === 'DATA') {
|
|
154
|
+
isData = true;
|
|
155
|
+
dataViewName = PCore.getDataTypeUtils().getLookUpDataPage(resourcePayload.className);
|
|
156
|
+
const lookUpDataPageInfo = PCore.getDataTypeUtils().getLookUpDataPageInfo(resourcePayload.className);
|
|
157
|
+
const { content } = resourcePayload;
|
|
158
|
+
if (lookUpDataPageInfo) {
|
|
159
|
+
const { parameters }: any = lookUpDataPageInfo;
|
|
160
|
+
payload = Object.keys(parameters).reduce((acc, param) => {
|
|
161
|
+
const paramValue = parameters[param];
|
|
162
|
+
return {
|
|
163
|
+
...acc,
|
|
164
|
+
[param]: PCore.getAnnotationUtils().isProperty(paramValue) ? content[PCore.getAnnotationUtils().getPropertyName(paramValue)] : paramValue
|
|
165
|
+
};
|
|
166
|
+
}, {});
|
|
167
|
+
} else {
|
|
168
|
+
const keysInfo = PCore.getDataTypeUtils().getDataPageKeys(dataViewName) ?? [];
|
|
169
|
+
payload = keysInfo.reduce((acc, curr) => {
|
|
170
|
+
return {
|
|
171
|
+
...acc,
|
|
172
|
+
[curr.keyName]: content[curr.isAlternateKeyStorage ? curr.linkedField : curr.keyName]
|
|
173
|
+
};
|
|
174
|
+
}, {});
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
if (isData && dataViewName && payload) {
|
|
179
|
+
linkURL = PCore.getSemanticUrlUtils().getResolvedSemanticURL(
|
|
180
|
+
ACTION_SHOWDATA,
|
|
181
|
+
{ pageName: 'pyDetails', dataViewName },
|
|
182
|
+
{
|
|
183
|
+
...payload
|
|
184
|
+
}
|
|
70
185
|
);
|
|
186
|
+
} else {
|
|
187
|
+
// BUG-678282 fix to handle scenario when workID was not populated.
|
|
188
|
+
// Check renderParentLink in Caseview / CasePreview
|
|
189
|
+
resourceParams.objectID = resourceParams.workID === '' && typeof previewKey === 'string' ? previewKey.split(' ')[1] : resourceParams.workID;
|
|
190
|
+
if (previewKey) {
|
|
191
|
+
resourceParams.id = previewKey;
|
|
192
|
+
}
|
|
193
|
+
linkURL = PCore.getSemanticUrlUtils().getResolvedSemanticURL(ACTION_OPENWORKBYHANDLE, resourcePayload, resourceParams);
|
|
71
194
|
}
|
|
72
195
|
|
|
73
|
-
if (
|
|
74
|
-
|
|
196
|
+
if (text) {
|
|
197
|
+
linkComponentProps = {
|
|
198
|
+
...linkComponentProps,
|
|
199
|
+
href: linkURL
|
|
200
|
+
};
|
|
75
201
|
}
|
|
202
|
+
|
|
203
|
+
return (
|
|
204
|
+
<Link component='button' {...linkComponentProps} {...restProps} onClick={openLinkClick} data-testid={testId}>
|
|
205
|
+
{text}
|
|
206
|
+
</Link>
|
|
207
|
+
);
|
|
76
208
|
}
|
|
@@ -32,7 +32,7 @@ function getDataReferenceInfo(pConnect, dataRelationshipContext) {
|
|
|
32
32
|
dataContext = name;
|
|
33
33
|
for (const [key, value] of Object.entries(parameters)) {
|
|
34
34
|
const property =
|
|
35
|
-
// @ts-
|
|
35
|
+
// @ts-expect-error - Property 'getLeafPropertyName' is private and only accessible within class 'AnnotationUtils'
|
|
36
36
|
dataRelationshipContext !== null ? annotationUtils.getPropertyName(value as string) : annotationUtils.getLeafPropertyName(value);
|
|
37
37
|
payload[key] = pConnect.getValue(`.${property}`);
|
|
38
38
|
}
|
|
@@ -1,20 +1,67 @@
|
|
|
1
|
+
import { useCallback } from 'react';
|
|
1
2
|
import download from 'downloadjs';
|
|
2
3
|
|
|
3
|
-
export const
|
|
4
|
-
|
|
5
|
-
return parseFloat(fileSize) < parseFloat(maxSizeInMB);
|
|
4
|
+
export const isContentBinary = headers => {
|
|
5
|
+
return headers && headers['content-transfer-encoding'] === 'binary';
|
|
6
6
|
};
|
|
7
7
|
|
|
8
|
-
export const
|
|
8
|
+
export const isContentBase64 = headers => {
|
|
9
|
+
return headers && headers['content-transfer-encoding'] === 'base64';
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
export const fileDownload = (data, fileName, ext, headers) => {
|
|
9
13
|
const name = ext ? `${fileName}.${ext}` : fileName;
|
|
10
14
|
// Temp fix: downloading EMAIl type attachment as html file
|
|
11
15
|
if (ext === 'html') {
|
|
12
|
-
download(data, name, 'text/html');
|
|
16
|
+
download(isContentBase64(headers) ? atob(data) : data, name, 'text/html');
|
|
17
|
+
} else if (isContentBinary(headers)) {
|
|
18
|
+
download(data, name);
|
|
13
19
|
} else {
|
|
14
20
|
download(atob(data), name);
|
|
15
21
|
}
|
|
16
22
|
};
|
|
17
23
|
|
|
24
|
+
export const fileDownloadVar = (content, type, name, extension) => {
|
|
25
|
+
if (type === 'FILE' || type === undefined) {
|
|
26
|
+
fileDownload(content.data, name, extension, content.headers);
|
|
27
|
+
} else if (type === 'URL') {
|
|
28
|
+
let { data } = content;
|
|
29
|
+
if (!/^(http|https):\/\//.test(data)) {
|
|
30
|
+
data = `//${data}`;
|
|
31
|
+
}
|
|
32
|
+
window.open(content.data, '_blank');
|
|
33
|
+
} else if (type === 'EMAIL') {
|
|
34
|
+
// Temp Fix: for EMAIL type attachment
|
|
35
|
+
fileDownload(content.data, name, 'html', content.headers);
|
|
36
|
+
}
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
export const useFileDownload = context => {
|
|
40
|
+
return useCallback(
|
|
41
|
+
({ ID, name, extension, type, category, responseType }) => {
|
|
42
|
+
if (category !== 'pxDocument') {
|
|
43
|
+
PCore.getAttachmentUtils()
|
|
44
|
+
.downloadAttachment(ID, context, responseType)
|
|
45
|
+
.then(content => {
|
|
46
|
+
fileDownloadVar(content, type, name, extension);
|
|
47
|
+
})
|
|
48
|
+
|
|
49
|
+
.catch(console.error);
|
|
50
|
+
} else {
|
|
51
|
+
PCore.getAttachmentUtils()
|
|
52
|
+
// @ts-expect-error
|
|
53
|
+
.downloadDocument(ID, context, responseType)
|
|
54
|
+
.then(content => {
|
|
55
|
+
fileDownloadVar(content, type, name, extension);
|
|
56
|
+
})
|
|
57
|
+
|
|
58
|
+
.catch(console.error);
|
|
59
|
+
}
|
|
60
|
+
},
|
|
61
|
+
[context]
|
|
62
|
+
);
|
|
63
|
+
};
|
|
64
|
+
|
|
18
65
|
export const getIconFromFileType = (fileType): string => {
|
|
19
66
|
let icon = 'document-doc';
|
|
20
67
|
if (!fileType) return icon;
|
|
@@ -42,35 +89,9 @@ export const getIconFromFileType = (fileType): string => {
|
|
|
42
89
|
return icon;
|
|
43
90
|
};
|
|
44
91
|
|
|
45
|
-
export const
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
case 'FILE':
|
|
49
|
-
icon = inThis.getIconFromFileType(attachment.mimeType);
|
|
50
|
-
break;
|
|
51
|
-
case 'URL':
|
|
52
|
-
icon = 'chain';
|
|
53
|
-
break;
|
|
54
|
-
default:
|
|
55
|
-
icon = 'document-doc';
|
|
56
|
-
}
|
|
57
|
-
return icon;
|
|
92
|
+
export const validateMaxSize = (fileObj: any, maxSizeInMB: string): boolean => {
|
|
93
|
+
const fileSize = (fileObj.size / 1048576).toFixed(2);
|
|
94
|
+
return parseFloat(fileSize) < parseFloat(maxSizeInMB);
|
|
58
95
|
};
|
|
59
96
|
|
|
60
|
-
export const
|
|
61
|
-
respObj
|
|
62
|
-
): {
|
|
63
|
-
props: { meta: string; name: string; icon: string };
|
|
64
|
-
responseProps: any;
|
|
65
|
-
} => {
|
|
66
|
-
return {
|
|
67
|
-
props: {
|
|
68
|
-
meta: `${respObj.pyCategoryName}, ${respObj.pxCreateOperator}`,
|
|
69
|
-
name: respObj.pyAttachName,
|
|
70
|
-
icon: getIconFromFileType(respObj.pyMimeFileExtension)
|
|
71
|
-
},
|
|
72
|
-
responseProps: {
|
|
73
|
-
...respObj
|
|
74
|
-
}
|
|
75
|
-
};
|
|
76
|
-
};
|
|
97
|
+
export const isFileUploadedToServer = file => file.responseProps && !file.responseProps.ID?.includes('temp');
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
export function isEmptyObject(obj:
|
|
1
|
+
export function isEmptyObject(obj: object): boolean {
|
|
2
2
|
return Object.keys(obj).length === 0;
|
|
3
3
|
}
|
|
4
4
|
|
|
@@ -16,7 +16,7 @@ export function getGenericFieldsLocalizedValue(path: string, key: string): strin
|
|
|
16
16
|
|
|
17
17
|
// Split the path and traverse the object
|
|
18
18
|
const pathParts = path.split('.');
|
|
19
|
-
let currentObj = localeStore;
|
|
19
|
+
let currentObj: any = localeStore;
|
|
20
20
|
|
|
21
21
|
for (const part of pathParts) {
|
|
22
22
|
if (!currentObj[part]) return key;
|
package/lib/helpers/data_page.ts
CHANGED
|
@@ -89,6 +89,51 @@ export const getApiContext = (processedData, pConnect, reorderCB) => {
|
|
|
89
89
|
};
|
|
90
90
|
};
|
|
91
91
|
|
|
92
|
+
const PRIMARY_FIELDS = 'pyPrimaryFields';
|
|
93
|
+
const SUPPORTED_FIELD_TYPES = [
|
|
94
|
+
'Address',
|
|
95
|
+
'TextArea',
|
|
96
|
+
'TextInput',
|
|
97
|
+
'Phone',
|
|
98
|
+
'Email',
|
|
99
|
+
'Time',
|
|
100
|
+
'URL',
|
|
101
|
+
'Percentage',
|
|
102
|
+
'Integer',
|
|
103
|
+
'Decimal',
|
|
104
|
+
'Date',
|
|
105
|
+
'DateTime',
|
|
106
|
+
'Currency',
|
|
107
|
+
'Checkbox',
|
|
108
|
+
'Dropdown',
|
|
109
|
+
'AutoComplete',
|
|
110
|
+
'UserReference',
|
|
111
|
+
'RichText'
|
|
112
|
+
];
|
|
113
|
+
|
|
114
|
+
export const getConfigFields = (rawFields, contextClass, primaryFieldsViewIndex) => {
|
|
115
|
+
let primaryFields: any = [];
|
|
116
|
+
let configFields: any = [];
|
|
117
|
+
|
|
118
|
+
if (primaryFieldsViewIndex > -1) {
|
|
119
|
+
let primaryFieldVMD: any = PCore.getMetadataUtils().resolveView(PRIMARY_FIELDS);
|
|
120
|
+
if (Array.isArray(primaryFieldVMD)) {
|
|
121
|
+
primaryFieldVMD = primaryFieldVMD.find(primaryFieldView => primaryFieldView.classID === contextClass);
|
|
122
|
+
primaryFields = primaryFieldVMD?.children?.[0]?.children || [];
|
|
123
|
+
} else if (primaryFieldVMD?.classID === contextClass) {
|
|
124
|
+
primaryFields = primaryFieldVMD?.children?.[0]?.children || [];
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
if (primaryFields.length) {
|
|
128
|
+
primaryFields = primaryFields.filter(primaryField => SUPPORTED_FIELD_TYPES.includes(primaryField.type));
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
configFields = [...rawFields.slice(0, primaryFieldsViewIndex), ...primaryFields, ...rawFields.slice(primaryFieldsViewIndex + 1)];
|
|
133
|
+
// filter duplicate fields after combining raw fields and primary fields
|
|
134
|
+
return configFields.filter((field, index) => configFields.findIndex(_field => field.config?.value === _field.config?.value) === index);
|
|
135
|
+
};
|
|
136
|
+
|
|
92
137
|
export const buildMetaForListView = (fieldMetadata, fields, type, ruleClass, name, propertyLabel, isDataObject, parameters) => {
|
|
93
138
|
return {
|
|
94
139
|
name,
|
|
@@ -126,11 +171,80 @@ export const buildMetaForListView = (fieldMetadata, fields, type, ruleClass, nam
|
|
|
126
171
|
};
|
|
127
172
|
};
|
|
128
173
|
|
|
129
|
-
export
|
|
174
|
+
export function isFLProperty(label) {
|
|
175
|
+
return label?.startsWith('@FL');
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
/**
|
|
179
|
+
* [getFieldLabel]
|
|
180
|
+
* Description - A utility that returns resolved field label for "@FL" annotation i.e from data model.
|
|
181
|
+
* @param {Object} fieldConfig
|
|
182
|
+
* @returns {string} resolved label string
|
|
183
|
+
*
|
|
184
|
+
* example:
|
|
185
|
+
* fieldConfig = {label: "@FL .pyID", classID: "TestCase-Work"};
|
|
186
|
+
* return "Case ID"
|
|
187
|
+
*/
|
|
188
|
+
export function getFieldLabel(fieldConfig) {
|
|
189
|
+
const { label, classID, caption } = fieldConfig;
|
|
190
|
+
let fieldLabel = (label ?? caption)?.substring(4);
|
|
191
|
+
const labelSplit = fieldLabel?.split('.');
|
|
192
|
+
const propertyName = labelSplit?.pop();
|
|
193
|
+
const fieldMetaData: any = PCore.getMetadataUtils().getPropertyMetadata(propertyName, classID) ?? {};
|
|
194
|
+
fieldLabel = fieldMetaData.label ?? fieldMetaData.caption ?? propertyName;
|
|
195
|
+
return fieldLabel;
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
export const updateFieldLabels = (fields, configFields, primaryFieldsViewIndex, pConnect, options) => {
|
|
199
|
+
const labelsOfFields: any = [];
|
|
200
|
+
const { columnsRawConfig = [] } = options;
|
|
201
|
+
fields.forEach((field, idx) => {
|
|
202
|
+
const rawColumnConfig = columnsRawConfig[idx]?.config;
|
|
203
|
+
if (field.config.value === PRIMARY_FIELDS) {
|
|
204
|
+
labelsOfFields.push('');
|
|
205
|
+
} else if (isFLProperty(rawColumnConfig?.label ?? rawColumnConfig?.caption)) {
|
|
206
|
+
labelsOfFields.push(getFieldLabel(rawColumnConfig) || field.config.label || field.config.caption);
|
|
207
|
+
} else {
|
|
208
|
+
labelsOfFields.push(field.config.label || field.config.caption);
|
|
209
|
+
}
|
|
210
|
+
});
|
|
211
|
+
|
|
212
|
+
if (primaryFieldsViewIndex > -1) {
|
|
213
|
+
const totalPrimaryFieldsColumns = configFields.length - fields.length + 1;
|
|
214
|
+
if (totalPrimaryFieldsColumns) {
|
|
215
|
+
const primaryFieldLabels: any = [];
|
|
216
|
+
for (let i = primaryFieldsViewIndex; i < primaryFieldsViewIndex + totalPrimaryFieldsColumns; i += 1) {
|
|
217
|
+
let label = configFields[i].config?.label;
|
|
218
|
+
if (isFLProperty(label)) {
|
|
219
|
+
label = getFieldLabel(configFields[i].config);
|
|
220
|
+
} else if (label.startsWith('@')) {
|
|
221
|
+
label = label.substring(3);
|
|
222
|
+
}
|
|
223
|
+
if (pConnect) {
|
|
224
|
+
label = pConnect.getLocalizedValue(label);
|
|
225
|
+
}
|
|
226
|
+
primaryFieldLabels.push(label);
|
|
227
|
+
}
|
|
228
|
+
labelsOfFields.splice(primaryFieldsViewIndex, 1, ...primaryFieldLabels);
|
|
229
|
+
} else {
|
|
230
|
+
labelsOfFields.splice(primaryFieldsViewIndex, 1);
|
|
231
|
+
}
|
|
232
|
+
}
|
|
233
|
+
return labelsOfFields;
|
|
234
|
+
};
|
|
235
|
+
|
|
236
|
+
export const buildFieldsForTable = (configFields, pConnect, showDeleteButton, options) => {
|
|
237
|
+
const { primaryFieldsViewIndex, fields } = options;
|
|
238
|
+
|
|
239
|
+
// get resolved field labels for primary fields raw config included in configFields
|
|
240
|
+
const fieldsLabels = updateFieldLabels(fields, configFields, primaryFieldsViewIndex, pConnect, {
|
|
241
|
+
columnsRawConfig: pConnect.getRawConfigProps()?.children?.find(item => item?.name === 'Columns')?.children
|
|
242
|
+
});
|
|
243
|
+
|
|
130
244
|
const fieldDefs = configFields.map((field, index) => {
|
|
131
245
|
return {
|
|
132
246
|
type: 'text',
|
|
133
|
-
label:
|
|
247
|
+
label: fieldsLabels[index],
|
|
134
248
|
fillAvailableSpace: !!field.config.fillAvailableSpace,
|
|
135
249
|
id: `${index}`,
|
|
136
250
|
name: field.config.value.substr(4),
|
|
@@ -213,7 +327,7 @@ export function createPConnect(contextName, referenceList, pageReference): any {
|
|
|
213
327
|
};
|
|
214
328
|
|
|
215
329
|
// create PConnect object
|
|
216
|
-
const config = { meta: {}, options };
|
|
330
|
+
const config: any = { meta: {}, options };
|
|
217
331
|
const { getPConnect } = PCore.createPConnect(config);
|
|
218
332
|
|
|
219
333
|
return getPConnect();
|
|
@@ -235,7 +349,6 @@ export const filterData = filterByColumns => {
|
|
|
235
349
|
filterValue =
|
|
236
350
|
filterObj.containsFilterValue !== null && filterObj.containsFilterValue !== '' ? Utils.getSeconds(filterObj.containsFilterValue) : null;
|
|
237
351
|
|
|
238
|
-
// eslint-disable-next-line sonarjs/no-nested-switch
|
|
239
352
|
switch (filterObj.containsFilter) {
|
|
240
353
|
case 'notequal':
|
|
241
354
|
// becasue filterValue is in minutes, need to have a range of less than 60 secons
|
|
@@ -302,7 +415,6 @@ export const filterData = filterByColumns => {
|
|
|
302
415
|
value = item[filterObj.ref].toLowerCase();
|
|
303
416
|
filterValue = filterObj.containsFilterValue.toLowerCase();
|
|
304
417
|
|
|
305
|
-
// eslint-disable-next-line sonarjs/no-nested-switch
|
|
306
418
|
switch (filterObj.containsFilter) {
|
|
307
419
|
case 'contains':
|
|
308
420
|
if (value.indexOf(filterValue) < 0) {
|
package/lib/helpers/utils.ts
CHANGED
|
@@ -48,7 +48,6 @@ export class Utils {
|
|
|
48
48
|
// eslint-disable-next-line no-case-declarations
|
|
49
49
|
const dataPage = configProps.datasource;
|
|
50
50
|
if (typeof dataPage === 'string' && dataObject[dataPage]) {
|
|
51
|
-
// eslint-disable-next-line no-alert
|
|
52
51
|
alert('need to handle data page');
|
|
53
52
|
} else {
|
|
54
53
|
let listSourceItems = configProps.listOutput;
|
|
@@ -337,6 +336,14 @@ export class Utils {
|
|
|
337
336
|
static isObject(objValue) {
|
|
338
337
|
return objValue && typeof objValue === 'object' && objValue.constructor === Object;
|
|
339
338
|
}
|
|
339
|
+
|
|
340
|
+
static getMappedKey(key) {
|
|
341
|
+
const mappedKey = PCore.getEnvironmentInfo().getKeyMapping(key);
|
|
342
|
+
if (!mappedKey) {
|
|
343
|
+
return key;
|
|
344
|
+
}
|
|
345
|
+
return mappedKey;
|
|
346
|
+
}
|
|
340
347
|
}
|
|
341
348
|
|
|
342
349
|
export default Utils;
|
|
@@ -10,6 +10,5 @@ export const sdkVersion = '8.7';
|
|
|
10
10
|
export function compareSdkPCoreVersions() {
|
|
11
11
|
// const theConstellationVersion = PCore.getPCoreVersion();
|
|
12
12
|
|
|
13
|
-
// eslint-disable-next-line no-console
|
|
14
13
|
console.warn(`Using Constellation version ${PCore.getPCoreVersion()}. Ensure this is the same version as your Infinity server.`);
|
|
15
14
|
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import makeStyles from '@mui/styles/makeStyles';
|
|
2
2
|
import Button from '@mui/material/Button';
|
|
3
|
-
import {
|
|
3
|
+
import { Grid2, Divider } from '@mui/material';
|
|
4
4
|
|
|
5
5
|
// ActionButtons does NOT have getPConnect. So, no need to extend from PConnProps
|
|
6
6
|
interface ActionButtonsProps {
|
|
@@ -10,13 +10,18 @@ interface ActionButtonsProps {
|
|
|
10
10
|
onButtonPress: any;
|
|
11
11
|
}
|
|
12
12
|
|
|
13
|
-
const useStyles = makeStyles(
|
|
14
|
-
button: {
|
|
15
|
-
padding: '0px 5px'
|
|
16
|
-
},
|
|
13
|
+
const useStyles = makeStyles(theme => ({
|
|
17
14
|
divider: {
|
|
18
15
|
marginTop: '10px',
|
|
19
16
|
marginBottom: '10px'
|
|
17
|
+
},
|
|
18
|
+
secondaryButton: {
|
|
19
|
+
backgroundColor: theme.actionButtons.secondary.backgroundColor,
|
|
20
|
+
color: theme.actionButtons.secondary.color
|
|
21
|
+
},
|
|
22
|
+
primaryButton: {
|
|
23
|
+
backgroundColor: theme.actionButtons.primary.backgroundColor,
|
|
24
|
+
color: theme.actionButtons.primary.color
|
|
20
25
|
}
|
|
21
26
|
}));
|
|
22
27
|
|
|
@@ -33,42 +38,44 @@ export default function ActionButtons(props: ActionButtonsProps) {
|
|
|
33
38
|
return (
|
|
34
39
|
<>
|
|
35
40
|
<Divider className={classes.divider} />
|
|
36
|
-
<
|
|
37
|
-
<
|
|
38
|
-
<
|
|
41
|
+
<Grid2 container spacing={4} justifyContent='space-between'>
|
|
42
|
+
<Grid2>
|
|
43
|
+
<Grid2 container spacing={1}>
|
|
39
44
|
{arSecondaryButtons.map(sButton => (
|
|
40
|
-
<
|
|
45
|
+
<Grid2 key={sButton.name}>
|
|
41
46
|
<Button
|
|
42
|
-
|
|
47
|
+
className={classes.secondaryButton}
|
|
43
48
|
color='secondary'
|
|
49
|
+
variant='contained'
|
|
44
50
|
onClick={() => {
|
|
45
51
|
_onButtonPress(sButton.jsAction, 'secondary');
|
|
46
52
|
}}
|
|
47
53
|
>
|
|
48
54
|
{localizedVal(sButton.name, localeCategory)}
|
|
49
55
|
</Button>
|
|
50
|
-
</
|
|
56
|
+
</Grid2>
|
|
51
57
|
))}
|
|
52
|
-
</
|
|
53
|
-
</
|
|
54
|
-
<
|
|
55
|
-
<
|
|
58
|
+
</Grid2>
|
|
59
|
+
</Grid2>
|
|
60
|
+
<Grid2>
|
|
61
|
+
<Grid2 container spacing={1}>
|
|
56
62
|
{arMainButtons.map(mButton => (
|
|
57
|
-
<
|
|
63
|
+
<Grid2 key={mButton.name}>
|
|
58
64
|
<Button
|
|
59
|
-
|
|
65
|
+
className={classes.primaryButton}
|
|
60
66
|
color='primary'
|
|
67
|
+
variant='contained'
|
|
61
68
|
onClick={() => {
|
|
62
69
|
_onButtonPress(mButton.jsAction, 'primary');
|
|
63
70
|
}}
|
|
64
71
|
>
|
|
65
72
|
{localizedVal(mButton.name, localeCategory)}
|
|
66
73
|
</Button>
|
|
67
|
-
</
|
|
74
|
+
</Grid2>
|
|
68
75
|
))}
|
|
69
|
-
</
|
|
70
|
-
</
|
|
71
|
-
</
|
|
76
|
+
</Grid2>
|
|
77
|
+
</Grid2>
|
|
78
|
+
</Grid2>
|
|
72
79
|
</>
|
|
73
80
|
);
|
|
74
81
|
}
|
|
@@ -13,7 +13,7 @@ interface AssignmentProps extends PConnProps {
|
|
|
13
13
|
itemKey: string;
|
|
14
14
|
isInModal: boolean;
|
|
15
15
|
banners: any[];
|
|
16
|
-
|
|
16
|
+
|
|
17
17
|
actionButtons: any[];
|
|
18
18
|
}
|
|
19
19
|
|
|
@@ -133,7 +133,7 @@ export default function Assignment(props: PropsWithChildren<AssignmentProps>) {
|
|
|
133
133
|
|
|
134
134
|
function showToast(message: string) {
|
|
135
135
|
const theMessage = `Assignment: ${message}`;
|
|
136
|
-
|
|
136
|
+
|
|
137
137
|
console.error(theMessage);
|
|
138
138
|
setSnackbarMessage(message);
|
|
139
139
|
setShowSnackbar(true);
|