@ampath/esm-reports-app 1.0.0-next.41 → 1.0.0-next.45

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 (183) hide show
  1. package/dist/143.css +1 -0
  2. package/dist/143.css.map +1 -0
  3. package/dist/143.js +1 -0
  4. package/dist/143.js.map +1 -0
  5. package/dist/197.js +1 -1
  6. package/dist/282.js +1 -1
  7. package/dist/282.js.map +1 -1
  8. package/dist/295.css +1 -0
  9. package/dist/295.css.map +1 -0
  10. package/dist/295.js +1 -0
  11. package/dist/295.js.map +1 -0
  12. package/dist/300.js +1 -1
  13. package/dist/311.js +1 -1
  14. package/dist/311.js.map +1 -1
  15. package/dist/335.js +1 -1
  16. package/dist/353.js +1 -1
  17. package/dist/353.js.map +1 -1
  18. package/dist/410.js +1 -0
  19. package/dist/410.js.map +1 -0
  20. package/dist/427.js +2 -0
  21. package/dist/427.js.LICENSE.txt +35 -0
  22. package/dist/427.js.map +1 -0
  23. package/dist/441.js +1 -0
  24. package/dist/441.js.map +1 -0
  25. package/dist/478.js +1 -1
  26. package/dist/478.js.map +1 -1
  27. package/dist/540.js +1 -1
  28. package/dist/540.js.map +1 -1
  29. package/dist/55.js +1 -1
  30. package/dist/652.js +1 -1
  31. package/dist/961.js +1 -1
  32. package/dist/961.js.map +1 -1
  33. package/dist/99.js +1 -1
  34. package/dist/ampath-esm-reports-app.js +1 -1
  35. package/dist/ampath-esm-reports-app.js.map +1 -1
  36. package/dist/routes.json +1 -1
  37. package/package.json +2 -2
  38. package/src/common/report-error/index.ts +1 -0
  39. package/src/common/report-error/show-report-error.ts +25 -0
  40. package/src/common/report-filters/date-range.ts +137 -0
  41. package/src/common/report-filters/index.ts +4 -0
  42. package/src/common/report-filters/report-filters.component.tsx +281 -151
  43. package/src/common/report-filters/report-filters.scss +180 -55
  44. package/src/common/report-filters/types.ts +66 -0
  45. package/src/common/report-filters/use-restore-period.ts +43 -0
  46. package/src/common/report-page/index.ts +2 -0
  47. package/src/common/report-page/report-page.component.tsx +32 -0
  48. package/src/common/report-page/report-page.scss +45 -0
  49. package/src/common/report-page/use-page-scale.ts +50 -0
  50. package/src/common/report-placeholder/has-report-data.ts +15 -0
  51. package/src/common/report-placeholder/index.ts +2 -0
  52. package/src/common/report-placeholder/report-placeholder.component.tsx +56 -0
  53. package/src/common/report-placeholder/report-placeholder.scss +46 -0
  54. package/src/common/report-register/index.ts +5 -0
  55. package/src/common/report-register/register-columns.ts +34 -0
  56. package/src/common/report-register/register-layout.component.tsx +237 -0
  57. package/src/common/report-register/register-layout.scss +140 -0
  58. package/src/common/report-register/register-table.scss +62 -0
  59. package/src/common/report-register/report-parents.ts +27 -0
  60. package/src/common/report-register/rows-to-csv.ts +59 -0
  61. package/src/common/report-register/use-patient-list.ts +92 -0
  62. package/src/common/report-skeleton/index.ts +1 -0
  63. package/src/common/report-skeleton/report-skeleton.component.tsx +46 -0
  64. package/src/common/report-skeleton/report-skeleton.scss +29 -0
  65. package/src/config-schema.ts +9 -1
  66. package/src/dashboard/report-catalog.ts +173 -0
  67. package/src/dashboard/reports-dasboard.tsx +101 -35
  68. package/src/dashboard/reports-dashboard.module.scss +269 -11
  69. package/src/index.ts +13 -1
  70. package/src/reports/datatable-wrapper/datatable-wrapper.component.tsx +50 -48
  71. package/src/reports/moh-240/moh-240-header.component.tsx +54 -56
  72. package/src/reports/moh-240/moh-240.columns.ts +64 -0
  73. package/src/reports/moh-240/moh-240.component.tsx +65 -84
  74. package/src/reports/moh-240/moh-240.scss +36 -7
  75. package/src/reports/moh-240/sub-reports/moh-240-register.component.tsx +27 -65
  76. package/src/reports/moh-240/sub-reports/page-summary.component.tsx +2 -2
  77. package/src/reports/moh-505/moh-505-header.component.tsx +59 -57
  78. package/src/reports/moh-505/moh-505.component.tsx +51 -56
  79. package/src/reports/moh-505/moh-505.scss +116 -2
  80. package/src/reports/moh-705B/moh-204b-register.component.tsx +41 -42
  81. package/src/reports/moh-705B/moh-204b.columns.ts +39 -0
  82. package/src/reports/moh-705B/moh-705b.component.tsx +492 -473
  83. package/src/reports/moh-705B/moh-705b.scss +110 -24
  84. package/src/reports/moh-705a/moh-705a.component.tsx +496 -476
  85. package/src/reports/moh-705a/moh-705a.scss +109 -24
  86. package/src/reports/moh-705a/registers/moh-204a-register.component.tsx +41 -42
  87. package/src/reports/moh-705a/registers/moh-204a.columns.ts +57 -0
  88. package/src/reports/moh-706/moh-706-header.component.tsx +58 -56
  89. package/src/reports/moh-706/moh-706.component.tsx +84 -55
  90. package/src/reports/moh-706/moh-706.scss +115 -19
  91. package/src/reports/moh-710/moh-710.component.tsx +743 -727
  92. package/src/reports/moh-710/moh-710.scss +140 -23
  93. package/src/reports/moh-710/registers/moh-511-710-register.component.tsx +48 -43
  94. package/src/reports/moh-710/registers/moh-511-710.columns.ts +52 -0
  95. package/src/reports/moh-711/moh-711.component.tsx +94 -106
  96. package/src/reports/moh-711/moh711.scss +95 -64
  97. package/src/reports/moh-711/registers/moh-333-register.component.tsx +92 -94
  98. package/src/reports/moh-711/registers/moh-333.columns.ts +119 -0
  99. package/src/reports/moh-711/registers/moh-405-register.component.tsx +88 -89
  100. package/src/reports/moh-711/registers/moh-405.columns.ts +120 -0
  101. package/src/reports/moh-711/registers/moh-406-register.component.tsx +85 -88
  102. package/src/reports/moh-711/registers/moh-406.columns.ts +133 -0
  103. package/src/reports/moh-711/registers/moh-510-register.component.tsx +38 -44
  104. package/src/reports/moh-711/registers/moh-511-register.component.tsx +42 -43
  105. package/src/reports/moh-711/registers/moh-511.columns.ts +59 -0
  106. package/src/reports/moh-711/sections/anc.component.tsx +3 -3
  107. package/src/reports/moh-711/sections/cervical-cancer.component.tsx +3 -3
  108. package/src/reports/moh-711/sections/chanis.component.tsx +2 -3
  109. package/src/reports/moh-711/sections/family-planning.component.tsx +2 -2
  110. package/src/reports/moh-711/sections/gbv.component.tsx +2 -2
  111. package/src/reports/moh-711/sections/maternity.component.tsx +3 -8
  112. package/src/reports/moh-711/sections/medical-social-work.component.tsx +2 -12
  113. package/src/reports/moh-711/sections/other.component.tsx +2 -2
  114. package/src/reports/moh-711/sections/physiotherapy.component.tsx +2 -2
  115. package/src/reports/moh-711/sections/pnc.component.tsx +7 -5
  116. package/src/reports/moh-711/sections/post-abortion.component.tsx +2 -2
  117. package/src/reports/moh-711/sections/rehabilitation.component.tsx +2 -2
  118. package/src/reports/moh-711/sections/report-compiled-by.component.tsx +12 -4
  119. package/src/reports/moh-711/sections/tb-screening.component.tsx +2 -2
  120. package/src/reports/moh-717/moh-717.component.tsx +100 -121
  121. package/src/reports/moh-717/moh717.scss +163 -102
  122. package/src/reports/moh-717/sections/maternity.component.tsx +1 -1
  123. package/src/reports/moh-717/sections/orthopaedic-trauma.component.tsx +1 -1
  124. package/src/reports/moh-717/sections/outpatient.component.tsx +23 -23
  125. package/src/reports/moh-717/sections/preparedby.component.tsx +7 -2
  126. package/src/reports/moh-717/sections/special-services.component.tsx +1 -1
  127. package/src/reports/moh-731/moh-731.component.tsx +127 -110
  128. package/src/reports/moh-731/moh-731.scss +396 -68
  129. package/src/reports/moh-731/registers/moh-366.columns.ts +38 -0
  130. package/src/reports/moh-731/registers/moh-366.component.tsx +76 -83
  131. package/src/reports/moh-731/registers/prep-register.component.tsx +70 -78
  132. package/src/reports/moh-731/registers/prep.columns.ts +34 -0
  133. package/src/reports/moh-731/sections/hiv-and-tb-treatment.component.tsx +1031 -751
  134. package/src/reports/moh-731/sections/hiv-testing-and-pre-exposure.component.tsx +230 -86
  135. package/src/reports/moh-731/sections/pmtct.component.tsx +185 -64
  136. package/src/reports/moh-740/moh-740.component.scss +159 -79
  137. package/src/reports/moh-740/moh-740.component.tsx +261 -230
  138. package/src/reports/moh-740/moh-740.resource.ts +17 -10
  139. package/src/reports/moh-740/registers/moh-222-daily-register/moh-222-daily-register.tsx +77 -96
  140. package/src/reports/moh-740/registers/moh-270-permanent-register/moh-270-permanent-register.tsx +50 -70
  141. package/src/reports/moh-740/registers/moh-740-patient-list.tsx +61 -32
  142. package/src/reports/moh-740/registers/moh-740.columns.ts +52 -0
  143. package/src/reports/moh-740/shared/utils/indicator-register-map.ts +3 -3
  144. package/src/reports/moh-740/types/index.ts +3 -3
  145. package/src/reports/moh-745/moh-745.component.tsx +897 -877
  146. package/src/reports/moh-745/moh-745.scss +104 -46
  147. package/src/reports/moh-745/registers/moh-412-register.component.tsx +42 -43
  148. package/src/reports/moh-745/registers/moh-412.columns.ts +52 -0
  149. package/src/reports/table-wrapper/table-wrapper.component.tsx +23 -14
  150. package/src/reports/table-wrapper/table-wrapper.scss +1 -16
  151. package/src/resources/moh-505.resource.ts +18 -35
  152. package/src/resources/moh-705.resource.ts +28 -39
  153. package/src/resources/moh-706.resource.ts +17 -30
  154. package/src/resources/moh-710.resource.ts +7 -17
  155. package/src/resources/moh-711.resource.ts +46 -64
  156. package/src/resources/moh-717.resource.ts +7 -17
  157. package/src/resources/moh-731.resource.ts +26 -32
  158. package/src/resources/moh-745.resource.ts +18 -20
  159. package/src/resources/patient-list-page.ts +66 -0
  160. package/src/root.component.tsx +28 -26
  161. package/src/root.scss +36 -0
  162. package/src/utils/get-base-url.ts +39 -7
  163. package/tsconfig.json +1 -1
  164. package/dist/110.js +0 -1
  165. package/dist/110.js.map +0 -1
  166. package/dist/184.js +0 -2
  167. package/dist/184.js.LICENSE.txt +0 -14
  168. package/dist/184.js.map +0 -1
  169. package/dist/205.js +0 -1
  170. package/dist/205.js.map +0 -1
  171. package/dist/812.js +0 -1
  172. package/dist/812.js.map +0 -1
  173. package/dist/822.js +0 -2
  174. package/dist/822.js.LICENSE.txt +0 -20
  175. package/dist/822.js.map +0 -1
  176. package/dist/ampath-esm-reports-app.js.buildmanifest.json +0 -560
  177. package/dist/main.js +0 -1
  178. package/dist/main.js.map +0 -1
  179. package/src/reports/moh-731/registers/moh-366.scss +0 -45
  180. package/src/reports/moh-731/registers/prep-registers.scss +0 -45
  181. package/src/reports/moh-740/registers/moh-222-daily-register/moh-222-daily-register.scss +0 -18
  182. package/src/reports/moh-740/registers/moh-270-permanent-register/moh-270-permanent-register.scss +0 -18
  183. /package/src/{reports/moh-740/shared/utils → utils}/format-indicator.ts +0 -0
