@openmrs/esm-laboratory-app 1.0.1-pre.106

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 (157) hide show
  1. package/.editorconfig +12 -0
  2. package/.eslintignore +2 -0
  3. package/.eslintrc +32 -0
  4. package/.husky/pre-commit +4 -0
  5. package/.husky/pre-push +6 -0
  6. package/.prettierignore +14 -0
  7. package/.turbo/turbo-build.log +30 -0
  8. package/.turbo/turbo-lint.log +12 -0
  9. package/.turbo/turbo-typescript.log +0 -0
  10. package/.yarn/plugins/@yarnpkg/plugin-interactive-tools.cjs +541 -0
  11. package/.yarn/plugins/@yarnpkg/plugin-outdated.cjs +35 -0
  12. package/.yarn/plugins/@yarnpkg/plugin-version.cjs +550 -0
  13. package/.yarn/versions/3d4697b8.yml +0 -0
  14. package/README.md +39 -0
  15. package/__mocks__/react-i18next.js +50 -0
  16. package/assets/logo/logo.png +0 -0
  17. package/assets/logo/moh_logo_without_word.png +0 -0
  18. package/assets/screenshots/labs_enter_results.png +0 -0
  19. package/assets/screenshots/labs_general_dashboard.png +0 -0
  20. package/dist/142.js +1 -0
  21. package/dist/142.js.map +1 -0
  22. package/dist/319.js +1 -0
  23. package/dist/36.js +1 -0
  24. package/dist/36.js.map +1 -0
  25. package/dist/395.js +1 -0
  26. package/dist/395.js.map +1 -0
  27. package/dist/453.js +1 -0
  28. package/dist/453.js.map +1 -0
  29. package/dist/533.js +1 -0
  30. package/dist/533.js.map +1 -0
  31. package/dist/56.js +2 -0
  32. package/dist/56.js.LICENSE.txt +32 -0
  33. package/dist/56.js.map +1 -0
  34. package/dist/572.js +1 -0
  35. package/dist/572.js.map +1 -0
  36. package/dist/574.js +1 -0
  37. package/dist/581.js +1 -0
  38. package/dist/581.js.map +1 -0
  39. package/dist/66.js +1 -0
  40. package/dist/66.js.map +1 -0
  41. package/dist/757.js +1 -0
  42. package/dist/769.js +1 -0
  43. package/dist/769.js.map +1 -0
  44. package/dist/770.js +1 -0
  45. package/dist/770.js.map +1 -0
  46. package/dist/800.js +2 -0
  47. package/dist/800.js.LICENSE.txt +3 -0
  48. package/dist/800.js.map +1 -0
  49. package/dist/809.js +1 -0
  50. package/dist/809.js.map +1 -0
  51. package/dist/889.js +1 -0
  52. package/dist/889.js.map +1 -0
  53. package/dist/894.js +2 -0
  54. package/dist/894.js.LICENSE.txt +48 -0
  55. package/dist/894.js.map +1 -0
  56. package/dist/924.js +1 -0
  57. package/dist/924.js.map +1 -0
  58. package/dist/928.js +1 -0
  59. package/dist/928.js.map +1 -0
  60. package/dist/967b98e46b0984c4.png +0 -0
  61. package/dist/97.js +1 -0
  62. package/dist/97.js.map +1 -0
  63. package/dist/983.js +1 -0
  64. package/dist/983.js.map +1 -0
  65. package/dist/main.js +2 -0
  66. package/dist/main.js.LICENSE.txt +48 -0
  67. package/dist/main.js.map +1 -0
  68. package/dist/openmrs-esm-laboratory-app.js +1 -0
  69. package/dist/openmrs-esm-laboratory-app.js.buildmanifest.json +628 -0
  70. package/dist/openmrs-esm-laboratory-app.js.map +1 -0
  71. package/dist/routes.json +1 -0
  72. package/i18next-parser.config.js +89 -0
  73. package/jest.config.js +16 -0
  74. package/package.json +121 -0
  75. package/src/completed-list/completed-list.component.tsx +242 -0
  76. package/src/completed-list/completed-list.resource.ts +0 -0
  77. package/src/completed-list/completed-list.scss +232 -0
  78. package/src/components/create-dashboard-link.component.tsx +44 -0
  79. package/src/components/overlay/hook.ts +47 -0
  80. package/src/components/overlay/overlay.component.tsx +52 -0
  81. package/src/components/overlay/overlay.scss +93 -0
  82. package/src/config-schema.ts +36 -0
  83. package/src/constants.ts +5 -0
  84. package/src/declarations.d.ts +6 -0
  85. package/src/header/laboratory-header.component.tsx +35 -0
  86. package/src/header/laboratory-header.scss +68 -0
  87. package/src/header/laboratory-illustration.component.tsx +13 -0
  88. package/src/index.ts +92 -0
  89. package/src/laboratory.component.tsx +18 -0
  90. package/src/patient-chart/laboratory-item/view-laboratory-item.component.tsx +39 -0
  91. package/src/patient-chart/laboratory-item/view-laboratory-item.resource.ts +290 -0
  92. package/src/patient-chart/laboratory-item/view-laboratory-item.scss +0 -0
  93. package/src/patient-chart/laboratory-order.component.tsx +453 -0
  94. package/src/patient-chart/laboratory-order.resource.ts +437 -0
  95. package/src/patient-chart/laboratory-order.scss +66 -0
  96. package/src/patient-chart/results-summary/print-results-summary.component.tsx +240 -0
  97. package/src/patient-chart/results-summary/print-results-summary.scss +105 -0
  98. package/src/patient-chart/results-summary/print-results-table.component.tsx +163 -0
  99. package/src/patient-chart/results-summary/results/results.component.tsx +25 -0
  100. package/src/patient-chart/results-summary/results/results.resource.ts +50 -0
  101. package/src/patient-chart/results-summary/results/results.scss +0 -0
  102. package/src/patient-chart/results-summary/results-dialog/edit-results-dialog.component.tsx +46 -0
  103. package/src/patient-chart/results-summary/results-summary.component.tsx +98 -0
  104. package/src/patient-chart/results-summary/results-summary.resource.tsx +185 -0
  105. package/src/patient-chart/results-summary/results-summary.scss +154 -0
  106. package/src/patient-chart/results-summary/send-email-dialog.component.tsx +111 -0
  107. package/src/patient-chart/results-summary/test-children-results.component.tsx +221 -0
  108. package/src/patient-chart/results-summary/test-print-results-table.component.tsx +148 -0
  109. package/src/patient-chart/results-summary/test-results-delete-action-menu.component.tsx +27 -0
  110. package/src/patient-chart/results-summary/test-results-rescend-action-menu.component.tsx +26 -0
  111. package/src/patient-chart/results-summary/test-results-table.component.tsx +153 -0
  112. package/src/patient-chart/results-summary/tests-children-detail.component.tsx +54 -0
  113. package/src/patient-chart/results-summary/views/email.handlebars +13 -0
  114. package/src/queue-list/lab-dialogs/add-to-worklist-dialog.component.tsx +323 -0
  115. package/src/queue-list/lab-dialogs/add-to-worklist-dialog.resource.ts +155 -0
  116. package/src/queue-list/lab-dialogs/add-to-worklist-dialog.scss +20 -0
  117. package/src/queue-list/lab-tests/lab-tests.component.tsx +116 -0
  118. package/src/queue-list/lab-tests/lab-tests.resource.ts +17 -0
  119. package/src/queue-list/lab-tests/lab-tests.scss +12 -0
  120. package/src/queue-list/laboratory-patient-list.component.tsx +277 -0
  121. package/src/queue-list/laboratory-patient-list.resource.ts +86 -0
  122. package/src/queue-list/laboratory-queue.component.tsx +120 -0
  123. package/src/queue-list/laboratory-queue.scss +213 -0
  124. package/src/queue-list/laboratory-tabs.component.tsx +81 -0
  125. package/src/queue-list/pick-lab-request-menu.component.tsx +38 -0
  126. package/src/reject-order/reject-order-dialog.component.tsx +114 -0
  127. package/src/reject-order/reject-order-dialog.resource.ts +14 -0
  128. package/src/reject-order/reject-order-dialog.scss +14 -0
  129. package/src/results/result-form.component.tsx +223 -0
  130. package/src/results/result-form.resource.ts +328 -0
  131. package/src/results/result-form.scss +19 -0
  132. package/src/review-list/dialog/review-item.component.tsx +283 -0
  133. package/src/review-list/dialog/review-item.resource.ts +14 -0
  134. package/src/review-list/dialog/review-item.scss +0 -0
  135. package/src/review-list/review-list.component.tsx +277 -0
  136. package/src/review-list/review-list.resource.ts +0 -0
  137. package/src/review-list/review-list.scss +189 -0
  138. package/src/root.component.tsx +15 -0
  139. package/src/root.scss +50 -0
  140. package/src/routes.json +72 -0
  141. package/src/setup-tests.ts +1 -0
  142. package/src/summary-tiles/laboratory-summary-tiles.component.tsx +53 -0
  143. package/src/summary-tiles/laboratory-summary-tiles.scss +12 -0
  144. package/src/summary-tiles/laboratory-summary.resource.tsx +50 -0
  145. package/src/summary-tiles/summary-tile.component.tsx +48 -0
  146. package/src/summary-tiles/summary-tile.scss +43 -0
  147. package/src/types/index.ts +412 -0
  148. package/src/types/patient-queues.ts +189 -0
  149. package/src/utils/functions.ts +246 -0
  150. package/src/work-list/work-list.component.tsx +310 -0
  151. package/src/work-list/work-list.resource.ts +136 -0
  152. package/src/work-list/work-list.scss +215 -0
  153. package/translations/en.json +16 -0
  154. package/translations/es.json +3 -0
  155. package/translations/fr.json +3 -0
  156. package/tsconfig.json +23 -0
  157. package/webpack.config.js +29 -0
