Skip to content

Commit

Permalink
Migrate hiv program management to JSON config workflow
Browse files Browse the repository at this point in the history
  • Loading branch information
hadijahkyampeire committed May 29, 2024
1 parent 02b422a commit 990cfc2
Show file tree
Hide file tree
Showing 11 changed files with 705 additions and 720 deletions.
1 change: 1 addition & 0 deletions packages/esm-commons-lib/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ export * from './utils/ohri-sidebar';
export * from './utils/pagination';
export * from './utils/sidenav-links';
export * from './utils/encounter-list-utils';
export * from './utils/encounter-list-builder';
export * from './workspace/ohri-workspace-utils';
export * from './workspace/patient-list-workspace';
export * from './dashboards/createDashboard';
Expand Down
88 changes: 88 additions & 0 deletions packages/esm-commons-lib/src/utils/encounter-list-builder.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
import { getObsFromEncounter, findObs } from './encounter-list-utils';

interface MenuProps {
menuId: string;
tabDefinitions: Array<TabSchema>;
}
interface ActionProps {
mode: string;
label: string;
package: string;
formName: string;
}
interface ColumnDefinition {
id: string;
title: string;
isComplex?: boolean;
concept?: string;
fallbackConcepts?: Array<string>;
actionOptions?: Array<ActionProps>;
isDate?: boolean;
isTrueFalseConcept?: boolean;
type?: string;
}

interface LaunchOptions {
displayText: string;
moduleName: string;
}
interface TabSchema {
tabName: string;
headerTitle: string;
displayText: string;
encounterType: string;
columns: Array<ColumnDefinition>;
formList: Array<{ name: string; uuid: string }>;
launchOptions: LaunchOptions;
}

interface FormattedColumn {
key: string;
header: string;
getValue: (encounter: any) => string;
link?: any;
}
export const getTabColumns = (columnsDefinition: Array<ColumnDefinition>) => {
const columns: Array<FormattedColumn> = columnsDefinition.map((column: ColumnDefinition) => ({
key: column.id,
header: column.title,
getValue: (encounter) => {
if (column.id === 'actions') {
return column.actionOptions.map((action: ActionProps) => ({
form: { name: action.formName, package: action.package },
encounterUuid: encounter.uuid,
intent: '*',
label: action.label,
mode: action.mode,
}));
} else {
return getObsFromEncounter(
encounter,
column.concept,
column.isDate,
column.isTrueFalseConcept,
column.type,
column.fallbackConcepts,
);
}
},
}));

return columns;
};

export const getMenuItemTabConfiguration = (schemaConfig: MenuProps) => {
const tabs = schemaConfig.tabDefinitions.map((tab) => {
return {
name: tab.tabName,
encounterType: tab.encounterType,
headerTitle: tab.headerTitle,
description: tab.displayText,
formList: tab.formList,
columns: getTabColumns(tab.columns),
launchOptions: tab.launchOptions,
};
});

return tabs;
};
129 changes: 127 additions & 2 deletions packages/esm-commons-lib/src/utils/encounter-list-utils.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,82 @@ export function getObsFromEncounters(encounters, obsConcept) {
return getObsFromEncounter(filteredEnc, obsConcept);
}

const artDateConcepts = {
artTherapyDateTime_UUID: '159599AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
artStopDateUUID: '162572AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
switchDateUUID: '164516AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
substitutionDateUUID: '164431AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
dateRestartedUUID: '160738AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
};

export const getARTDateConcept = (encounter): string => {
let artStartDate = findObs(encounter, artDateConcepts.artTherapyDateTime_UUID);
let artSwitchDate = findObs(encounter, artDateConcepts.switchDateUUID);
let artSubstitutionDate = findObs(encounter, artDateConcepts.substitutionDateUUID);
let artStopDate = findObs(encounter, artDateConcepts.artStopDateUUID);
let artRestartDate = findObs(encounter, artDateConcepts.dateRestartedUUID);

artStartDate = artStartDate ? artStartDate.value : null;
artSubstitutionDate = artSubstitutionDate ? artSubstitutionDate.value : null;
artSwitchDate = artSwitchDate ? artSwitchDate.value : null;
artStopDate = artStopDate ? artStopDate.value : null;
artRestartDate = artRestartDate ? artRestartDate.value : null;

let latestDateConcept: string = artDateConcepts.artTherapyDateTime_UUID;
let latestDate = artStartDate;
if (artSubstitutionDate != null) {
latestDateConcept = artDateConcepts.substitutionDateUUID;
latestDate = artSubstitutionDate;
}
if (artSwitchDate != null) {
latestDate = artSwitchDate;
latestDateConcept = artDateConcepts.switchDateUUID;
}
if (artStopDate != null) {
latestDate = artStopDate;
latestDateConcept = artDateConcepts.artStopDateUUID;
}
if (artRestartDate != null) {
latestDate = artRestartDate;
latestDateConcept = artDateConcepts.dateRestartedUUID;
}

return latestDateConcept;
};

const artReasonConcepts = {
switchReasonUUID: '160568AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
substituteReasonUUID: '160562AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
stopReasonUUID: '163513AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
freeTextCommentConcept: '161011AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA',
};

const getARTReasonConcept = (encounter, startDate, switchDate, substitutionDate, stopDate, restartDate): string => {
const latestDateConcept: string = getARTDateConcept(encounter);

let artReasonConcept;
switch (latestDateConcept) {
case startDate:
artReasonConcept = '';
break;
case substitutionDate:
artReasonConcept = artReasonConcepts.substituteReasonUUID;
break;
case switchDate:
artReasonConcept = artReasonConcepts.switchReasonUUID;
break;
case restartDate:
artReasonConcept = artReasonConcepts.freeTextCommentConcept;
break;
case stopDate:
artReasonConcept = artReasonConcepts.stopReasonUUID;
default:
artReasonConcept = artReasonConcepts.stopReasonUUID;
}

return artReasonConcept;
};