@@ -1,45 +1,130 @@
1
+ @use '@openmrs/esm-styleguide/src/vars' as *;
1
2
 
2
- h3 {
3
- text-align: center;
3
+ /* MOH-705A laid out for A4, on the same scale as the other reports. Its 76 rows
4
+ are a single diagnoses table, so the sheet is one continuous form: masthead,
5
+ facility strip, table and sign-off share their edges. */
6
+
7
+ $ink: #000;
8
+ $rule: 1px solid $ink;
9
+
10
+ $text: 7pt;
11
+ $title: 7.5pt;
12
+ $meta: 6.5pt;
13
+
14
+ $pad: 3mm;
15
+
16
+ .mainTitleBox {
17
+ padding: $pad;
18
+ text-align: center;
19
+ border: $rule;
4
20
  }
5
21
 
6
- .container {
7
- margin: 0 2rem;
8
- margin-top: 0.5px;
22
+ .ministry {
23
+ font-size: $meta;
24
+ }
25
+
26
+ .reportTitle {
27
+ font-size: $title;
28
+ font-weight: 700;
29
+ color: $ink;
9
30
  }
10
31
 
11
- .tableContainer {
12
- margin-left: 1rem;
13
- margin-bottom: 1rem;
14
- font-weight: bold;
32
+ .location {
33
+ display: flex;
34
+ flex-wrap: nowrap;
35
+ align-items: baseline;
36
+ justify-content: space-between;
37
+ gap: 2.5mm;
38
+ padding: 2mm $pad;
39
+ font-size: $meta;
40
+ white-space: nowrap;
41
+ border: $rule;
42
+ border-top: none;
15
43
  }
16
44
 
17
- .sectionTitle {
18
- margin-left: 1rem ;
45
+ .line,
46
+ .shortLine {
47
+ display: inline-block;
48
+ padding: 0 0.5mm;
49
+ margin-left: 1mm;
50
+ overflow: hidden;
51
+ font-weight: 600;
52
+ text-align: center;
53
+ text-overflow: ellipsis;
54
+ vertical-align: bottom;
55
+ border-bottom: $rule;
19
56
  }
20
57
 
21
- .title {
22
- text-align: center;
23
- font-size: 1rem;
24
- margin: 1rem;
58
+ .line {
59
+ width: 26mm;
25
60
  }
61
+
62
+ .shortLine {
63
+ width: 14mm;
64
+ }
65
+
66
+ .container {
67
+ overflow-x: auto;
68
+ margin: 0;
69
+ }
70
+
26
71
  .table {
27
- width: auto;
72
+ width: 100%;
28
73
  border-collapse: collapse;
29
-
30
74
  }
31
75
 
32
76
  .tableBordered td,
33
77
  .tableBordered th {
34
- border: 1px solid black;
35
- padding: 1rem;
36
- font-size: small;
78
+ padding: 1mm 1.5mm;
79
+ font-size: $text;
80
+ text-align: left;
81
+ border: $rule;
82
+ }
83
+
84
+ .tableBordered th {
85
+ font-weight: 700;
86
+ color: $ink;
87
+ background-color: #f0f0f0;
37
88
  }
38
89
 
39
90
  .tableStriped tbody tr:nth-of-type(odd) {
40
- background-color: #f9f9f9;
91
+ background-color: #fafafa;
92
+ }
93
+
94
+ @media screen {
95
+ .tableStriped tbody tr:hover {
96
+ background-color: $brand-primary-10;
97
+ }
98
+ }
99
+
100
+ /* Sign-off, enclosed by the form. Three fields across the sheet, so its rules
101
+ are wider than the header strip's five. */
102
+
103
+ .signOff {
104
+ display: flex;
105
+ flex-wrap: nowrap;
106
+ align-items: baseline;
107
+ justify-content: space-between;
108
+ gap: 2.5mm;
109
+ padding: $pad;
110
+ font-size: $meta;
111
+ white-space: nowrap;
112
+ border: $rule;
113
+ border-top: none;
114
+
115
+ .line {
116
+ width: 45mm;
117
+ }
118
+
119
+ .shortLine {
120
+ width: 25mm;
121
+ }
41
122
  }
42
123
 
43
- .buttonContainer {
44
- margin: 1rem;
45
- }
124
+ /* On paper the striping is screen affordance that prints as grey noise */
125
+
126
+ @media print {
127
+ .tableStriped tbody tr:nth-of-type(odd) {
128
+ background-color: transparent;
129
+ }
130
+ }
@@ -1,60 +1,59 @@
1
- import React, { useEffect, useState } from 'react';
2
- import { Button, Loading, Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from '@carbon/react';
1
+ import React from 'react';
2
+ import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from '@carbon/react';
3
3
 
4
- import styles from '../moh-705a.scss';
4
+ import styles from '../../../common/report-register/register-table.scss';
5
5
  import classNames from 'classnames';
6
6
  import { useLocation, useNavigate, useSearchParams } from 'react-router-dom';
7
7
  import { getMoh705aPatientList } from '../../../resources/moh-705.resource';
8
+ import { moh204aExportColumns } from './moh-204a.columns';
9
+ import { RegisterLayout, usePatientList } from '../../../common/report-register';
8
10
 
9
11
  interface Moh204ARegisterComponentProps {}
10
12
 
11
13
  const Moh204ARegisterComponent: React.FC<Moh204ARegisterComponentProps> = () => {
12
- const [patientlist, setPatientList] = useState<any[]>([]);
13
- const [isLoading, setIsLoading] = useState<boolean>(false);
14
14
  const [searchParams] = useSearchParams();
15
- const navigate = useNavigate();
16
- const location = useLocation();
17
15
  const startDate = searchParams.get('startDate');
18
16
  const endDate = searchParams.get('endDate');
19
17
  const locationUuids = searchParams.get('locationUuids');
20
18
  const indicator = searchParams.get('indicator');
21
19
 
22
- function navigateBack() {
23
- navigate(location.state?.from || '/moh-705b');
24
- }
25
-
26
- useEffect(() => {
27
- const fetchData = async () => {
28
- if (!startDate || !endDate || !locationUuids || !indicator) return;
29
-
30
- setIsLoading(true);
31
-
32
- try {
33
- const params = {
34
- startDate,
35
- endDate,
36
- locationUuids,
37
- indicator,
38
- };
39
-
40
- const data = await getMoh705aPatientList(params);
41
- setPatientList(data?.results.results || []);
42
- } catch (error) {
43
- console.error('Failed to fetch register data', error);
44
- } finally {
45
- setIsLoading(false);
46
- }
47
- };
48
-
49
- fetchData();
50
- }, [startDate, endDate, locationUuids, indicator]);
20
+ const {
21
+ rows: patientlist,
22
+ total,
23
+ isTotalExact,
24
+ isLoading,
25
+ page,
26
+ pageSize,
27
+ onPageChange,
28
+ fetchAll,
29
+ } = usePatientList(
30
+ ({ startIndex, limit }) =>
31
+ getMoh705aPatientList({
32
+ startDate: startDate!,
33
+ endDate: endDate!,
34
+ locationUuids: locationUuids!,
35
+ indicator: indicator!,
36
+ startIndex,
37
+ limit,
38
+ }),
39
+ [startDate, endDate, locationUuids, indicator],
40
+ );
51
41
 
52
42
  return (
53
- <>
54
- <div className={styles.buttonContainer}>
55
- <Button onClick={navigateBack}>Back</Button>
56
- </div>
57
- <div>{isLoading && <Loading />}</div>
43
+ <RegisterLayout
44
+ parentLabel="MOH-705A Report"
45
+ parentPath="/moh-705a"
46
+ title="MOH 204A Under-5 Outpatient Register"
47
+ isLoading={isLoading}
48
+ isEmpty={patientlist.length === 0}
49
+ page={page}
50
+ pageSize={pageSize}
51
+ total={total}
52
+ isTotalExact={isTotalExact}
53
+ onPageChange={onPageChange}
54
+ fetchAll={fetchAll}
55
+ columns={moh204aExportColumns}
56
+ >
58
57
  <div className={styles.tableContainer}>
59
58
  <Table className={classNames(`${styles.table}`, `${styles.tableBordered}`, `${styles.tableStriped}`)}>
60
59
  <TableHead>
@@ -314,7 +313,7 @@ const Moh204ARegisterComponent: React.FC<Moh204ARegisterComponentProps> = () =>
314
313
  </TableBody>
315
314
  </Table>
316
315
  </div>
317
- </>
316
+ </RegisterLayout>
318
317
  );
319
318
  };
320
319
 
@@ -0,0 +1,57 @@
1
+ import { type RegisterColumn } from '../../../common/report-register';
2
+
3
+ /**
4
+ * MOH 204A as the register prints it: one column per cell, in the order they appear.
5
+ */
6
+ export const moh204aExportColumns: RegisterColumn[] = [
7
+ { header: 'Date (DD/MM/YYYY) - A', value: (row) => row.date ?? '' },
8
+ { header: 'OPD No. (New) - B', value: (row) => row.opd_number_new_visit ?? '' },
9
+ { header: 'OPD No. (Revisit) - C', value: (row) => row.opd_number_return_visit ?? '' },
10
+ { header: 'Referred From 1=CU, 2=From Other facility, 3= Within 4=N/A - D', value: (row) => row.referred_from ?? '' },
11
+ { header: 'Full Names (THREE names) - E', value: (row) => row.full_names ?? '' },
12
+ { header: 'Age - F', value: (row) => row.age ?? '' },
13
+ { header: 'Sex - G', value: (row) => row.sex ?? '' },
14
+ { header: 'Countu/Sub-county - H', value: (row) => row.county_sub_county ?? '' },
15
+ { header: 'Village /Estate / Landmark - I', value: (row) => row.village_estate_landmark ?? '' },
16
+ { header: "Parent/Caregivers's Telephone No. - J", value: (row) => row.caregiver_phone_number ?? '' },
17
+ { header: 'Weight(kg) - K', value: (row) => row.weight ?? '' },
18
+ { header: 'Height /Length (cm) - L', value: (row) => row.height ?? '' },
19
+ { header: 'MUAC 1.Green 2.Yellow 3.Red - M', value: (row) => row.muac ?? '' },
20
+ { header: 'Temp (oC) - N', value: (row) => row.temp ?? '' },
21
+ { header: 'Respiratory Rate - O', value: (row) => row.respiratory_rate ?? '' },
22
+ { header: 'Oxygen Saturation Reading (SPO2) - P', value: (row) => row.oxygen_saturation ?? '' },
23
+ { header: 'Pulse Rate - Q', value: (row) => row.pulse_rate ?? '' },
24
+ {
25
+ header:
26
+ 'DANGER SIGNS 1.Unable to drink or breastfeed 2.Vomits everything 3.Had convulsions in this illness 4.Is lethargic or unconscious 5.Is convulsing now - R',
27
+ value: (row) => row.danger_signs ?? '',
28
+ },
29
+ { header: 'Duration of Current Illness (in hours/ days) - S', value: (row) => row.duration_of_illness ?? '' },
30
+ {
31
+ header:
32
+ 'Malaria 1.Presenting with symptoms NOT Tested 2.RDT Tested (-ve) 3.Microscopy Tested (-ve) 4.RDT Tested (+ve) 5. Microscopy Tested (+ve) - T',
33
+ value: (row) => row.suspected_malaria_cases ?? '',
34
+ },
35
+ { header: 'IMNCI Classification or Diagnosis - U', value: (row) => row.diagnosis ?? '' },
36
+ {
37
+ header:
38
+ 'TRACER DRUGS PRESCRIBED 1. ORS & Zinc (Co-pack) 2.Zinc Only 3. ORS Only 4. Amoxicillin DT 5. Vitamin A 6.Oxygen 7. Albendazole 8.IV Fluids - V',
39
+ value: (row) => row.tracer_drugs_prescribed ?? '',
40
+ },
41
+ {
42
+ header: 'Other ALL Treatments Prescribed 1. CPAP 2. Other - W',
43
+ value: (row) => row.all_other_treatments_prescribed ?? '',
44
+ },
45
+ { header: 'Immunization Status Up to Date (Y/N) - X', value: (row) => row.immunization_status_up_to_date ?? '' },
46
+ { header: 'TB Screening 1. presumed TB 2. Referred - Y', value: (row) => row.tb_screening ?? '' },
47
+ {
48
+ header:
49
+ 'Nutrition and diatetics Interventions 1=Nutrition counselling 2=Nutrition therapeutic supplements 3 =. Diatetics - Z',
50
+ value: (row) => row.nutrition_dietetics ?? '',
51
+ },
52
+ {
53
+ header: 'Referred to (1=CU, 2= to other H/F, 3=within the facility/ 4=N/A) - AA',
54
+ value: (row) => row.referred_to ?? '',
55
+ },
56
+ { header: 'REMARKS/ Outcome - AB', value: (row) => row.remarks ?? '' },
57
+ ];
@@ -1,61 +1,63 @@
1
- import React, { useMemo } from "react";
2
- import TableWrapper from "../table-wrapper/table-wrapper.component";
3
- import TableRowMapper from "../table-wrapper/table-row-mapper.component";
4
- import { getCell } from "../../utils/utils";
1
+ import React, { useMemo } from 'react';
2
+ import dayjs from 'dayjs';
3
+ import TableWrapper from '../table-wrapper/table-wrapper.component';
4
+ import TableRowMapper from '../table-wrapper/table-row-mapper.component';
5
+ import { getCell } from '../../utils/utils';
5
6
  import styles from './moh-706.scss';
6
7
 
7
- const MOH706Header: React.FC = () => {
8
- const tableRows = useMemo(() => {
9
- return [
10
- {
11
- tableCells: [
12
- getCell("", "County:", 1, 1, true),
13
- getCell("", "", 3),
14
- ],
15
- },
16
- {
17
- tableCells: [
18
- getCell("", "Sub-County:", 1, 1, true),
19
- getCell("", "", 3),
20
- ],
21
- },
22
- {
23
- tableCells: [
24
- getCell("", "Health Facility:", 1, 1, true),
25
- getCell("", "", 3),
26
- ],
27
- },
28
- {
29
- tableCells: [
30
- getCell("", "KMHFL Code:", 1, 1, true),
31
- getCell("", "", 3),
32
- ],
33
- },
34
- {
35
- tableCells: [
36
- getCell("", "Facility Type:", 1, 1, true),
37
- getCell("", ""),
38
- getCell("", "Man. Agency:", 1, 1, true),
39
- getCell("", ""),
40
- ],
41
- },
42
- {
43
- tableCells: [
44
- getCell("", "Start Date:", 1, 1, true),
45
- getCell("", ""),
46
- getCell("", "End Date:", 1, 1, true),
47
- getCell("", ""),
48
- ],
49
- },
50
- ];
51
- }, []);
8
+ interface MOH706HeaderProps {
9
+ facility?: string;
10
+ startDate?: string;
11
+ endDate?: string;
12
+ }
13
+
14
+ const asDate = (value?: string) => (value ? dayjs(value).format('DD/MM/YYYY') : '');
52
15
 
53
- return <div className={styles.headerSection}>
54
- <h3>MOH 706 _Laboratory (LAB) Services Summary</h3>
55
- <TableWrapper>
56
- <TableRowMapper tableRows={tableRows} />
57
- </TableWrapper>
16
+ const MOH706Header: React.FC<MOH706HeaderProps> = ({ facility = '', startDate, endDate }) => {
17
+ const tableRows = useMemo(() => {
18
+ return [
19
+ {
20
+ tableCells: [getCell('', 'County:', 1, 1, true), getCell('', '', 3)],
21
+ },
22
+ {
23
+ tableCells: [getCell('', 'Sub-County:', 1, 1, true), getCell('', '', 3)],
24
+ },
25
+ {
26
+ tableCells: [getCell('', 'Health Facility:', 1, 1, true), getCell('', facility, 3)],
27
+ },
28
+ {
29
+ tableCells: [getCell('', 'KMHFL Code:', 1, 1, true), getCell('', '', 3)],
30
+ },
31
+ {
32
+ tableCells: [
33
+ getCell('', 'Facility Type:', 1, 1, true),
34
+ getCell('', ''),
35
+ getCell('', 'Man. Agency:', 1, 1, true),
36
+ getCell('', ''),
37
+ ],
38
+ },
39
+ {
40
+ tableCells: [
41
+ getCell('', 'Start Date:', 1, 1, true),
42
+ getCell('', asDate(startDate)),
43
+ getCell('', 'End Date:', 1, 1, true),
44
+ getCell('', asDate(endDate)),
45
+ ],
46
+ },
47
+ ];
48
+ }, [facility, startDate, endDate]);
49
+
50
+ return (
51
+ <div className={styles.headerSection}>
52
+ <div className={styles.mainTitleBox}>
53
+ <p className={styles.ministry}>Ministry of Health</p>
54
+ <h3 className={styles.reportTitle}>MOH 706 &ndash; Laboratory (LAB) Services Summary</h3>
55
+ </div>
56
+ <TableWrapper>
57
+ <TableRowMapper tableRows={tableRows} />
58
+ </TableWrapper>
58
59
  </div>
59
- }
60
+ );
61
+ };
60
62
 
61
- export default MOH706Header;
63
+ export default MOH706Header;
@@ -1,6 +1,6 @@
1
1
  import React, { useEffect, useState } from 'react';
2
- import { useSession } from '@openmrs/esm-framework';
3
- import { Column, Grid, Loading } from '@carbon/react';
2
+ import { formatDate, useSession } from '@openmrs/esm-framework';
3
+ import { Column, Grid } from '@carbon/react';
4
4
  import UrineAnalysis from './sub-reports/urine-analysis/urine-analysis.component';
5
5
  import BloodChemistry from './sub-reports/blood-chemistry/blood-chemistry.component';
6
6
  import Parasitology from './sub-reports/parasitology/parasitology.component';
@@ -10,21 +10,30 @@ import HistologyAndCytology from './sub-reports/histology-and-cytology/histology
10
10
  import Serology from './sub-reports/serology/serology.component';
11
11
  import SpecimenReferralToHigherLevels from './sub-reports/specimen-referral-to-higher-levels/specimen-referral-to-higher-levels.component';
12
12
  import DrugSusceptibilityTesting from './sub-reports/drug-susceptibility-testing/drug-susceptibility-testing.component';
13
- import ReportFiltersComponent from '../../common/report-filters/report-filters.component';
13
+ import { ReportFiltersComponent, type ReportPeriod } from '../../common/report-filters';
14
+ import { showReportError } from '../../common/report-error';
15
+ import { hasReportData, ReportPlaceholder } from '../../common/report-placeholder';
14
16
  import { getMoh706 } from '../../resources/moh-706.resource';
15
17
  import styles from './moh-706.scss';
16
18
  import MOH706Header from './moh-706-header.component';
17
19
  import { useSearchParams } from 'react-router-dom';
20
+ import { ReportSkeleton } from '../../common/report-skeleton';
21
+ import { ReportPage } from '../../common/report-page';
18
22
 
19
23
  const MoH706Report: React.FC = () => {
20
24
  const [moh706Data, setMoh706Data] = useState<any>({});
25
+ const isReportGenerated = hasReportData(moh706Data);
21
26
  const [isLoading, setIsLoading] = useState<boolean>(false);
22
- const [errorMessage, setErrorMessage] = useState<string>('');
23
27
  const [filters, setFilters] = useState<{ locationUuids?: string; startDate?: string; endDate?: string }>({});
24
28
 
25
29
  const session = useSession();
26
30
  const locationUuids = session?.sessionLocation?.uuid;
27
31
 
32
+ /* Masthead and sign-off fill themselves in, as on the other reports */
33
+ const facility = session?.sessionLocation?.display ?? '';
34
+ const compiledBy = session?.user?.person?.display ?? session?.user?.display ?? '';
35
+ const compiledOn = formatDate(new Date(), { mode: 'standard', time: false, noToday: true });
36
+
28
37
  const [searchParams] = useSearchParams();
29
38
 
30
39
  useEffect(() => {
@@ -37,29 +46,9 @@ const MoH706Report: React.FC = () => {
37
46
  }
38
47
  }, [searchParams]);
39
48
 
40
- const fetchMoh706Data = async (filters: { startDate?: string; endDate?: string; month?: string }) => {
41
- setErrorMessage('');
49
+ const fetchMoh706Data = async ({ startDate, endDate }: Pick<ReportPeriod, 'startDate' | 'endDate'>) => {
42
50
  setIsLoading(true);
43
51
 
44
- let startDate = filters.startDate;
45
- let endDate = filters.endDate;
46
-
47
- if (filters.month) {
48
- const [year, monthIndex] = filters.month.split('-').map(Number);
49
- const start = new Date(year, monthIndex - 1, 1);
50
- const end = new Date(year, monthIndex, 0);
51
-
52
- const formatLocalDate = (d: Date) => {
53
- const y = d.getFullYear();
54
- const m = String(d.getMonth() + 1).padStart(2, '0');
55
- const day = String(d.getDate()).padStart(2, '0');
56
- return `${y}-${m}-${day}`;
57
- };
58
-
59
- startDate = formatLocalDate(start);
60
- endDate = formatLocalDate(end);
61
- }
62
-
63
52
  const params = {
64
53
  locationUuids: locationUuids || '',
65
54
  startDate,
@@ -72,7 +61,7 @@ const MoH706Report: React.FC = () => {
72
61
  setMoh706Data(flatData);
73
62
  setFilters({ locationUuids: params.locationUuids, startDate, endDate });
74
63
  } catch (error: any) {
75
- setErrorMessage(error instanceof Error ? error.message : String(error));
64
+ showReportError('the MOH-706 report', error);
76
65
  } finally {
77
66
  setIsLoading(false);
78
67
  }
@@ -80,36 +69,76 @@ const MoH706Report: React.FC = () => {
80
69
 
81
70
  return (
82
71
  <>
83
- <ReportFiltersComponent reportName="MOH-706 Report" mode="monthly" onGenerate={fetchMoh706Data} isLoding={isLoading} />
84
- {isLoading && <Loading description="Fetching data...." />}
85
- {!isLoading && errorMessage && (
86
- <div>
87
- <a href="#" className="close" data-dismiss="alert">
88
- &times;
89
- </a>
90
- <h4>
91
- <strong>
92
- <span className="glyphicon glyphicon-warning-sign"></span>{' '}
93
- </strong>{' '}
94
- An error occurred while trying to load the report. Please try again.
95
- </h4>
96
- <p>
97
- <small>{errorMessage}</small>
98
- </p>
99
- </div>
72
+ <ReportFiltersComponent
73
+ reportName="MOH-706 Report"
74
+ mode="both"
75
+ onGenerate={fetchMoh706Data}
76
+ isLoading={isLoading}
77
+ isReportGenerated={isReportGenerated}
78
+ />
79
+ {isLoading && <ReportSkeleton />}
80
+ {!isLoading && !isReportGenerated && <ReportPlaceholder reportName="MOH-706" />}
81
+ {!isLoading && isReportGenerated && (
82
+ <ReportPage>
83
+ <div className={styles.sheet}>
84
+ <MOH706Header facility={facility} startDate={filters.startDate} endDate={filters.endDate} />
85
+ <div className={styles.reportSections}>
86
+ <UrineAnalysis
87
+ data={moh706Data}
88
+ locationUuids={filters.locationUuids}
89
+ startDate={filters.startDate}
90
+ endDate={filters.endDate}
91
+ />
92
+ <BloodChemistry
93
+ data={moh706Data}
94
+ locationUuids={filters.locationUuids}
95
+ startDate={filters.startDate}
96
+ endDate={filters.endDate}
97
+ />
98
+ <Parasitology
99
+ data={moh706Data}
100
+ locationUuids={filters.locationUuids}
101
+ startDate={filters.startDate}
102
+ endDate={filters.endDate}
103
+ />
104
+ <Haematology
105
+ data={moh706Data}
106
+ locationUuids={filters.locationUuids}
107
+ startDate={filters.startDate}
108
+ endDate={filters.endDate}
109
+ />
110
+ <Bacteriology
111
+ data={moh706Data}
112
+ locationUuids={filters.locationUuids}
113
+ startDate={filters.startDate}
114
+ endDate={filters.endDate}
115
+ />
116
+ <HistologyAndCytology />
117
+ <Serology
118
+ data={moh706Data}
119
+ locationUuids={filters.locationUuids}
120
+ startDate={filters.startDate}
121
+ endDate={filters.endDate}
122
+ />
123
+ <SpecimenReferralToHigherLevels />
124
+ <DrugSusceptibilityTesting />
125
+ </div>
126
+
127
+ <div className={styles.signOff}>
128
+ <span>
129
+ Compiled by:<span className={styles.line}>{compiledBy}</span>
130
+ </span>
131
+ <span>
132
+ Signature:
133
+ <span className={styles.line} />
134
+ </span>
135
+ <span>
136
+ Date:<span className={styles.shortLine}>{compiledOn}</span>
137
+ </span>
138
+ </div>
139
+ </div>
140
+ </ReportPage>
100
141
  )}
101
- <MOH706Header />
102
- <div className={styles.reportSections}>
103
- <UrineAnalysis data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
104
- <BloodChemistry data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
105
- <Parasitology data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
106
- <Haematology data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
107
- <Bacteriology data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
108
- <HistologyAndCytology />
109
- <Serology data={moh706Data} locationUuids={filters.locationUuids} startDate={filters.startDate} endDate={filters.endDate} />
110
- <SpecimenReferralToHigherLevels />
111
- <DrugSusceptibilityTesting />
112
- </div>
113
142
  </>
114
143
  );
115
144
  };