@@ -0,0 +1,323 @@
1
+ import React, { useCallback, useEffect, useState } from "react";
2
+ import { MappedQueueEntry } from "../../types";
3
+ import {
4
+ Button,
5
+ ContentSwitcher,
6
+ Form,
7
+ ModalBody,
8
+ ModalFooter,
9
+ ModalHeader,
10
+ Select,
11
+ SelectItem,
12
+ Switch,
13
+ TextArea,
14
+ Grid,
15
+ Checkbox,
16
+ TextInput,
17
+ IconButton,
18
+ } from "@carbon/react";
19
+ import { useTranslation } from "react-i18next";
20
+ import { MappedPatientQueueEntry } from "../laboratory-patient-list.resource";
21
+ import styles from "./add-to-worklist-dialog.scss";
22
+ import {
23
+ navigate,
24
+ showNotification,
25
+ showToast,
26
+ useLocations,
27
+ useSession,
28
+ } from "@openmrs/esm-framework";
29
+ import { Renew } from "@carbon/react/icons";
30
+ import {
31
+ GenerateSpecimenId,
32
+ GetOrderByUuid,
33
+ UpdateOrder,
34
+ useQueueRoomLocations,
35
+ useSpecimenTypes,
36
+ } from "./add-to-worklist-dialog.resource";
37
+ import { Encounter, Order } from "../../types/patient-queues";
38
+
39
+ interface AddToWorklistDialogProps {
40
+ queueId;
41
+ encounter: Encounter;
42
+ order: Order;
43
+ closeModal: () => void;
44
+ }
45
+
46
+ const AddToWorklistDialog: React.FC<AddToWorklistDialogProps> = ({
47
+ queueId,
48
+ encounter,
49
+ order,
50
+ closeModal,
51
+ }) => {
52
+ const { t } = useTranslation();
53
+
54
+ const locations = useLocations();
55
+
56
+ const sessionUser = useSession();
57
+
58
+ const [selectedLocation, setSelectedLocation] = useState("");
59
+
60
+ const [preferred, setPreferred] = useState(false);
61
+
62
+ const [specimenID, setSpecimenID] = useState();
63
+
64
+ const { specimenTypes } = useSpecimenTypes();
65
+
66
+ const [orderer, setOrderer] = useState("");
67
+
68
+ const [concept, setConcept] = useState("");
69
+
70
+ const [patient, setPatient] = useState("");
71
+
72
+ const [encounterUuid, setEncounterUuid] = useState("");
73
+
74
+ const { queueRoomLocations } = useQueueRoomLocations(
75
+ sessionUser?.sessionLocation?.uuid
76
+ );
77
+
78
+ const [specimenType, setSpecimenType] = useState();
79
+
80
+ const [selectedNextQueueLocation, setSelectedNextQueueLocation] = useState(
81
+ queueRoomLocations[0]?.uuid
82
+ );
83
+
84
+ const filteredlocations = queueRoomLocations?.filter(
85
+ (location) => location.uuid != selectedLocation
86
+ );
87
+
88
+ useEffect(() => {
89
+ if (locations?.length && sessionUser) {
90
+ setSelectedLocation(sessionUser?.sessionLocation?.uuid);
91
+ }
92
+ }, [locations, sessionUser]);
93
+
94
+ // GetOrderByUuid
95
+ GetOrderByUuid(order.uuid).then(
96
+ (resp) => {
97
+ setOrderer(resp.data?.orderer?.uuid);
98
+ setConcept(resp.data?.concept?.uuid);
99
+ setPatient(resp.data?.patient?.uuid);
100
+ setEncounterUuid(resp.data?.encounter.uuid);
101
+ },
102
+ (err) => {
103
+ showNotification({
104
+ title: t(`errorGettingOrder', 'Error Getting Order Id`),
105
+ kind: "error",
106
+ critical: true,
107
+ description: err?.message,
108
+ });
109
+ }
110
+ );
111
+
112
+ const pickLabRequestQueue = async (event) => {
113
+ event.preventDefault();
114
+ // pick lab test
115
+ let body = {
116
+ sampleId: specimenID,
117
+ specimenSourceId: specimenType,
118
+ unProcessedOrders: "",
119
+ patientQueueId: queueId,
120
+ };
121
+
122
+ UpdateOrder(order.uuid, body).then(
123
+ () => {
124
+ showToast({
125
+ critical: true,
126
+ title: t("pickedAnOrder", "Picked an order"),
127
+ kind: "success",
128
+ description: t(
129
+ "pickSuccessfully",
130
+ "You have successfully picked an Order"
131
+ ),
132
+ });
133
+ closeModal();
134
+ },
135
+ (error) => {
136
+ showNotification({
137
+ title: t(`errorPicking an order', 'Error Picking an Order`),
138
+ kind: "error",
139
+ critical: true,
140
+ description: error?.message,
141
+ });
142
+ }
143
+ );
144
+ };
145
+
146
+ const onChecked = () => {
147
+ setPreferred(!preferred);
148
+ };
149
+
150
+ const generateId = async (e) => {
151
+ e.preventDefault();
152
+ // generate sample Id
153
+ GenerateSpecimenId(order.uuid).then(
154
+ (resp) => {
155
+ setSpecimenID(resp.data.results[0].sampleId);
156
+ showToast({
157
+ critical: true,
158
+ title: t("generatesampleID", "Generate Sample Id"),
159
+ kind: "success",
160
+ description: t(
161
+ "generateSuccessfully",
162
+ "You have successfully generated a Sample Id"
163
+ ),
164
+ });
165
+ },
166
+ (err) => {
167
+ showNotification({
168
+ title: t(`errorGeneratingId', 'Error Generating Sample Id`),
169
+ kind: "error",
170
+ critical: true,
171
+ description: err?.message,
172
+ });
173
+ }
174
+ );
175
+ };
176
+
177
+ return (
178
+ <div>
179
+ <Form onSubmit={pickLabRequestQueue}>
180
+ <ModalHeader
181
+ closeModal={closeModal}
182
+ title={t("pickRequest", "Pick Lab Request")}
183
+ />
184
+ <ModalBody>
185
+ <div className={styles.modalBody}>
186
+ <section className={styles.section}>
187
+ <div
188
+ style={{
189
+ display: "flex",
190
+ alignItems: "center",
191
+ justifyContent: "space-between",
192
+ alignContent: "stretch",
193
+ }}
194
+ >
195
+ <div className={styles.sectionTitle}>
196
+ {t("specimenID", "Specimen ID")}
197
+ </div>
198
+
199
+ <div
200
+ style={{
201
+ display: "flex",
202
+ alignItems: "center",
203
+ justifyContent: "space-between",
204
+ columnGap: "10px",
205
+ }}
206
+ >
207
+ <div style={{ width: "430px" }}>
208
+ <TextInput
209
+ type="text"
210
+ id="specimentID"
211
+ value={specimenID}
212
+ />
213
+ </div>
214
+ <div style={{ width: "50px" }}>
215
+ <Button
216
+ hasIconOnly
217
+ onClick={(e) => generateId(e)}
218
+ renderIcon={(props) => <Renew size={16} {...props} />}
219
+ />
220
+ </div>
221
+ </div>
222
+ </div>
223
+ </section>
224
+ <section className={styles.section}>
225
+ <div
226
+ style={{
227
+ display: "flex",
228
+ alignItems: "center",
229
+ justifyContent: "space-between",
230
+ alignContent: "stretch",
231
+ }}
232
+ >
233
+ <div className={styles.sectionTitle}>
234
+ {t("specimenType", "Specimen Type")}
235
+ </div>
236
+ <div style={{ width: "500px" }}>
237
+ <section className={styles.section}>
238
+ <Select
239
+ labelText=" Specimen Type"
240
+ id="speciment-types"
241
+ name="specimen-types"
242
+ value={specimenType}
243
+ onChange={(event) => setSpecimenType(event.target.value)}
244
+ >
245
+ {!specimenType ? (
246
+ <SelectItem
247
+ text={t("specimenType", "Select Specimen Type")}
248
+ value=""
249
+ />
250
+ ) : null}
251
+ {specimenTypes.map((type) => (
252
+ <SelectItem
253
+ key={type.uuid}
254
+ text={type.display}
255
+ value={type.uuid}
256
+ >
257
+ {type.display}
258
+ </SelectItem>
259
+ ))}
260
+ </Select>
261
+ </section>
262
+ </div>
263
+ </div>
264
+ </section>
265
+ <section
266
+ style={{
267
+ display: "flex",
268
+ alignItems: "center",
269
+ justifyContent: "space-between",
270
+ alignContent: "stretch",
271
+ }}
272
+ >
273
+ <div>
274
+ <Checkbox
275
+ checked={preferred}
276
+ onChange={onChecked}
277
+ labelText={"Referred"}
278
+ id="test-referred"
279
+ />
280
+ </div>
281
+ {preferred && (
282
+ <div style={{ width: "500px" }}>
283
+ <section className={styles.section}>
284
+ <Select
285
+ labelText={t("location", "Location ")}
286
+ id="nextQueueLocation"
287
+ name="nextQueueLocation"
288
+ invalidText="Required"
289
+ value={selectedNextQueueLocation}
290
+ onChange={(event) =>
291
+ setSelectedNextQueueLocation(event.target.value)
292
+ }
293
+ >
294
+ {filteredlocations.map((location) => (
295
+ <SelectItem
296
+ key={location.uuid}
297
+ text={location.display}
298
+ value={location.uuid}
299
+ >
300
+ {location.display}
301
+ </SelectItem>
302
+ ))}
303
+ </Select>
304
+ </section>
305
+ </div>
306
+ )}
307
+ </section>
308
+ </div>
309
+ </ModalBody>
310
+ <ModalFooter>
311
+ <Button kind="secondary" onClick={closeModal}>
312
+ {t("cancel", "Cancel")}
313
+ </Button>
314
+ <Button type="submit" onClick={pickLabRequestQueue}>
315
+ {t("pickPatient", "Pick Lab Request")}
316
+ </Button>
317
+ </ModalFooter>
318
+ </Form>
319
+ </div>
320
+ );
321
+ };
322
+
323
+ export default AddToWorklistDialog;
@@ -0,0 +1,155 @@
1
+ import { FetchResponse, openmrsFetch, useConfig } from "@openmrs/esm-framework";
2
+ import { useMemo } from "react";
3
+ import useSWR from "swr";
4
+ import useSWRImmutable from "swr/immutable";
5
+
6
+ export interface QueueRoomsResponse {
7
+ uuid: string;
8
+ display: string;
9
+ name: string;
10
+ description: string;
11
+ address1: string;
12
+ address2: string;
13
+ cityvillage: string;
14
+ stateprovince: string;
15
+ country: string;
16
+ postalcode: string;
17
+ latitude: string;
18
+ longitude: string;
19
+ countydistrict: string;
20
+ address3: string;
21
+ address4: string;
22
+ address5: string;
23
+ address6: string;
24
+ parentLocation: ParentLocation;
25
+ childLocations: String[];
26
+ retired: boolean;
27
+ attributes: String[];
28
+ address7: string;
29
+ address8: string;
30
+ address9: string;
31
+ address10: string;
32
+ address11: string;
33
+ address12: string;
34
+ address13: string;
35
+ address14: string;
36
+ address15: string;
37
+ resourceVersion: string;
38
+ }
39
+
40
+ export interface ParentLocation {
41
+ uuid: string;
42
+ display: string;
43
+ name: string;
44
+ description: string;
45
+ address1: string;
46
+ address2: string;
47
+ cityVillage: string;
48
+ stateProvince: string;
49
+ country: string;
50
+ postalcode: string;
51
+ latitude: string;
52
+ longitude: string;
53
+ countydistrict: string;
54
+ address3: string;
55
+ address4: string;
56
+ address5: string;
57
+ address6: string;
58
+ parentLocation: ParentLocation;
59
+ childLocations: ChildLocations[];
60
+ retired: boolean;
61
+ attributes: String[];
62
+ address7: string;
63
+ address8: string;
64
+ address9: string;
65
+ address10: string;
66
+ address11: string;
67
+ address12: string;
68
+ address13: string;
69
+ address14: string;
70
+ address15: string;
71
+ resourceversion: string;
72
+ }
73
+
74
+ export interface ChildLocations {
75
+ uuid: string;
76
+ display: string;
77
+ }
78
+
79
+ export interface ParentLocation {
80
+ uuid: string;
81
+ display: string;
82
+ }
83
+
84
+ // get queue rooms
85
+ export function useQueueRoomLocations(currentQueueLocation: string) {
86
+ const apiUrl = `/ws/rest/v1/location/${currentQueueLocation}?v=full`;
87
+ const { data, error, isLoading } = useSWR<{ data: QueueRoomsResponse }>(
88
+ apiUrl,
89
+ openmrsFetch
90
+ );
91
+
92
+ const queueRoomLocations = useMemo(
93
+ () =>
94
+ data?.data?.parentLocation?.childLocations?.map((response) => response) ??
95
+ [],
96
+ [data?.data?.parentLocation?.childLocations]
97
+ );
98
+ return {
99
+ queueRoomLocations: queueRoomLocations ? queueRoomLocations : [],
100
+ isLoading,
101
+ error,
102
+ };
103
+ }
104
+
105
+ // get specimen types
106
+ export function useSpecimenTypes() {
107
+ const config = useConfig();
108
+ const { laboratorySpecimenTypeConcept } = config;
109
+
110
+ const apiUrl = `/ws/rest/v1/concept/${laboratorySpecimenTypeConcept}`;
111
+ const { data, error, isLoading } = useSWRImmutable<FetchResponse>(
112
+ apiUrl,
113
+ openmrsFetch
114
+ );
115
+
116
+ return {
117
+ specimenTypes: data ? data?.data?.answers : [],
118
+ isLoading,
119
+ };
120
+ }
121
+
122
+ // generate specimen id
123
+ export async function GenerateSpecimenId(uuid: string) {
124
+ const abortController = new AbortController();
125
+ return openmrsFetch(`/ws/rest/v1/generatesampleId?uuid=${uuid}`, {
126
+ method: "GET",
127
+ headers: {
128
+ "Content-Type": "application/json",
129
+ },
130
+ signal: abortController.signal,
131
+ });
132
+ }
133
+
134
+ // update Order
135
+ export async function UpdateOrder(uuid: string, body: any) {
136
+ const abortController = new AbortController();
137
+ return openmrsFetch(`/ws/rest/v1/accessionorder/${uuid}`, {
138
+ method: "POST",
139
+ headers: {
140
+ "Content-Type": "application/json",
141
+ },
142
+ signal: abortController.signal,
143
+ body: body,
144
+ });
145
+ }
146
+
147
+ export async function GetOrderByUuid(uuid: string) {
148
+ const abortController = new AbortController();
149
+ return openmrsFetch(`/ws/rest/v1/order/${uuid}`, {
150
+ headers: {
151
+ "Content-Type": "application/json",
152
+ },
153
+ signal: abortController.signal,
154
+ });
155
+ }
@@ -0,0 +1,20 @@
1
+ @use '@carbon/styles/scss/spacing';
2
+ @use '@carbon/styles/scss/type';
3
+
4
+
5
+ .radioButton {
6
+ padding: spacing.$spacing-02 spacing.$spacing-02;
7
+ margin: spacing.$spacing-03 0;
8
+ }
9
+
10
+ section {
11
+ margin: spacing.$spacing-03;
12
+ }
13
+
14
+ .sectionTitle {
15
+ margin-bottom: spacing.$spacing-04;
16
+ }
17
+
18
+ .modalBody {
19
+ padding-bottom: spacing.$spacing-05;
20
+ }
@@ -0,0 +1,116 @@
1
+ import React, { useMemo } from "react";
2
+ import { useTranslation } from "react-i18next";
3
+
4
+ import {
5
+ DataTable,
6
+ DataTableHeader,
7
+ DataTableSkeleton,
8
+ Pagination,
9
+ Table,
10
+ TableBody,
11
+ TableCell,
12
+ TableContainer,
13
+ TableExpandHeader,
14
+ TableExpandRow,
15
+ TableHead,
16
+ TableHeader,
17
+ TableRow,
18
+ TabPanel,
19
+ TableToolbar,
20
+ TableToolbarContent,
21
+ TableToolbarSearch,
22
+ Layer,
23
+ Tag,
24
+ TableExpandedRow,
25
+ } from "@carbon/react";
26
+ import { ErrorState } from "@openmrs/esm-framework";
27
+ import { Encounter } from "../../types/patient-queues";
28
+ import styles from "../laboratory-queue.scss";
29
+ import PickLabRequestActionMenu from "../pick-lab-request-menu.component";
30
+
31
+ interface LabTestsProps {
32
+ encounter: Encounter;
33
+ queueId: string;
34
+ }
35
+
36
+ const LabTests: React.FC<LabTestsProps> = ({ encounter, queueId }) => {
37
+ const { t } = useTranslation();
38
+ // console.info(encounter);
39
+ let columns = [
40
+ { id: 1, header: t("order", "Order"), key: "order", align: "left" },
41
+ {
42
+ id: 2,
43
+ header: t("orderType", "OrderType"),
44
+ key: "orderType",
45
+ align: "center",
46
+ },
47
+ { id: 3, header: t("actions", "Actions"), key: "actions", align: "center" },
48
+ ];
49
+
50
+ const tableRows = useMemo(() => {
51
+ return encounter?.orders?.map((item) => ({
52
+ ...item,
53
+ id: item.uuid,
54
+ order: {
55
+ content: <span>{item.display}</span>,
56
+ },
57
+ orderType: {
58
+ content: <span>{item.type}</span>,
59
+ },
60
+ actions: {
61
+ content: (
62
+ <PickLabRequestActionMenu closeModal={() => true} order={item} />
63
+ ),
64
+ },
65
+ }));
66
+ }, [encounter]);
67
+
68
+ if (!encounter) {
69
+ return (
70
+ <ErrorState
71
+ error={"Error Loading encounter"}
72
+ headerTitle={"Tests Error"}
73
+ />
74
+ );
75
+ }
76
+
77
+ return (
78
+ <div>
79
+ <div className={styles.headerBtnContainer}></div>
80
+ <DataTable rows={tableRows} headers={columns} isSortable useZebraStyles>
81
+ {({ rows, headers, getHeaderProps, getTableProps, getRowProps }) => (
82
+ <TableContainer className={styles.tableContainer}>
83
+ <Table {...getTableProps()} className={styles.activePatientsTable}>
84
+ <TableHead>
85
+ <TableRow>
86
+ {headers.map((header) => (
87
+ <TableHeader {...getHeaderProps({ header })}>
88
+ {header.header}
89
+ </TableHeader>
90
+ ))}
91
+ </TableRow>
92
+ </TableHead>
93
+ <TableBody>
94
+ {rows.map((row, index) => {
95
+ return (
96
+ <React.Fragment key={row.id}>
97
+ <TableRow {...getRowProps({ row })} key={row.id}>
98
+ {row.cells.map((cell) => (
99
+ <TableCell key={cell.id}>
100
+ {cell.value?.content ?? cell.value}
101
+ </TableCell>
102
+ ))}
103
+ </TableRow>
104
+ </React.Fragment>
105
+ );
106
+ })}
107
+ </TableBody>
108
+ </Table>
109
+ </TableContainer>
110
+ )}
111
+ </DataTable>
112
+ </div>
113
+ );
114
+ };
115
+
116
+ export default LabTests;
@@ -0,0 +1,17 @@
1
+ import { FetchResponse, openmrsFetch, useConfig } from "@openmrs/esm-framework";
2
+ import useSWR from "swr";
3
+ import { EncounterResponse } from "../../patient-chart/laboratory-item/view-laboratory-item.resource";
4
+ export function useGetLabOrders(encounterUuid: string) {
5
+ const apiUrl = `/ws/rest/v1/encounter/${encounterUuid}?v=full`;
6
+
7
+ const { data, error, isLoading } = useSWR<{ data: EncounterResponse }, Error>(
8
+ apiUrl,
9
+ openmrsFetch
10
+ );
11
+
12
+ return {
13
+ labOrders: data?.data ? data?.data?.orders : [],
14
+ isLoading,
15
+ isError: error,
16
+ };
17
+ }
@@ -0,0 +1,12 @@
1
+ @use '@carbon/styles/scss/spacing';
2
+ @use '@carbon/styles/scss/type';
3
+ @import "~@openmrs/esm-styleguide/src/vars";
4
+
5
+ .cardContainer {
6
+ background-color: $ui-02 ;
7
+ display: flex;
8
+ justify-content: space-between;
9
+ padding: 0 spacing.$spacing-05 spacing.$spacing-10 spacing.$spacing-03;
10
+ flex-flow: row wrap;
11
+ margin-top: - spacing.$spacing-03;
12
+ }