export function getMultipleObsFromEncounter(encounter, obsConcepts: Array<string>) {
let observations = [];
obsConcepts.map((concept) => {
Expand All @@ -40,8 +116,51 @@ export function getMultipleObsFromEncounter(encounter, obsConcepts: Array<string
return observations.length ? observations.join(', ') : '--';
}

export function getObsFromEncounter(encounter, obsConcept, isDate?: Boolean, isTrueFalseConcept?: Boolean) {
const obs = findObs(encounter, obsConcept);
const artConcepts: { [key: string]: string } = {
'1256AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA': 'Start ART',
'1258AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA': 'Substitute ART Regimen',
'1259AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA': 'Switch ART Regimen Line',
'1260AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA': 'Stop ART',
'3e69cb60-2943-410f-83d4-b359ae83fefd': 'Restart ART therapy',
};

export function getObsFromEncounter(
encounter,
obsConcept,
isDate?: Boolean,
isTrueFalseConcept?: Boolean,
type?: string,
fallBackConcepts?: Array<string>,
) {
let obs = findObs(encounter, obsConcept);

// if (type === 'artDate') {
// const artDateConcept = getARTDateConcept(encounter);
// obs = findObs(encounter, artDateConcept);
// }

// if (type === 'artReason') {
// const reasonConcept = getARTReasonConcept(
// encounter,
// artDateConcepts.artTherapyDateTime_UUID,
// artDateConcepts.switchDateUUID,
// artDateConcepts.substitutionDateUUID,
// artDateConcepts.artStopDateUUID,
// artDateConcepts.dateRestartedUUID,
// );
// const artReasonConcept = reasonConcept;
// obs = findObs(encounter, artReasonConcept);
// }

// if (type === 'artTherapy') {
// const therapyObs = findObs(encounter, obsConcept);
// return therapyObs ? artConcepts[therapyObs.value.uuid] : '--';
// }

// if (type === 'transferVerified') {
// const obs = findObs(encounter, obsConcept);
// return obs?.value?.name?.name === 'FALSE' ? 'No' : obs?.value?.name?.name;
// }

if (isTrueFalseConcept) {
if (obs.value.uuid == 'cf82933b-3f3f-45e7-a5ab-5d31aaee3da3') {
Expand All @@ -50,9 +169,15 @@ export function getObsFromEncounter(encounter, obsConcept, isDate?: Boolean, isT
return 'No';
}
}
if (!obs && fallBackConcepts?.length) {
const concept = fallBackConcepts.find((c) => findObs(encounter, c) != null);
obs = findObs(encounter, concept);
}

if (!obs) {
return '--';
}

if (isDate) {
return formatDate(parseDate(obs.value), { mode: 'wide' });
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,12 +1,8 @@
import React from 'react';
import { Tabs, Tab, TabList, TabPanels, TabPanel } from '@carbon/react';
import styles from '../common.scss';
import HIVEnrolmentTabList from './tabs/hiv-enrolment-tab.component';
import ServiceDeliveryTabList from './tabs/service-delivery-tab.component';
import ArtTherapyTabList from './tabs/art-therapy-tab.component';
import DeathTabList from './tabs/death-tab.component';
import TransferOutTabList from './tabs/transfer-out-tab.component';
import PatientTracingList from '../partner-notification-services/tabs/patient-tracing.component';
import { EncounterList, getMenuItemTabConfiguration } from '@ohri/openmrs-esm-ohri-commons-lib';
import programManagementTabConfigSchema from './program-tabs-config.json';
import { useTranslation } from 'react-i18next';

interface OverviewListProps {
Expand All @@ -15,36 +11,30 @@ interface OverviewListProps {

const ProgramManagementSummary: React.FC<OverviewListProps> = ({ patientUuid }) => {
const { t } = useTranslation();
const tabs = getMenuItemTabConfiguration(programManagementTabConfigSchema);

return (
<div className={styles.tabContainer}>
<Tabs>
<TabList contained>
<Tab>{t('hivEnrolment', 'HIV Enrolment')}</Tab>
<Tab>{t('artTherapy', 'ART Therapy')}</Tab>
<Tab>{t('serviceDeliveryModel', 'Service Delivery Model')}</Tab>
<Tab>{t('transferOut', 'Transfer - Out')}</Tab>
<Tab>{t('patientTracing', 'Patient Tracing')}</Tab>
<Tab>{t('death', 'Death')}</Tab>
{tabs.map((tab) => (
<Tab key={tab.name}>{tab.name}</Tab>
))}
</TabList>
<TabPanels>
<TabPanel>
<HIVEnrolmentTabList patientUuid={patientUuid} />
</TabPanel>
<TabPanel>
<ArtTherapyTabList patientUuid={patientUuid} />
</TabPanel>
<TabPanel>
<ServiceDeliveryTabList patientUuid={patientUuid} />
</TabPanel>
<TabPanel>
<TransferOutTabList patientUuid={patientUuid} />
</TabPanel>
<TabPanel>
<PatientTracingList patientUuid={patientUuid} />
</TabPanel>
<TabPanel>
<DeathTabList patientUuid={patientUuid} />
</TabPanel>
{tabs.map((tab) => (
<TabPanel>
<EncounterList
patientUuid={patientUuid}
formList={tab.formList}
columns={tab.columns}
encounterType={tab.encounterType}
launchOptions={tab.launchOptions}
headerTitle={tab.headerTitle}
description={tab.description}
/>
</TabPanel>
))}
</TabPanels>
</Tabs>
</div>
Expand Down
Loading

0 comments on commit 990cfc2

Please sign in to comment.