@kenyaemr/esm-ward-app 8.5.1-pre.22 → 8.5.1-pre.25
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/.turbo/turbo-build.log +2 -2
- package/dist/1917.js +1 -1
- package/dist/1917.js.map +1 -1
- package/dist/4743.js +1 -1
- package/dist/4743.js.map +1 -1
- package/dist/6012.js +1 -1
- package/dist/6012.js.map +1 -1
- package/dist/kenyaemr-esm-ward-app.js.buildmanifest.json +12 -12
- package/dist/main.js +1 -1
- package/dist/main.js.map +1 -1
- package/dist/routes.json +1 -1
- package/package.json +1 -1
- package/src/config-schema.ts +9 -3
- package/src/hooks/useSummaryMetrics.ts +21 -7
- package/src/ward-view/linelist-wards/LineListTable.tsx +21 -3
package/src/config-schema.ts
CHANGED
|
@@ -270,7 +270,7 @@ export const configSchema: ConfigSchema = {
|
|
|
270
270
|
_default: '14b36860-5033-4765-b91b-ace856ab64c2',
|
|
271
271
|
},
|
|
272
272
|
admissionEncounterTypeUuid: {
|
|
273
|
-
_description:
|
|
273
|
+
_description: 'Admission encounter type',
|
|
274
274
|
_type: Type.String,
|
|
275
275
|
_default: 'e22e39fd-7db2-45e7-80f1-60fa0d5a4378',
|
|
276
276
|
},
|
|
@@ -299,6 +299,11 @@ export const configSchema: ConfigSchema = {
|
|
|
299
299
|
_type: Type.String,
|
|
300
300
|
_default: '98a781d2-b777-4756-b4c9-c9b0deb3483c',
|
|
301
301
|
},
|
|
302
|
+
mortuaryAdmissionLoctionTagUuid: {
|
|
303
|
+
_description: 'Mortuary admission location tag uuid',
|
|
304
|
+
_type: Type.String,
|
|
305
|
+
_default: '1dbbfe22-d21f-499c-bf33-cc9f75b6c7e8',
|
|
306
|
+
},
|
|
302
307
|
};
|
|
303
308
|
|
|
304
309
|
export interface WardConfigObject {
|
|
@@ -318,8 +323,9 @@ export interface WardConfigObject {
|
|
|
318
323
|
referralsConceptUuid: string;
|
|
319
324
|
referringToAnotherFacilityConceptUuid: string;
|
|
320
325
|
dischargeHomeConceptUuid: string;
|
|
321
|
-
doctorsNoteFormUuid:string
|
|
322
|
-
inpatientDischargeFormUuid:string
|
|
326
|
+
doctorsNoteFormUuid: string;
|
|
327
|
+
inpatientDischargeFormUuid: string;
|
|
328
|
+
mortuaryAdmissionLoctionTagUuid: string;
|
|
323
329
|
}
|
|
324
330
|
|
|
325
331
|
export interface PendingItemsElementConfig {
|
|
@@ -6,27 +6,40 @@ import { useIpdDischargeEncounter } from './useIpdDischargeEncounter';
|
|
|
6
6
|
import { useWardPatientGrouping } from './useWardPatientGrouping';
|
|
7
7
|
|
|
8
8
|
export const useWardsSummaryMetrics = () => {
|
|
9
|
-
const rep = 'custom:(totalBeds,occupiedBeds,bedLayouts:(patients:(uuid,display)))';
|
|
9
|
+
const rep = 'custom:(uuid,display,tags:(uuid,display),totalBeds,occupiedBeds,bedLayouts:(patients:(uuid,display)))';
|
|
10
10
|
|
|
11
11
|
const apiUrl = `${restBaseUrl}/admissionLocation?v=${rep}`;
|
|
12
12
|
const { data = [], isLoading, error } = useOpenmrsFetchAll<AdmissionLocationFetchResponse>(apiUrl);
|
|
13
|
+
const { mortuaryAdmissionLoctionTagUuid } = useConfig<WardConfigObject>();
|
|
14
|
+
|
|
15
|
+
const filteredData = useMemo(() => {
|
|
16
|
+
if (!mortuaryAdmissionLoctionTagUuid) return data;
|
|
17
|
+
|
|
18
|
+
return data.filter((location) => {
|
|
19
|
+
const hasMortuaryTag = location.ward.tags?.some((tag) => tag.uuid === mortuaryAdmissionLoctionTagUuid);
|
|
20
|
+
return !hasMortuaryTag;
|
|
21
|
+
});
|
|
22
|
+
}, [data, mortuaryAdmissionLoctionTagUuid]);
|
|
23
|
+
|
|
13
24
|
const totalBeds = useMemo(() => {
|
|
14
|
-
return
|
|
25
|
+
return filteredData.reduce((prev, curr) => {
|
|
15
26
|
return prev + curr.totalBeds;
|
|
16
27
|
}, 0);
|
|
17
|
-
}, [
|
|
28
|
+
}, [filteredData]);
|
|
29
|
+
|
|
18
30
|
const occupiedBeds = useMemo(() => {
|
|
19
|
-
return
|
|
31
|
+
return filteredData.reduce((prev, curr) => {
|
|
20
32
|
return prev + curr.occupiedBeds;
|
|
21
33
|
}, 0);
|
|
22
|
-
}, [
|
|
34
|
+
}, [filteredData]);
|
|
35
|
+
|
|
23
36
|
const bedOccupancy = useMemo(() => {
|
|
24
37
|
if (!totalBeds || !occupiedBeds) return `0%`;
|
|
25
38
|
return `${((occupiedBeds / totalBeds) * 100).toFixed(2)}%`;
|
|
26
39
|
}, [totalBeds, occupiedBeds]);
|
|
27
40
|
|
|
28
41
|
const admittedPatients = useMemo(() => {
|
|
29
|
-
return
|
|
42
|
+
return filteredData.reduce((prev, curr) => {
|
|
30
43
|
return (
|
|
31
44
|
prev +
|
|
32
45
|
curr.bedLayouts?.reduce((p, c) => {
|
|
@@ -34,7 +47,8 @@ export const useWardsSummaryMetrics = () => {
|
|
|
34
47
|
}, 0)
|
|
35
48
|
);
|
|
36
49
|
}, 0);
|
|
37
|
-
}, [
|
|
50
|
+
}, [filteredData]);
|
|
51
|
+
|
|
38
52
|
return {
|
|
39
53
|
totalBeds,
|
|
40
54
|
occupiedBeds,
|
|
@@ -12,7 +12,7 @@ import {
|
|
|
12
12
|
TableRow,
|
|
13
13
|
Tile,
|
|
14
14
|
} from '@carbon/react';
|
|
15
|
-
import { ConfigurableLink, ErrorState } from '@openmrs/esm-framework';
|
|
15
|
+
import { ConfigurableLink, ErrorState, useConfig } from '@openmrs/esm-framework';
|
|
16
16
|
import { CardHeader } from '@openmrs/esm-patient-common-lib';
|
|
17
17
|
import { useTranslation } from 'react-i18next';
|
|
18
18
|
import React, { useMemo } from 'react';
|
|
@@ -22,6 +22,8 @@ import styles from './linelist-wards.scss';
|
|
|
22
22
|
import { type AdmissionLocationFetchResponse } from '../../types';
|
|
23
23
|
import { EmptyState } from '../../ward-patients/table-state-components';
|
|
24
24
|
import WardPendingOutCell from './WardPendingOutCell';
|
|
25
|
+
import { type WardConfigObject } from '../../config-schema';
|
|
26
|
+
|
|
25
27
|
const LineListTable = () => {
|
|
26
28
|
const {
|
|
27
29
|
admissionLocations,
|
|
@@ -37,6 +39,17 @@ const LineListTable = () => {
|
|
|
37
39
|
} = useAdmisiionLocations();
|
|
38
40
|
const { t } = useTranslation();
|
|
39
41
|
const headerTitle = t('wards', 'Wards');
|
|
42
|
+
const { mortuaryAdmissionLoctionTagUuid } = useConfig<WardConfigObject>();
|
|
43
|
+
|
|
44
|
+
const filteredAdmissionLocations = useMemo(() => {
|
|
45
|
+
if (!mortuaryAdmissionLoctionTagUuid) return admissionLocations;
|
|
46
|
+
|
|
47
|
+
return admissionLocations.filter((location) => {
|
|
48
|
+
const hasMortuaryTag = location.ward.tags?.some((tag) => tag.uuid === mortuaryAdmissionLoctionTagUuid);
|
|
49
|
+
return !hasMortuaryTag;
|
|
50
|
+
});
|
|
51
|
+
}, [admissionLocations, mortuaryAdmissionLoctionTagUuid]);
|
|
52
|
+
|
|
40
53
|
const headers = [
|
|
41
54
|
{ key: 'ward', header: t('wardName', 'Ward Name') },
|
|
42
55
|
{ key: 'numberOfBeds', header: t('numberofbeds', 'Number of Beds') },
|
|
@@ -46,12 +59,14 @@ const LineListTable = () => {
|
|
|
46
59
|
{ key: 'pendingOut', header: t('pendingOut', 'Pending Out') },
|
|
47
60
|
{ key: 'action', header: t('action', 'Action') },
|
|
48
61
|
];
|
|
62
|
+
|
|
49
63
|
const calculateOccupancy = (location: AdmissionLocationFetchResponse) => {
|
|
50
64
|
if (!location.totalBeds || !location.occupiedBeds) return 0;
|
|
51
65
|
return (((location.totalBeds - location.occupiedBeds) / location.totalBeds) * 100).toFixed(2);
|
|
52
66
|
};
|
|
67
|
+
|
|
53
68
|
const tableRows = useMemo(() => {
|
|
54
|
-
return
|
|
69
|
+
return filteredAdmissionLocations.map((location) => {
|
|
55
70
|
const url = '${openmrsSpaBase}/home/ward/${locationUuid}';
|
|
56
71
|
|
|
57
72
|
return {
|
|
@@ -68,19 +83,22 @@ const LineListTable = () => {
|
|
|
68
83
|
pendingOut: <WardPendingOutCell locationUuid={location.ward.uuid} />,
|
|
69
84
|
};
|
|
70
85
|
});
|
|
71
|
-
}, [
|
|
86
|
+
}, [filteredAdmissionLocations]);
|
|
87
|
+
|
|
72
88
|
if (isLoading)
|
|
73
89
|
return (
|
|
74
90
|
<Layer className={styles.tableContainer}>
|
|
75
91
|
<DataTableSkeleton />
|
|
76
92
|
</Layer>
|
|
77
93
|
);
|
|
94
|
+
|
|
78
95
|
if (error)
|
|
79
96
|
return (
|
|
80
97
|
<Layer className={styles.tableContainer}>
|
|
81
98
|
<ErrorState headerTitle={headerTitle} error={error} />
|
|
82
99
|
</Layer>
|
|
83
100
|
);
|
|
101
|
+
|
|
84
102
|
return (
|
|
85
103
|
<Tile className={styles.tableContainer}>
|
|
86
104
|
<CardHeader title={headerTitle}>
|