@asaleh37/ui-base 26.2.131 → 27.5.26

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (176) hide show
  1. package/.env.development +1 -1
  2. package/.github/workflows/publish-npm.yml +49 -49
  3. package/README.md +51 -51
  4. package/__ODockerfile +14 -14
  5. package/dist/index.js +2 -2
  6. package/dist/index.js.map +1 -1
  7. package/dist/index.mjs +2 -2
  8. package/dist/index.mjs.map +1 -1
  9. package/eslint.config.js +29 -29
  10. package/index.html +20 -20
  11. package/package.json +122 -122
  12. package/public/manifest.json +21 -21
  13. package/rollup.config-1748377725725.cjs +50 -50
  14. package/rollup.config.js +45 -45
  15. package/src/components/App.tsx +155 -155
  16. package/src/components/BaseApp.tsx +75 -75
  17. package/src/components/ExampleTrial.tsx +24 -24
  18. package/src/components/administration/admin/ChangePasswordPanel.tsx +128 -128
  19. package/src/components/administration/admin/CustomPersonGrid.tsx +361 -361
  20. package/src/components/administration/admin/OrgMemberRoleForm.tsx +83 -83
  21. package/src/components/administration/admin/OrgProvidedPersonGrid.tsx +347 -347
  22. package/src/components/administration/admin/OrganizationApplicationModuleGrid.tsx +107 -107
  23. package/src/components/administration/admin/OrganizationGrid.tsx +118 -118
  24. package/src/components/administration/admin/OrganizationMemberGrid.tsx +190 -190
  25. package/src/components/administration/admin/OrganizationMemberRoleGrid.tsx +87 -87
  26. package/src/components/administration/admin/OrganizationRankGrid.tsx +133 -133
  27. package/src/components/administration/admin/OrganizationUnitGrid.tsx +143 -143
  28. package/src/components/administration/admin/OrganizationUnitTypeGrid.tsx +108 -108
  29. package/src/components/administration/admin/PersonGrid.tsx +27 -27
  30. package/src/components/administration/admin/RoleAuthoritiesForm.tsx +82 -82
  31. package/src/components/administration/admin/SystemApplicationAuthorityGrid.tsx +117 -117
  32. package/src/components/administration/admin/SystemApplicationGrid.tsx +83 -83
  33. package/src/components/administration/admin/SystemApplicationModuleGrid.tsx +96 -96
  34. package/src/components/administration/admin/SystemApplicationRoleAuthorityGrid.tsx +75 -75
  35. package/src/components/administration/admin/SystemApplicationRoleGrid.tsx +116 -116
  36. package/src/components/administration/dev/AttachmentConfigGrid.tsx +224 -224
  37. package/src/components/administration/dev/AttachmentGrid.tsx +172 -172
  38. package/src/components/administration/dev/BluePrintGrid.tsx +129 -129
  39. package/src/components/administration/dev/DashboardGrid.tsx +173 -173
  40. package/src/components/administration/dev/DashboardWidgetGrid.tsx +164 -164
  41. package/src/components/administration/dev/DataQueryGrid.tsx +216 -216
  42. package/src/components/administration/dev/DataQueryParameterGrid.tsx +191 -191
  43. package/src/components/administration/dev/DataQueryParametersForm.tsx +84 -84
  44. package/src/components/administration/dev/DatasourceConnectionGrid.tsx +151 -151
  45. package/src/components/administration/dev/EntityParameterGrid.tsx +322 -322
  46. package/src/components/administration/dev/LookupGrid.tsx +120 -120
  47. package/src/components/administration/dev/MailAttachmentGrid.tsx +172 -155
  48. package/src/components/administration/dev/MailBodyGrid.tsx +216 -216
  49. package/src/components/administration/dev/MailNotificationQueueGrid.tsx +245 -245
  50. package/src/components/administration/dev/MailRecipientGrid.tsx +170 -170
  51. package/src/components/administration/dev/MailSenderConfigGrid.tsx +486 -486
  52. package/src/components/administration/dev/MailTemplateGrid.tsx +385 -385
  53. package/src/components/administration/dev/NotificationGrid.tsx +435 -435
  54. package/src/components/administration/dev/NotificationQueueGrid.tsx +222 -222
  55. package/src/components/administration/dev/ReportGrid.tsx +503 -503
  56. package/src/components/administration/dev/ReportParameterGrid.tsx +186 -186
  57. package/src/components/administration/dev/ReportParametersForm.tsx +84 -84
  58. package/src/components/administration/dev/WidgetGrid.tsx +380 -380
  59. package/src/components/administration/dev/WorkflowDocumentActionGrid.tsx +264 -264
  60. package/src/components/administration/dev/WorkflowDocumentActionHistoryGrid.tsx +172 -172
  61. package/src/components/administration/dev/WorkflowDocumentActionMailGrid.tsx +161 -161
  62. package/src/components/administration/dev/WorkflowDocumentGrid.tsx +357 -357
  63. package/src/components/administration/dev/WorkflowDocumentMailLogGrid.tsx +218 -218
  64. package/src/components/administration/dev/WorkflowDocumentStatusGrid.tsx +243 -243
  65. package/src/components/common/AzureLogin.tsx +222 -222
  66. package/src/components/common/ChangeOrgForm.tsx +85 -85
  67. package/src/components/common/Home.tsx +43 -43
  68. package/src/components/common/LanguageSwitcher.tsx +25 -25
  69. package/src/components/common/LayoutHandlers.tsx +11 -11
  70. package/src/components/common/LoadingMask.tsx +24 -24
  71. package/src/components/common/Login.tsx +268 -268
  72. package/src/components/common/MobileLogin.tsx +229 -229
  73. package/src/components/common/MyNotificationsPanel.tsx +109 -109
  74. package/src/components/common/NoLicenseComponent.tsx +79 -79
  75. package/src/components/common/NotificationItem.tsx +138 -138
  76. package/src/components/index.ts +10 -10
  77. package/src/components/msalConfig.ts +11 -11
  78. package/src/components/templates/DataEntryTemplates/DataEntryTypes.ts +361 -361
  79. package/src/components/templates/DataEntryTemplates/DataEntryUtil.ts +297 -297
  80. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormAction.tsx +60 -60
  81. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormElementField.tsx +238 -238
  82. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormElementGroup.tsx +108 -108
  83. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/CheckBox.tsx +66 -66
  84. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/ComboBox.tsx +164 -164
  85. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/Datefield.tsx +70 -70
  86. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/DatetimeField.tsx +71 -71
  87. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/FiltersPanel.tsx +237 -237
  88. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/SystemLookupCombobox.tsx +56 -56
  89. package/src/components/templates/DataEntryTemplates/TemplateDataForm/FormFields/TemplateTextField.tsx +20 -20
  90. package/src/components/templates/DataEntryTemplates/TemplateDataForm/TemplateForm.tsx +431 -431
  91. package/src/components/templates/DataEntryTemplates/TemplateDataGrid/DataGridColumnsUtil.tsx +197 -197
  92. package/src/components/templates/DataEntryTemplates/TemplateDataGrid/TemplateGrid.tsx +1044 -1044
  93. package/src/components/templates/DataEntryTemplates/TemplateDataGrid/TemplateGridMultiRecordAction.tsx +89 -89
  94. package/src/components/templates/DataEntryTemplates/TemplateDataGrid/TemplateGridRecordAction.tsx +95 -95
  95. package/src/components/templates/DataEntryTemplates/TemplateDataGrid/TemplateGridTopBar.tsx +251 -251
  96. package/src/components/templates/TransferList.tsx +256 -256
  97. package/src/components/templates/Window/ConfirmationWindow.tsx +55 -55
  98. package/src/components/templates/attachment/AttachmentCard.tsx +141 -141
  99. package/src/components/templates/attachment/AttachmentImageViewer.tsx +85 -85
  100. package/src/components/templates/attachment/AttachmentPanel.tsx +285 -285
  101. package/src/components/templates/index.ts +35 -35
  102. package/src/components/templates/report/ExcelReportViewer.tsx +71 -71
  103. package/src/components/templates/report/ReportViewer.tsx +261 -261
  104. package/src/components/templates/report/ReportViewerRoute.tsx +9 -9
  105. package/src/components/templates/visuals/DashboardRouteView.tsx +9 -9
  106. package/src/components/templates/visuals/DashboardViewer.tsx +192 -192
  107. package/src/components/templates/visuals/WidgetViewer.tsx +208 -208
  108. package/src/components/templates/visuals/charts/TemplateBarChart.tsx +23 -23
  109. package/src/components/templates/visuals/charts/TemplateDataCard.tsx +35 -35
  110. package/src/components/templates/visuals/charts/TemplateGauge.tsx +21 -21
  111. package/src/components/templates/visuals/charts/TemplateLineChart.tsx +22 -22
  112. package/src/components/templates/visuals/charts/TemplateLineProgress.tsx +42 -42
  113. package/src/components/templates/visuals/charts/TemplatePieChart.tsx +24 -24
  114. package/src/components/templates/workflow/WorkflowDocumentPanel.tsx +611 -611
  115. package/src/components/templates/workflow/WorkflowDocumentTimeLine.tsx +145 -145
  116. package/src/components/templates/workflow/WorkflowRouteComponent.tsx +14 -14
  117. package/src/examples/ExampleGrid.tsx +134 -134
  118. package/src/hooks/UseConfirmationWindow.tsx +56 -56
  119. package/src/hooks/UseMobile.tsx +13 -13
  120. package/src/hooks/UseSession.tsx +59 -59
  121. package/src/hooks/UseWindow.tsx +111 -111
  122. package/src/hooks/index.ts +22 -22
  123. package/src/hooks/useApiActions.ts +124 -124
  124. package/src/hooks/useAxios.tsx +340 -340
  125. package/src/hooks/useCommonStore.tsx +29 -29
  126. package/src/hooks/useInterval.tsx +23 -23
  127. package/src/hooks/useLoadingMask.tsx +16 -16
  128. package/src/hooks/useLookupGridColumn.tsx +35 -35
  129. package/src/hooks/useParameterPanel.tsx +171 -171
  130. package/src/index.ts +4 -4
  131. package/src/layout/DrawerHeader.tsx +10 -10
  132. package/src/layout/Layout.tsx +102 -102
  133. package/src/layout/MainContent.tsx +115 -115
  134. package/src/layout/MobileDrawer.tsx +103 -103
  135. package/src/layout/NavigationTree.tsx +360 -360
  136. package/src/layout/NotificationButton.tsx +207 -207
  137. package/src/layout/RouteWrapper.tsx +63 -63
  138. package/src/layout/SideBar.tsx +85 -85
  139. package/src/layout/TopBar.tsx +317 -317
  140. package/src/locales/arabic/adminLocalsAr.json +94 -94
  141. package/src/locales/arabic/common.json +44 -44
  142. package/src/locales/arabic/devLocalsAr.json +317 -317
  143. package/src/locales/arabic/index.ts +9 -9
  144. package/src/locales/english/adminLocalsEn.json +97 -97
  145. package/src/locales/english/common.json +43 -43
  146. package/src/locales/english/devLocalsEn.json +318 -318
  147. package/src/locales/english/index.ts +9 -9
  148. package/src/locales/i18n.ts +8 -8
  149. package/src/locales/index.ts +9 -9
  150. package/src/main.tsx +41 -41
  151. package/src/navigationItems/Administration/adminNavigationItems.tsx +231 -231
  152. package/src/navigationItems/Administration/index.tsx +16 -16
  153. package/src/navigationItems/common/CommonNavigationItems.tsx +12 -12
  154. package/src/navigationItems/common/index.tsx +7 -7
  155. package/src/navigationItems/index.tsx +35 -35
  156. package/src/redux/features/administration/AdministrationStoresMetaData.ts +164 -164
  157. package/src/redux/features/common/AppInfoSlice.ts +95 -95
  158. package/src/redux/features/common/AppLayoutSlice.ts +29 -29
  159. package/src/redux/features/common/CommonStoreSlice.ts +44 -44
  160. package/src/redux/features/common/LoadingMaskSlice.ts +30 -30
  161. package/src/redux/features/common/SideBarSlice.ts +27 -27
  162. package/src/redux/features/common/UserSessionSlice.ts +54 -54
  163. package/src/redux/store.ts +29 -29
  164. package/src/routes/administration/adminRoutes.tsx +99 -99
  165. package/src/routes/administration/devRoutes.tsx +129 -129
  166. package/src/routes/administration/index.ts +10 -10
  167. package/src/routes/index.ts +5 -5
  168. package/src/routes/types/index.ts +6 -6
  169. package/src/styles/index.css +19 -19
  170. package/src/types/index.ts +8 -8
  171. package/src/util/AppUtils.ts +73 -73
  172. package/src/util/constants.ts +6 -6
  173. package/src/util/index.ts +5 -5
  174. package/tsconfig.json +135 -135
  175. package/vite.config.ts +24 -24
  176. package/package-lock.json/342/200/216 +0 -9040
@@ -1,71 +1,71 @@
1
- import { useEffect, useState } from "react";
2
- import TemplateGrid from "../DataEntryTemplates/TemplateDataGrid/TemplateGrid";
3
- import { FormElementProps } from "../DataEntryTemplates/DataEntryTypes";
4
-
5
- type ExcelReportViewerProps = {
6
- reportData: Array<any>;
7
- setReportData: (data) => void;
8
- reloadReport: () => void;
9
- gridLoadParameters?: Array<FormElementProps>;
10
- gridLoadParametersValues?: { [key: string]: any };
11
- setGridLoadParametersValues?: any;
12
- };
13
-
14
- const getGridColumnsFromRecord = (data: Array<any>) => {
15
- if (data.length === 0) {
16
- return [];
17
- }
18
- const formElements: Array<FormElementProps> = [];
19
- for (const key of Object.keys(data[0])) {
20
- const formElement: FormElementProps = {
21
- type: "field",
22
- mode: "props",
23
- props: {
24
- fieldLabel: key,
25
- fieldName: key,
26
- fieldType: "text",
27
- },
28
- };
29
- formElements.push(formElement);
30
- }
31
- return formElements;
32
- };
33
-
34
- const ExcelReportViewer: React.FC<ExcelReportViewerProps> = (props) => {
35
- const [data, setData] = useState([]);
36
- useEffect(() => {
37
- const newData = props.reportData.map((record, index) => {
38
- return { ...record, report_record_data_key: index };
39
- });
40
- setData(newData);
41
- }, [props.reportData]);
42
- return (
43
- <TemplateGrid
44
- data={data}
45
- disableDefaultAction={true}
46
- setData={props.setReportData}
47
- formElements={getGridColumnsFromRecord(props.reportData)}
48
- gridLoadParameters={props.gridLoadParameters}
49
- gridLoadParametersValues={props.gridLoadParametersValues}
50
- setGridLoadParametersValues={props.setGridLoadParametersValues}
51
- editMode={{ editMode: "none" }}
52
- girdIcon={"file-excel"}
53
- gridTitle="Report"
54
- autoLoad={true}
55
- keyColumnName={"report_record_data_key"}
56
- hideInfoBar={true}
57
- apiActions={{
58
- deleteRecordById: async () => {
59
- return true;
60
- },
61
- loadRecordById: async () => {},
62
- reloadData: async () => {
63
- props.reloadReport();
64
- },
65
- saveRecord: async () => {},
66
- }}
67
- />
68
- );
69
- };
70
-
71
- export default ExcelReportViewer;
1
+ import { useEffect, useState } from "react";
2
+ import TemplateGrid from "../DataEntryTemplates/TemplateDataGrid/TemplateGrid";
3
+ import { FormElementProps } from "../DataEntryTemplates/DataEntryTypes";
4
+
5
+ type ExcelReportViewerProps = {
6
+ reportData: Array<any>;
7
+ setReportData: (data) => void;
8
+ reloadReport: () => void;
9
+ gridLoadParameters?: Array<FormElementProps>;
10
+ gridLoadParametersValues?: { [key: string]: any };
11
+ setGridLoadParametersValues?: any;
12
+ };
13
+
14
+ const getGridColumnsFromRecord = (data: Array<any>) => {
15
+ if (data.length === 0) {
16
+ return [];
17
+ }
18
+ const formElements: Array<FormElementProps> = [];
19
+ for (const key of Object.keys(data[0])) {
20
+ const formElement: FormElementProps = {
21
+ type: "field",
22
+ mode: "props",
23
+ props: {
24
+ fieldLabel: key,
25
+ fieldName: key,
26
+ fieldType: "text",
27
+ },
28
+ };
29
+ formElements.push(formElement);
30
+ }
31
+ return formElements;
32
+ };
33
+
34
+ const ExcelReportViewer: React.FC<ExcelReportViewerProps> = (props) => {
35
+ const [data, setData] = useState([]);
36
+ useEffect(() => {
37
+ const newData = props.reportData.map((record, index) => {
38
+ return { ...record, report_record_data_key: index };
39
+ });
40
+ setData(newData);
41
+ }, [props.reportData]);
42
+ return (
43
+ <TemplateGrid
44
+ data={data}
45
+ disableDefaultAction={true}
46
+ setData={props.setReportData}
47
+ formElements={getGridColumnsFromRecord(props.reportData)}
48
+ gridLoadParameters={props.gridLoadParameters}
49
+ gridLoadParametersValues={props.gridLoadParametersValues}
50
+ setGridLoadParametersValues={props.setGridLoadParametersValues}
51
+ editMode={{ editMode: "none" }}
52
+ girdIcon={"file-excel"}
53
+ gridTitle="Report"
54
+ autoLoad={true}
55
+ keyColumnName={"report_record_data_key"}
56
+ hideInfoBar={true}
57
+ apiActions={{
58
+ deleteRecordById: async () => {
59
+ return true;
60
+ },
61
+ loadRecordById: async () => {},
62
+ reloadData: async () => {
63
+ props.reloadReport();
64
+ },
65
+ saveRecord: async () => {},
66
+ }}
67
+ />
68
+ );
69
+ };
70
+
71
+ export default ExcelReportViewer;
@@ -1,261 +1,261 @@
1
- import { useEffect, useState } from "react";
2
- import { useAxios } from "../../../hooks";
3
-
4
- import { Box, IconButton } from "@mui/material";
5
- import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
6
- import ExcelReportViewer from "./ExcelReportViewer";
7
- import { useParameterPanel } from "../../../hooks/useParameterPanel";
8
-
9
- type ReportViewerState =
10
- | "ERROR"
11
- | "WAITING_REPORT_CODE"
12
- | "LOADING_METADATA"
13
- | "WAITING_PARAMETER_INPUT"
14
- | "WAITING_RESULT"
15
- | "SHOWING_RESULT";
16
-
17
- type ReportViewerProps = {
18
- reportCode: string;
19
- resultMode: "Request" | "App";
20
- reportParametersValues?: { [key: string]: any };
21
- byPassParameterEntry?: boolean;
22
- jasperOutPutFileType?: "pdf" | "word" | "excel";
23
- };
24
-
25
- const ReportViewer: React.FC<ReportViewerProps> = (props) => {
26
- const [blobUrl, setBlobUrl] = useState(null);
27
- const [errorMessage, setErrorMessage] = useState(null);
28
- const [excelReportData, setExcelReportData] = useState<Array<any>>([]);
29
- const [reportViewerState, setReportViewerState] = useState<ReportViewerState>(
30
- "WAITING_REPORT_CODE",
31
- );
32
- const { handleGetRequest, handlePostRequest, HandleDownloadHTTPPostPDF } =
33
- useAxios();
34
- const [reportInfo, setReportInfo] = useState<any>(null);
35
- const {
36
- ParameterPanel,
37
- parametersValues,
38
- panelElements,
39
- setParametersValues,
40
- } = useParameterPanel({
41
- parameters: reportInfo?.reportParameters || [],
42
- initialParameterValues: { ...props?.reportParametersValues },
43
- });
44
- const loadReportData = async () => {
45
- setReportViewerState("LOADING_METADATA");
46
- await handleGetRequest({
47
- endPointURI: "api/v1/public/report/metadata",
48
- showMask: true,
49
- parameters: { reportCode: props.reportCode },
50
- successCallBkFn: (response: any) => {
51
- setReportInfo(response.data);
52
- },
53
- failureCallBkFn: (response) => {
54
- setErrorMessage(
55
- "Failed loading report metadata ... contact your administrator",
56
- );
57
- setReportViewerState("ERROR");
58
- },
59
- });
60
- };
61
-
62
- useEffect(() => {
63
- if (reportInfo) {
64
- if (
65
- props?.byPassParameterEntry === true ||
66
- reportInfo.reportParameters.length == 0
67
- ) {
68
- runReport(parametersValues);
69
- setReportViewerState("WAITING_RESULT");
70
- } else {
71
- setReportViewerState("WAITING_PARAMETER_INPUT");
72
- }
73
- }
74
- }, [reportInfo]);
75
-
76
- const runReport = async (params) => {
77
- setReportViewerState("WAITING_RESULT");
78
- if (reportInfo?.reportType === "Excel") {
79
- await handlePostRequest({
80
- endPointURI: "api/v1/public/report/run",
81
- showMask: true,
82
- data: {
83
- reportCode: props.reportCode,
84
- parameters: params,
85
- resultMode: props.resultMode,
86
- jasperOutPutFileType: props.jasperOutPutFileType,
87
- },
88
- successCallBkFn: (response: any) => {
89
- setReportViewerState("SHOWING_RESULT");
90
- setExcelReportData(response.data);
91
- },
92
- });
93
- } else if (reportInfo?.reportType) {
94
- await HandleDownloadHTTPPostPDF({
95
- endPointURI: "api/v1/public/report/run",
96
- showMask: true,
97
- data: {
98
- reportCode: props.reportCode,
99
- parameters: params,
100
- resultMode: props.resultMode,
101
- jasperOutPutFileType: props.jasperOutPutFileType,
102
- },
103
- successCallBkFn: (response: any) => {
104
- setReportViewerState("SHOWING_RESULT");
105
- const contentDisposition = response.headers["content-disposition"];
106
- let filename = "downloaded_file";
107
- if (
108
- contentDisposition &&
109
- contentDisposition.indexOf("filename=") !== -1
110
- ) {
111
- const match = contentDisposition.match(/filename="?([^"]+)"?/);
112
- if (match && match[1]) filename = match[1];
113
- }
114
- if (filename.includes("pdf")) {
115
- const file = new Blob([response.data], { type: "application/pdf" });
116
- const url = URL.createObjectURL(file);
117
- setBlobUrl(url);
118
- } else {
119
- const blob = new Blob([response.data], {
120
- type: response.headers["content-type"],
121
- });
122
- // Create a temporary anchor element
123
- const url = window.URL.createObjectURL(blob);
124
- const link = document.createElement("a");
125
- link.href = url;
126
- // Optional: Try to get filename from response headers
127
-
128
- link.download = filename;
129
- document.body.appendChild(link);
130
- link.click();
131
-
132
- // Clean up
133
- document.body.removeChild(link);
134
- window.URL.revokeObjectURL(url);
135
- }
136
- },
137
- failureCallBkFn: (response) => {
138
- setErrorMessage(
139
- "Failed To run report ... contact your administrator",
140
- );
141
- setReportViewerState("ERROR");
142
- },
143
- });
144
- }
145
- };
146
-
147
- useEffect(() => {
148
- if (props?.reportCode) {
149
- loadReportData();
150
- }
151
- }, [
152
- props.reportCode,
153
- props.byPassParameterEntry,
154
- props.reportParametersValues,
155
- props.jasperOutPutFileType,
156
- props.resultMode,
157
- ]);
158
-
159
- return (
160
- <>
161
- <Box
162
- sx={{
163
- // display: "flex",
164
- // alignItems: "center",
165
- // justifyContent: "center",
166
- width: "100%",
167
- }}
168
- >
169
- <Box sx={{ flex: 1, textAlign: "center", marginBottom: 1 }}>
170
- <FontAwesomeIcon
171
- icon={
172
- reportInfo?.reportType === "Excel" ? "file-excel" : "file-pdf"
173
- }
174
- color={reportInfo?.reportType === "Excel" ? "darkgreen" : "darkred"}
175
- style={{ marginRight: 10, marginLeft: 10 }}
176
- />
177
- {reportInfo?.reportName}
178
- </Box>
179
- {reportInfo?.reportType != "Excel" ? (
180
- reportViewerState === "SHOWING_RESULT" ? (
181
- <>
182
- {props?.byPassParameterEntry === true ? (
183
- <></>
184
- ) : reportInfo?.reportParameters.length > 0 ? (
185
- <IconButton
186
- onClick={() => {
187
- setReportViewerState("WAITING_PARAMETER_INPUT");
188
- }}
189
- >
190
- <FontAwesomeIcon icon="filter" />
191
- </IconButton>
192
- ) : (
193
- <></>
194
- )}
195
- <IconButton>
196
- <FontAwesomeIcon
197
- icon="refresh"
198
- onClick={() => {
199
- runReport(parametersValues);
200
- }}
201
- />
202
- </IconButton>
203
- </>
204
- ) : (
205
- <></>
206
- )
207
- ) : (
208
- <></>
209
- )}
210
- </Box>
211
- {reportViewerState === "WAITING_PARAMETER_INPUT" &&
212
- reportInfo?.reportType != "Excel" ? (
213
- <ParameterPanel searchBtnClickCallBk={runReport} />
214
- ) : reportViewerState === "SHOWING_RESULT" ||
215
- ((reportViewerState === "WAITING_PARAMETER_INPUT" ||
216
- reportViewerState === "WAITING_RESULT") &&
217
- reportInfo?.reportType === "Excel") ? (
218
- reportInfo?.reportType === "Excel" ? (
219
- <ExcelReportViewer
220
- reportData={excelReportData}
221
- setReportData={setExcelReportData}
222
- reloadReport={async () => {
223
- runReport(parametersValues);
224
- }}
225
- gridLoadParameters={panelElements}
226
- gridLoadParametersValues={parametersValues}
227
- setGridLoadParametersValues={setParametersValues}
228
- />
229
- ) : (
230
- <iframe
231
- src={blobUrl}
232
- width="100%"
233
- height="100%"
234
- title="PDF Preview"
235
- style={{ border: "1px solid #ccc", marginTop: "20px" }}
236
- ></iframe>
237
- )
238
- ) : reportViewerState === "ERROR" ? (
239
- <Box
240
- sx={{
241
- display: "flex",
242
- flex: 1,
243
- alignItems: "center",
244
- justifyContent: "center",
245
- }}
246
- >
247
- <FontAwesomeIcon
248
- icon="circle-exclamation"
249
- color="darkred"
250
- style={{ marginRight: 10, marginLeft: 10 }}
251
- />
252
- {errorMessage}
253
- </Box>
254
- ) : (
255
- <></>
256
- )}
257
- </>
258
- );
259
- };
260
-
261
- export default ReportViewer;
1
+ import { useEffect, useState } from "react";
2
+ import { useAxios } from "../../../hooks";
3
+
4
+ import { Box, IconButton } from "@mui/material";
5
+ import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
6
+ import ExcelReportViewer from "./ExcelReportViewer";
7
+ import { useParameterPanel } from "../../../hooks/useParameterPanel";
8
+
9
+ type ReportViewerState =
10
+ | "ERROR"
11
+ | "WAITING_REPORT_CODE"
12
+ | "LOADING_METADATA"
13
+ | "WAITING_PARAMETER_INPUT"
14
+ | "WAITING_RESULT"
15
+ | "SHOWING_RESULT";
16
+
17
+ type ReportViewerProps = {
18
+ reportCode: string;
19
+ resultMode: "Request" | "App";
20
+ reportParametersValues?: { [key: string]: any };
21
+ byPassParameterEntry?: boolean;
22
+ jasperOutPutFileType?: "pdf" | "word" | "excel";
23
+ };
24
+
25
+ const ReportViewer: React.FC<ReportViewerProps> = (props) => {
26
+ const [blobUrl, setBlobUrl] = useState(null);
27
+ const [errorMessage, setErrorMessage] = useState(null);
28
+ const [excelReportData, setExcelReportData] = useState<Array<any>>([]);
29
+ const [reportViewerState, setReportViewerState] = useState<ReportViewerState>(
30
+ "WAITING_REPORT_CODE",
31
+ );
32
+ const { handleGetRequest, handlePostRequest, HandleDownloadHTTPPostPDF } =
33
+ useAxios();
34
+ const [reportInfo, setReportInfo] = useState<any>(null);
35
+ const {
36
+ ParameterPanel,
37
+ parametersValues,
38
+ panelElements,
39
+ setParametersValues,
40
+ } = useParameterPanel({
41
+ parameters: reportInfo?.reportParameters || [],
42
+ initialParameterValues: { ...props?.reportParametersValues },
43
+ });
44
+ const loadReportData = async () => {
45
+ setReportViewerState("LOADING_METADATA");
46
+ await handleGetRequest({
47
+ endPointURI: "api/v1/public/report/metadata",
48
+ showMask: true,
49
+ parameters: { reportCode: props.reportCode },
50
+ successCallBkFn: (response: any) => {
51
+ setReportInfo(response.data);
52
+ },
53
+ failureCallBkFn: (response) => {
54
+ setErrorMessage(
55
+ "Failed loading report metadata ... contact your administrator",
56
+ );
57
+ setReportViewerState("ERROR");
58
+ },
59
+ });
60
+ };
61
+
62
+ useEffect(() => {
63
+ if (reportInfo) {
64
+ if (
65
+ props?.byPassParameterEntry === true ||
66
+ reportInfo.reportParameters.length == 0
67
+ ) {
68
+ runReport(parametersValues);
69
+ setReportViewerState("WAITING_RESULT");
70
+ } else {
71
+ setReportViewerState("WAITING_PARAMETER_INPUT");
72
+ }
73
+ }
74
+ }, [reportInfo]);
75
+
76
+ const runReport = async (params) => {
77
+ setReportViewerState("WAITING_RESULT");
78
+ if (reportInfo?.reportType === "Excel") {
79
+ await handlePostRequest({
80
+ endPointURI: "api/v1/public/report/run",
81
+ showMask: true,
82
+ data: {
83
+ reportCode: props.reportCode,
84
+ parameters: params,
85
+ resultMode: props.resultMode,
86
+ jasperOutPutFileType: props.jasperOutPutFileType,
87
+ },
88
+ successCallBkFn: (response: any) => {
89
+ setReportViewerState("SHOWING_RESULT");
90
+ setExcelReportData(response.data);
91
+ },
92
+ });
93
+ } else if (reportInfo?.reportType) {
94
+ await HandleDownloadHTTPPostPDF({
95
+ endPointURI: "api/v1/public/report/run",
96
+ showMask: true,
97
+ data: {
98
+ reportCode: props.reportCode,
99
+ parameters: params,
100
+ resultMode: props.resultMode,
101
+ jasperOutPutFileType: props.jasperOutPutFileType,
102
+ },
103
+ successCallBkFn: (response: any) => {
104
+ setReportViewerState("SHOWING_RESULT");
105
+ const contentDisposition = response.headers["content-disposition"];
106
+ let filename = "downloaded_file";
107
+ if (
108
+ contentDisposition &&
109
+ contentDisposition.indexOf("filename=") !== -1
110
+ ) {
111
+ const match = contentDisposition.match(/filename="?([^"]+)"?/);
112
+ if (match && match[1]) filename = match[1];
113
+ }
114
+ if (filename.includes("pdf")) {
115
+ const file = new Blob([response.data], { type: "application/pdf" });
116
+ const url = URL.createObjectURL(file);
117
+ setBlobUrl(url);
118
+ } else {
119
+ const blob = new Blob([response.data], {
120
+ type: response.headers["content-type"],
121
+ });
122
+ // Create a temporary anchor element
123
+ const url = window.URL.createObjectURL(blob);
124
+ const link = document.createElement("a");
125
+ link.href = url;
126
+ // Optional: Try to get filename from response headers
127
+
128
+ link.download = filename;
129
+ document.body.appendChild(link);
130
+ link.click();
131
+
132
+ // Clean up
133
+ document.body.removeChild(link);
134
+ window.URL.revokeObjectURL(url);
135
+ }
136
+ },
137
+ failureCallBkFn: (response) => {
138
+ setErrorMessage(
139
+ "Failed To run report ... contact your administrator",
140
+ );
141
+ setReportViewerState("ERROR");
142
+ },
143
+ });
144
+ }
145
+ };
146
+
147
+ useEffect(() => {
148
+ if (props?.reportCode) {
149
+ loadReportData();
150
+ }
151
+ }, [
152
+ props.reportCode,
153
+ props.byPassParameterEntry,
154
+ props.reportParametersValues,
155
+ props.jasperOutPutFileType,
156
+ props.resultMode,
157
+ ]);
158
+
159
+ return (
160
+ <>
161
+ <Box
162
+ sx={{
163
+ // display: "flex",
164
+ // alignItems: "center",
165
+ // justifyContent: "center",
166
+ width: "100%",
167
+ }}
168
+ >
169
+ <Box sx={{ flex: 1, textAlign: "center", marginBottom: 1 }}>
170
+ <FontAwesomeIcon
171
+ icon={
172
+ reportInfo?.reportType === "Excel" ? "file-excel" : "file-pdf"
173
+ }
174
+ color={reportInfo?.reportType === "Excel" ? "darkgreen" : "darkred"}
175
+ style={{ marginRight: 10, marginLeft: 10 }}
176
+ />
177
+ {reportInfo?.reportName}
178
+ </Box>
179
+ {reportInfo?.reportType != "Excel" ? (
180
+ reportViewerState === "SHOWING_RESULT" ? (
181
+ <>
182
+ {props?.byPassParameterEntry === true ? (
183
+ <></>
184
+ ) : reportInfo?.reportParameters.length > 0 ? (
185
+ <IconButton
186
+ onClick={() => {
187
+ setReportViewerState("WAITING_PARAMETER_INPUT");
188
+ }}
189
+ >
190
+ <FontAwesomeIcon icon="filter" />
191
+ </IconButton>
192
+ ) : (
193
+ <></>
194
+ )}
195
+ <IconButton>
196
+ <FontAwesomeIcon
197
+ icon="refresh"
198
+ onClick={() => {
199
+ runReport(parametersValues);
200
+ }}
201
+ />
202
+ </IconButton>
203
+ </>
204
+ ) : (
205
+ <></>
206
+ )
207
+ ) : (
208
+ <></>
209
+ )}
210
+ </Box>
211
+ {reportViewerState === "WAITING_PARAMETER_INPUT" &&
212
+ reportInfo?.reportType != "Excel" ? (
213
+ <ParameterPanel searchBtnClickCallBk={runReport} />
214
+ ) : reportViewerState === "SHOWING_RESULT" ||
215
+ ((reportViewerState === "WAITING_PARAMETER_INPUT" ||
216
+ reportViewerState === "WAITING_RESULT") &&
217
+ reportInfo?.reportType === "Excel") ? (
218
+ reportInfo?.reportType === "Excel" ? (
219
+ <ExcelReportViewer
220
+ reportData={excelReportData}
221
+ setReportData={setExcelReportData}
222
+ reloadReport={async () => {
223
+ runReport(parametersValues);
224
+ }}
225
+ gridLoadParameters={panelElements}
226
+ gridLoadParametersValues={parametersValues}
227
+ setGridLoadParametersValues={setParametersValues}
228
+ />
229
+ ) : (
230
+ <iframe
231
+ src={blobUrl}
232
+ width="100%"
233
+ height="100%"
234
+ title="PDF Preview"
235
+ style={{ border: "1px solid #ccc", marginTop: "20px" }}
236
+ ></iframe>
237
+ )
238
+ ) : reportViewerState === "ERROR" ? (
239
+ <Box
240
+ sx={{
241
+ display: "flex",
242
+ flex: 1,
243
+ alignItems: "center",
244
+ justifyContent: "center",
245
+ }}
246
+ >
247
+ <FontAwesomeIcon
248
+ icon="circle-exclamation"
249
+ color="darkred"
250
+ style={{ marginRight: 10, marginLeft: 10 }}
251
+ />
252
+ {errorMessage}
253
+ </Box>
254
+ ) : (
255
+ <></>
256
+ )}
257
+ </>
258
+ );
259
+ };
260
+
261
+ export default ReportViewer;