diff --git a/cypress/e2e/patient_spec/PatientBedManagement.cy.ts b/cypress/e2e/patient_spec/PatientBedManagement.cy.ts
new file mode 100644
index 00000000000..d9453806c9f
--- /dev/null
+++ b/cypress/e2e/patient_spec/PatientBedManagement.cy.ts
@@ -0,0 +1,56 @@
+import LoginPage from "../../pageobject/Login/LoginPage";
+import { PatientPage } from "../../pageobject/Patient/PatientCreation";
+import PatientLogupdate from "../../pageobject/Patient/PatientLogupdate";
+import { PatientConsultationPage } from "../../pageobject/Patient/PatientConsultation";
+
+describe("Patient swtich bed functionality", () => {
+ const loginPage = new LoginPage();
+ const patientPage = new PatientPage();
+ const patientLogupdate = new PatientLogupdate();
+ const patientConsultationPage = new PatientConsultationPage();
+ const switchBedOne = "Dummy Bed 4";
+ const switchBedTwo = "Dummy Bed 1";
+ const switchBedThree = "Dummy Bed 3";
+ const switchPatientOne = "Dummy Patient 6";
+ const switchPatientTwo = "Dummy Patient 7";
+
+ before(() => {
+ loginPage.loginAsDisctrictAdmin();
+ cy.saveLocalStorage();
+ });
+
+ beforeEach(() => {
+ cy.restoreLocalStorage();
+ cy.clearLocalStorage(/filters--.+/);
+ cy.awaitUrl("/patients");
+ });
+
+ it("Assign a bed for a admitted patient from update consultation page", () => {
+ // Open the update consultation page and assign a bed
+ patientPage.visitPatient(switchPatientTwo);
+ patientConsultationPage.clickEditConsultationButton();
+ patientLogupdate.selectBed(switchBedThree);
+ // verify the notification
+ cy.verifyNotification("Bed allocated successfully");
+ });
+
+ it("Assign a bed for a admitted patient from patient dashboard", () => {
+ // Assign a bed to a patient
+ patientPage.visitPatient(switchPatientOne);
+ patientLogupdate.clickSwitchBed();
+ patientLogupdate.selectBed(switchBedOne);
+ cy.verifyNotification("Bed allocated successfully");
+ // Clear the bed and reassign
+ patientLogupdate.clickSwitchBed();
+ cy.get("#clear-button").click();
+ patientLogupdate.selectBed(switchBedTwo);
+ cy.verifyNotification("Bed allocated successfully");
+ // verify the card is reflected
+ patientLogupdate.clickSwitchBed();
+ cy.verifyContentPresence("#previousbed-list", [switchBedOne, switchBedTwo]);
+ });
+
+ afterEach(() => {
+ cy.saveLocalStorage();
+ });
+});
diff --git a/cypress/e2e/patient_spec/PatientHomepage.cy.ts b/cypress/e2e/patient_spec/PatientHomepage.cy.ts
new file mode 100644
index 00000000000..c1575057fe4
--- /dev/null
+++ b/cypress/e2e/patient_spec/PatientHomepage.cy.ts
@@ -0,0 +1,42 @@
+import LoginPage from "../../pageobject/Login/LoginPage";
+import PatientHome from "../../pageobject/Patient/PatientHome";
+
+describe("Patient Homepage present functionalities", () => {
+ const loginPage = new LoginPage();
+ const patientHome = new PatientHome();
+
+ before(() => {
+ loginPage.loginAsDisctrictAdmin();
+ cy.saveLocalStorage();
+ });
+
+ beforeEach(() => {
+ cy.restoreLocalStorage();
+ cy.clearLocalStorage(/filters--.+/);
+ cy.awaitUrl("/patients");
+ });
+
+ it("Verify the functionality of the patient tab pagination", () => {
+ let firstPatientPageOne: string;
+ cy.get('[data-cy="patient"]')
+ .first()
+ .invoke("text")
+ .then((patientOne: string) => {
+ firstPatientPageOne = patientOne.trim();
+ patientHome.clickNextPage();
+ patientHome.verifySecondPageUrl();
+ cy.get('[data-cy="patient"]')
+ .first()
+ .invoke("text")
+ .then((patientTwo: string) => {
+ const firstPatientPageTwo = patientTwo.trim();
+ expect(firstPatientPageOne).not.to.eq(firstPatientPageTwo);
+ patientHome.clickPreviousPage();
+ });
+ });
+ });
+
+ afterEach(() => {
+ cy.saveLocalStorage();
+ });
+});
diff --git a/cypress/e2e/patient_spec/PatientLogUpdate.cy.ts b/cypress/e2e/patient_spec/PatientLogUpdate.cy.ts
index 99d4170fde5..7faaeed5a9f 100644
--- a/cypress/e2e/patient_spec/PatientLogUpdate.cy.ts
+++ b/cypress/e2e/patient_spec/PatientLogUpdate.cy.ts
@@ -12,7 +12,6 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
const patientLogupdate = new PatientLogupdate();
const patientInvestigation = new PatientInvestigation();
const patientPrescription = new PatientPrescription();
- const domicilaryPatient = "Dummy Patient 11";
const patientCategory = "Moderate";
const additionalSymptoms = "Fever";
const physicalExamination = "physical examination details";
@@ -33,6 +32,13 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
const patientInsulinDosage = "56";
const patientFluidBalance = "500";
const patientNetBalance = "1000";
+ const patientOne = "Dummy Patient 9";
+ const bedOne = "Dummy Bed 5";
+ const patientTwo = "Dummy Patient 10";
+ const bedTwo = "Dummy Bed 2";
+ const patientThree = "Dummy Patient 8";
+ const bedThree = "Dummy Bed 3";
+ const domicilaryPatient = "Dummy Patient 11";
before(() => {
loginPage.loginAsDisctrictAdmin();
@@ -45,15 +51,110 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
cy.awaitUrl("/patients");
});
- it("Create a basic critical care log update for a admitted patient and edit it", () => {
- patientPage.visitPatient("Dummy Patient 10");
+ it("Create a new TeleIcu log update for a domicilary care patient", () => {
+ patientPage.visitPatient(domicilaryPatient);
+ patientConsultationPage.clickEditConsultationButton();
+ patientConsultationPage.selectPatientSuggestion("Domiciliary Care");
+ cy.submitButton("Update Consultation");
+ cy.verifyNotification("Consultation updated successfully");
+ cy.closeNotification();
+ patientLogupdate.clickLogupdate();
+ patientLogupdate.typePhysicalExamination(physicalExamination);
+ patientLogupdate.selectRoundType("Tele-medicine Log");
+ patientLogupdate.selectPatientCategory(patientCategory);
+ patientLogupdate.typeOtherDetails(otherExamination);
+ patientLogupdate.selectSymptomsDate("01012024");
+ patientLogupdate.typeAndMultiSelectSymptoms("fe", ["Fever"]);
+ patientLogupdate.typeSystolic(patientSystolic);
+ patientLogupdate.typeDiastolic(patientDiastolic);
+ patientLogupdate.typePulse(patientPulse);
+ patientLogupdate.typeTemperature(patientTemperature);
+ patientLogupdate.typeRespiratory(patientRespiratory);
+ patientLogupdate.typeSpo2(patientSpo2);
+ patientLogupdate.selectRhythm(patientRhythmType);
+ patientLogupdate.typeRhythm(patientRhythm);
+ cy.get("#consciousness_level-option-RESPONDS_TO_PAIN").click();
+ cy.submitButton("Save");
+ cy.verifyNotification("Tele-medicine Log created successfully");
+ });
+
+ it("Create a new Progress log update for a admitted patient and edit it", () => {
+ patientPage.visitPatient(patientOne);
patientLogupdate.clickLogupdate();
cy.verifyNotification("Please assign a bed to the patient");
- patientLogupdate.selectBed("Dummy Bed 2");
+ patientLogupdate.selectBed(bedOne);
cy.closeNotification();
patientLogupdate.clickLogupdate();
+ // Only will be using random non-unique progress note fields
+ patientLogupdate.selectRoundType("Progress Note");
patientLogupdate.selectPatientCategory(patientCategory);
+ patientLogupdate.selectSymptomsDate("01012024");
+ patientLogupdate.typeAndMultiSelectSymptoms("fe", ["Fever"]);
+ patientLogupdate.typeTemperature(patientTemperature);
+ // add diagnosis
+ patientConsultationPage.selectPatientDiagnosis(
+ "1A06",
+ "add-icd11-diagnosis-as-differential",
+ );
+ // add a investigation for the patient
+ patientInvestigation.clickAddInvestigation();
+ patientInvestigation.selectInvestigation("Vitals (GROUP)");
+ patientInvestigation.clickInvestigationCheckbox();
+ patientInvestigation.selectInvestigationFrequency("6");
+ // add a medicine for the patient
+ patientPrescription.clickAddPrescription();
+ patientPrescription.interceptMedibase();
+ patientPrescription.selectMedicinebox();
+ patientPrescription.selectMedicine("DOLO");
+ patientPrescription.enterDosage("4");
+ patientPrescription.selectDosageFrequency("Twice daily");
+ cy.submitButton("Submit");
+ cy.verifyNotification("Medicine prescribed");
+ cy.closeNotification();
+ // Submit the doctors log update
+ cy.submitButton("Save and Continue");
+ cy.verifyNotification("Progress Note created successfully");
+ cy.closeNotification();
+ // modify the relevant critical care log update
+ patientLogupdate.selectCriticalCareSection("Neurological Monitoring");
+ cy.get("#consciousness_level-option-RESPONDS_TO_PAIN").click();
+ cy.get("#left_pupil_light_reaction-option-FIXED").click();
+ cy.submitButton("Update Details");
+ cy.verifyNotification(
+ "Neurological Monitoring details succesfully updated.",
+ );
+ cy.closeNotification();
+ // Final Submission of the form
+ cy.submitButton("Complete");
+ cy.verifyNotification("Progress Note Log Update filed successfully");
+ cy.closeNotification();
+ // Verify the data reflection
+ cy.contains("button", "Daily Rounds").click();
+ patientLogupdate.clickLogUpdateViewDetails(
+ "#dailyround-entry",
+ patientCategory,
+ );
+ cy.verifyContentPresence("#consultation-preview", [
+ patientCategory,
+ patientTemperature,
+ ]);
+ // verify the edit functionality
+ patientLogupdate.clickUpdateDetail();
+ patientLogupdate.typeSystolic(patientModifiedSystolic);
+ patientLogupdate.typeDiastolic(patientModifiedDiastolic);
+ cy.submitButton("Continue");
+ cy.verifyNotification("Progress Note updated successfully");
+ });
+
+ it("Create a basic critical care log update for a admitted patient and edit it", () => {
+ patientPage.visitPatient(patientTwo);
+ patientLogupdate.clickLogupdate();
+ cy.verifyNotification("Please assign a bed to the patient");
+ patientLogupdate.selectBed(bedTwo);
+ cy.closeNotification();
+ patientLogupdate.clickLogupdate();
patientLogupdate.selectRoundType("Detailed Update");
+ patientLogupdate.selectPatientCategory(patientCategory);
cy.submitButton("Save and Continue");
cy.verifyNotification("Detailed Update created successfully");
cy.closeNotification();
@@ -127,88 +228,19 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
]);
});
- it("Create a new Progress log update for a admitted patient and edit it", () => {
- patientPage.visitPatient("Dummy Patient 12");
+ it("Create a new Normal update for a admission patient and verify its reflection in cards", () => {
+ patientPage.visitPatient(patientThree);
patientLogupdate.clickLogupdate();
cy.verifyNotification("Please assign a bed to the patient");
- patientLogupdate.selectBed("Dummy Bed 4");
- cy.closeNotification();
- patientLogupdate.clickLogupdate();
- // Only will be using random non-unique progress note fields
- patientLogupdate.selectPatientCategory(patientCategory);
- patientLogupdate.selectRoundType("Progress Note");
- patientLogupdate.selectSymptomsDate("01012024");
- patientLogupdate.typeAndMultiSelectSymptoms("fe", ["Fever"]);
- patientLogupdate.typeTemperature(patientTemperature);
- // add diagnosis
- patientConsultationPage.selectPatientDiagnosis(
- "1A06",
- "add-icd11-diagnosis-as-differential",
- );
- // add a investigation for the patient
- patientInvestigation.clickAddInvestigation();
- patientInvestigation.selectInvestigation("Vitals (GROUP)");
- patientInvestigation.clickInvestigationCheckbox();
- patientInvestigation.selectInvestigationFrequency("6");
- // add a medicine for the patient
- patientPrescription.clickAddPrescription();
- patientPrescription.interceptMedibase();
- patientPrescription.selectMedicinebox();
- patientPrescription.selectMedicine("DOLO");
- patientPrescription.enterDosage("4");
- patientPrescription.selectDosageFrequency("Twice daily");
- cy.submitButton("Submit");
- cy.verifyNotification("Medicine prescribed");
- cy.closeNotification();
- // Submit the doctors log update
- cy.submitButton("Save and Continue");
- cy.verifyNotification("Progress Note created successfully");
- cy.closeNotification();
- // modify the relevant critical care log update
- patientLogupdate.selectCriticalCareSection("Neurological Monitoring");
- cy.get("#consciousness_level-option-RESPONDS_TO_PAIN").click();
- cy.get("#left_pupil_light_reaction-option-FIXED").click();
- cy.submitButton("Update Details");
- cy.verifyNotification(
- "Neurological Monitoring details succesfully updated.",
- );
- cy.closeNotification();
- // Final Submission of the form
- cy.submitButton("Complete");
- cy.verifyNotification("Progress Note Log Update filed successfully");
- cy.closeNotification();
- // Verify the data reflection
- cy.contains("button", "Daily Rounds").click();
- patientLogupdate.clickLogUpdateViewDetails(
- "#dailyround-entry",
- patientCategory,
- );
- cy.verifyContentPresence("#consultation-preview", [
- patientCategory,
- patientTemperature,
- ]);
- // verify the edit functionality
- patientLogupdate.clickUpdateDetail();
- patientLogupdate.typeSystolic(patientModifiedSystolic);
- patientLogupdate.typeDiastolic(patientModifiedDiastolic);
- cy.submitButton("Continue");
- cy.verifyNotification("Progress Note updated successfully");
- });
-
- it("Create a new TeleIcu log update for a domicilary care patient", () => {
- patientPage.visitPatient("Dummy Patient 11");
- patientConsultationPage.clickEditConsultationButton();
- patientConsultationPage.selectPatientSuggestion("Domiciliary Care");
- cy.submitButton("Update Consultation");
- cy.verifyNotification("Consultation updated successfully");
+ patientLogupdate.selectBed(bedThree);
cy.closeNotification();
patientLogupdate.clickLogupdate();
patientLogupdate.typePhysicalExamination(physicalExamination);
- patientLogupdate.selectRoundType("Tele-medicine Log");
+ patientLogupdate.selectPatientCategory(patientCategory);
patientLogupdate.typeOtherDetails(otherExamination);
patientLogupdate.selectSymptomsDate("01012024");
patientLogupdate.typeAndMultiSelectSymptoms("fe", ["Fever"]);
- patientLogupdate.selectPatientCategory(patientCategory);
+ patientLogupdate.clickAddSymptom();
patientLogupdate.typeSystolic(patientSystolic);
patientLogupdate.typeDiastolic(patientDiastolic);
patientLogupdate.typePulse(patientPulse);
@@ -219,7 +251,11 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
patientLogupdate.typeRhythm(patientRhythm);
cy.get("#consciousness_level-option-RESPONDS_TO_PAIN").click();
cy.submitButton("Save");
- cy.verifyNotification("Tele-medicine Log created successfully");
+ cy.wait(2000);
+ cy.verifyNotification("Brief Update created successfully");
+ // Verify the card content
+ cy.get("#basic-information").scrollIntoView();
+ cy.verifyContentPresence("#encounter-symptoms", [additionalSymptoms]);
});
it("Create a new Normal Log update for a domicilary care patient and edit it", () => {
@@ -283,36 +319,6 @@ describe("Patient Log Update in Normal, Critical and TeleIcu", () => {
]);
});
- it("Create a new Normal update for a admission patient and verify its reflection in cards", () => {
- patientPage.visitPatient("Dummy Patient 13");
- patientLogupdate.clickLogupdate();
- cy.verifyNotification("Please assign a bed to the patient");
- patientLogupdate.selectBed("Dummy Bed 6");
- cy.closeNotification();
- patientLogupdate.clickLogupdate();
- patientLogupdate.typePhysicalExamination(physicalExamination);
- patientLogupdate.typeOtherDetails(otherExamination);
- patientLogupdate.selectSymptomsDate("01012024");
- patientLogupdate.typeAndMultiSelectSymptoms("fe", ["Fever"]);
- patientLogupdate.clickAddSymptom();
- patientLogupdate.selectPatientCategory(patientCategory);
- patientLogupdate.typeSystolic(patientSystolic);
- patientLogupdate.typeDiastolic(patientDiastolic);
- patientLogupdate.typePulse(patientPulse);
- patientLogupdate.typeTemperature(patientTemperature);
- patientLogupdate.typeRespiratory(patientRespiratory);
- patientLogupdate.typeSpo2(patientSpo2);
- patientLogupdate.selectRhythm(patientRhythmType);
- patientLogupdate.typeRhythm(patientRhythm);
- cy.get("#consciousness_level-option-RESPONDS_TO_PAIN").click();
- cy.submitButton("Save");
- cy.wait(2000);
- cy.verifyNotification("Brief Update created successfully");
- // Verify the card content
- cy.get("#basic-information").scrollIntoView();
- cy.verifyContentPresence("#encounter-symptoms", [additionalSymptoms]);
- });
-
it("Create a Normal Log update to verify MEWS Score Functionality", () => {
patientPage.visitPatient(domicilaryPatient);
patientConsultationPage.clickEditConsultationButton();
diff --git a/cypress/pageobject/Patient/PatientHome.ts b/cypress/pageobject/Patient/PatientHome.ts
new file mode 100644
index 00000000000..94801cd4bb8
--- /dev/null
+++ b/cypress/pageobject/Patient/PatientHome.ts
@@ -0,0 +1,14 @@
+class PatientHome {
+ clickNextPage() {
+ cy.get("#next-pages").click();
+ }
+
+ verifySecondPageUrl() {
+ cy.url().should("include", "/patients?page=2");
+ }
+
+ clickPreviousPage() {
+ cy.get("#prev-pages").click();
+ }
+}
+export default PatientHome;
diff --git a/cypress/pageobject/Patient/PatientLogupdate.ts b/cypress/pageobject/Patient/PatientLogupdate.ts
index 8a4c11ab25b..add3fbb0590 100644
--- a/cypress/pageobject/Patient/PatientLogupdate.ts
+++ b/cypress/pageobject/Patient/PatientLogupdate.ts
@@ -5,13 +5,17 @@ class PatientLogupdate {
cy.wait(2000);
}
+ clickSwitchBed() {
+ cy.get("#switch-bed").click();
+ }
+
selectRoundType(roundType: string) {
cy.clickAndSelectOption("#rounds_type", roundType);
}
selectBed(bed: string) {
cy.searchAndSelectOption("input[name='bed']", bed);
- cy.submitButton("Update");
+ cy.get("#update-switchbed").click();
cy.wait(2000);
}
diff --git a/package-lock.json b/package-lock.json
index 99f4f706f58..051c12bd2b4 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -56,6 +56,7 @@
"@tailwindcss/container-queries": "^0.1.1",
"@tailwindcss/forms": "^0.5.7",
"@tailwindcss/typography": "^0.5.13",
+ "@types/cypress": "^1.1.3",
"@types/events": "^3.0.3",
"@types/google.maps": "^3.55.8",
"@types/lodash-es": "^4.17.12",
@@ -68,7 +69,7 @@
"@typescript-eslint/eslint-plugin": "^7.18.0",
"@vitejs/plugin-react-swc": "^3.6.0",
"autoprefixer": "^10.4.19",
- "cypress": "^13.14.1",
+ "cypress": "^13.14.2",
"cypress-localstorage-commands": "^2.2.5",
"cypress-split": "^1.23.2",
"eslint-config-prettier": "^9.1.0",
@@ -4425,6 +4426,16 @@
"@types/node": "*"
}
},
+ "node_modules/@types/cypress": {
+ "version": "1.1.3",
+ "resolved": "https://registry.npmjs.org/@types/cypress/-/cypress-1.1.3.tgz",
+ "integrity": "sha512-OXe0Gw8LeCflkG1oPgFpyrYWJmEKqYncBsD/J0r17r0ETx/TnIGDNLwXt/pFYSYuYTpzcq1q3g62M9DrfsBL4g==",
+ "deprecated": "This is a stub types definition for cypress (https://cypress.io). cypress provides its own type definitions, so you don't need @types/cypress installed!",
+ "dev": true,
+ "dependencies": {
+ "cypress": "*"
+ }
+ },
"node_modules/@types/debug": {
"version": "4.1.12",
"resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.12.tgz",
@@ -6629,9 +6640,9 @@
"integrity": "sha512-M1uQkMl8rQK/szD0LNhtqxIPLpimGm8sOBwU7lLnCpSbTyY3yeU1Vc7l4KT5zT4s/yOxHH5O7tIuuLOCnLADRw=="
},
"node_modules/cypress": {
- "version": "13.14.1",
- "resolved": "https://registry.npmjs.org/cypress/-/cypress-13.14.1.tgz",
- "integrity": "sha512-Wo+byPmjps66hACEH5udhXINEiN3qS3jWNGRzJOjrRJF3D0+YrcP2LVB1T7oYaVQM/S+eanqEvBWYc8cf7Vcbg==",
+ "version": "13.14.2",
+ "resolved": "https://registry.npmjs.org/cypress/-/cypress-13.14.2.tgz",
+ "integrity": "sha512-lsiQrN17vHMB2fnvxIrKLAjOr9bPwsNbPZNrWf99s4u+DVmCY6U+w7O3GGG9FvP4EUVYaDu+guWeNLiUzBrqvA==",
"dev": true,
"hasInstallScript": true,
"dependencies": {
diff --git a/package.json b/package.json
index cc2c7b955c2..62cdc8a0fb9 100644
--- a/package.json
+++ b/package.json
@@ -91,6 +91,7 @@
"@tailwindcss/container-queries": "^0.1.1",
"@tailwindcss/forms": "^0.5.7",
"@tailwindcss/typography": "^0.5.13",
+ "@types/cypress": "^1.1.3",
"@types/events": "^3.0.3",
"@types/google.maps": "^3.55.8",
"@types/lodash-es": "^4.17.12",
@@ -103,7 +104,7 @@
"@typescript-eslint/eslint-plugin": "^7.18.0",
"@vitejs/plugin-react-swc": "^3.6.0",
"autoprefixer": "^10.4.19",
- "cypress": "^13.14.1",
+ "cypress": "^13.14.2",
"cypress-localstorage-commands": "^2.2.5",
"cypress-split": "^1.23.2",
"eslint-config-prettier": "^9.1.0",
diff --git a/src/CAREUI/display/Timeline.tsx b/src/CAREUI/display/Timeline.tsx
index 7fcb57f56ea..ee21b337724 100644
--- a/src/CAREUI/display/Timeline.tsx
+++ b/src/CAREUI/display/Timeline.tsx
@@ -26,7 +26,7 @@ const TimelineContext = createContext("");
export default function Timeline({ className, children, name }: TimelineProps) {
return (
-
+
{children}
diff --git a/src/Common/constants.tsx b/src/Common/constants.tsx
index 307e912844f..70b5bc78e23 100644
--- a/src/Common/constants.tsx
+++ b/src/Common/constants.tsx
@@ -1,4 +1,7 @@
-import { PatientCategory } from "../Components/Facility/models";
+import {
+ PatientCategory,
+ SpokeRelationship,
+} from "../Components/Facility/models";
import { SortOption } from "../Components/Common/SortDropdown";
import { dateQueryString } from "../Utils/utils";
import { IconName } from "../CAREUI/icons/CareIcon";
@@ -1517,6 +1520,17 @@ export const DEFAULT_ALLOWED_EXTENSIONS = [
"application/vnd.oasis.opendocument.spreadsheet,application/pdf",
];
+export const SPOKE_RELATION_TYPES = [
+ {
+ text: "Regular",
+ value: SpokeRelationship.REGULAR,
+ },
+ {
+ text: "Tele ICU",
+ value: SpokeRelationship.TELE_ICU,
+ },
+];
+
export const HumanBodyPaths = {
anterior: [
{
diff --git a/src/Common/hooks/useFilters.tsx b/src/Common/hooks/useFilters.tsx
index a4b924edcdb..188dec2229d 100644
--- a/src/Common/hooks/useFilters.tsx
+++ b/src/Common/hooks/useFilters.tsx
@@ -109,7 +109,7 @@ export default function useFilters({
return {
name,
paramKey,
- value: qParams[paramKey] && t("SortOptions." + qParams[paramKey]),
+ value: qParams[paramKey] && t("SORT_OPTIONS__" + qParams[paramKey]),
};
},
value(name: string, paramKey: FilterBadgeProps["paramKey"], value: string) {
diff --git a/src/Components/Common/FacilitySelect.tsx b/src/Components/Common/FacilitySelect.tsx
index d718ef3e781..d91b9a7f8fc 100644
--- a/src/Components/Common/FacilitySelect.tsx
+++ b/src/Components/Common/FacilitySelect.tsx
@@ -23,6 +23,8 @@ interface FacilitySelectProps {
selected?: FacilityModel | FacilityModel[] | null;
setSelected: (selected: FacilityModel | FacilityModel[] | null) => void;
allowNone?: boolean;
+ placeholder?: string;
+ filter?: (facilities: FacilityModel) => boolean;
}
export const FacilitySelect = (props: FacilitySelectProps) => {
@@ -44,6 +46,8 @@ export const FacilitySelect = (props: FacilitySelectProps) => {
allowNone = false,
freeText = false,
errors = "",
+ placeholder,
+ filter,
} = props;
const facilitySearch = useCallback(
@@ -82,6 +86,7 @@ export const FacilitySelect = (props: FacilitySelectProps) => {
return (
{
compareBy="id"
className={className}
error={errors}
+ filter={filter}
/>
);
};
diff --git a/src/Components/Common/Sidebar/Sidebar.tsx b/src/Components/Common/Sidebar/Sidebar.tsx
index 52e5e0680fa..e18c17bcb68 100644
--- a/src/Components/Common/Sidebar/Sidebar.tsx
+++ b/src/Components/Common/Sidebar/Sidebar.tsx
@@ -70,7 +70,7 @@ const StatelessSidebar = ({
const [lastIndicatorPosition, setLastIndicatorPosition] = useState(0);
const [isOverflowVisible, setOverflowVisisble] = useState(false);
- useEffect(() => {
+ const updateIndicator = () => {
if (!indicatorRef.current) return;
const index = NavItems.findIndex((item) => item.to === activeLink);
const navItemCount = NavItems.length + (careConfig.urls.dashboard ? 2 : 1); // +2 for notification and dashboard
@@ -94,8 +94,17 @@ const StatelessSidebar = ({
} else {
indicatorRef.current.style.display = "none";
}
+ };
+
+ useEffect(() => {
+ updateIndicator();
}, [activeLink, lastIndicatorPosition]);
+ useEffect(() => {
+ addEventListener("resize", updateIndicator);
+ return () => removeEventListener("resize", updateIndicator);
+ }, []);
+
const handleOverflow = (value: boolean) => {
setOverflowVisisble(value);
};
diff --git a/src/Components/Common/SortDropdown.tsx b/src/Components/Common/SortDropdown.tsx
index 8ffd09ba269..b54edffa595 100644
--- a/src/Components/Common/SortDropdown.tsx
+++ b/src/Components/Common/SortDropdown.tsx
@@ -41,7 +41,7 @@ export default function SortDropdownMenu(props: Props) {
/>
}
>
- {t("SortOptions." + value)}
+ {t("SORT_OPTIONS__" + value)}
))}
diff --git a/src/Components/Facility/CentralNursingStation.tsx b/src/Components/Facility/CentralNursingStation.tsx
index 178bd2bc25c..fbbdf24d7f2 100644
--- a/src/Components/Facility/CentralNursingStation.tsx
+++ b/src/Components/Facility/CentralNursingStation.tsx
@@ -145,7 +145,7 @@ export default function CentralNursingStation({ facilityId }: Props) {
value={qParams.ordering || "bed__name"}
onChange={({ value }) => updateQuery({ ordering: value })}
options={SORT_OPTIONS}
- optionLabel={({ value }) => t("SortOptions." + value)}
+ optionLabel={({ value }) => t("SORT_OPTIONS__" + value)}
optionIcon={({ isAscending }) => (
{
const [facilityName, setFacilityName] = useState("");
const [patientName, setPatientName] = useState("");
const [focused, setFocused] = useState(false);
+ const [reply_to, setReplyTo] = useState(
+ undefined,
+ );
const initialData: PatientNoteStateType = {
notes: [],
@@ -65,6 +69,7 @@ const ConsultationDoctorNotes = (props: ConsultationDoctorNotesProps) => {
note: noteField,
thread,
consultation: consultationId,
+ reply_to: reply_to?.id,
},
});
@@ -73,6 +78,7 @@ const ConsultationDoctorNotes = (props: ConsultationDoctorNotesProps) => {
setState({ ...state, cPage: 1 });
setNoteField("");
setReload(true);
+ setReplyTo(undefined);
}
};
@@ -145,36 +151,41 @@ const ConsultationDoctorNotes = (props: ConsultationDoctorNotesProps) => {
reload={reload}
setReload={setReload}
thread={thread}
+ setReplyTo={setReplyTo}
/>
-
-
-
setNoteField(e.value)}
- className="w-full grow"
- innerClassName="pr-10"
- errorClassName="hidden"
- placeholder={t("notes_placeholder")}
- disabled={!patientActive}
- onFocus={() => setFocused(true)}
- onBlur={() => setFocused(false)}
- />
-
-
-
-
+ setReplyTo(undefined)}
+ >
+
+
setNoteField(e.value)}
+ className="w-full grow"
+ innerClassName="pr-10"
+ errorClassName="hidden"
+ placeholder={t("notes_placeholder")}
+ disabled={!patientActive}
+ onFocus={() => setFocused(true)}
+ onBlur={() => setFocused(false)}
+ />
+
+
+
+
+
);
diff --git a/src/Components/Facility/Consultations/Beds.tsx b/src/Components/Facility/Consultations/Beds.tsx
index 0333ec40f63..0b62af9fdcb 100644
--- a/src/Components/Facility/Consultations/Beds.tsx
+++ b/src/Components/Facility/Consultations/Beds.tsx
@@ -231,7 +231,7 @@ const Beds = (props: BedsProps) => {
-
+
Update
diff --git a/src/Components/Facility/DoctorNote.tsx b/src/Components/Facility/DoctorNote.tsx
index 91c361cc82e..c2bf8155cf2 100644
--- a/src/Components/Facility/DoctorNote.tsx
+++ b/src/Components/Facility/DoctorNote.tsx
@@ -1,17 +1,19 @@
import InfiniteScroll from "react-infinite-scroll-component";
import CircularProgress from "../Common/components/CircularProgress";
import PatientNoteCard from "./PatientNoteCard";
-import { PatientNoteStateType } from "./models";
+import { PatientNoteStateType, PatientNotesModel } from "./models";
+import DoctorNoteReplyPreviewCard from "./DoctorNoteReplyPreviewCard";
interface DoctorNoteProps {
state: PatientNoteStateType;
setReload: any;
handleNext: () => void;
disableEdit?: boolean;
+ setReplyTo?: (reply_to: PatientNotesModel | undefined) => void;
}
const DoctorNote = (props: DoctorNoteProps) => {
- const { state, handleNext, setReload, disableEdit } = props;
+ const { state, handleNext, setReload, disableEdit, setReplyTo } = props;
return (
{
scrollableTarget="patient-notes-list"
>
{state.notes.map((note) => (
-
+ parentNote={note.reply_to_object}
+ >
+
+
))}
) : (
diff --git a/src/Components/Facility/DoctorNoteReplyPreviewCard.tsx b/src/Components/Facility/DoctorNoteReplyPreviewCard.tsx
new file mode 100644
index 00000000000..470f05f2bfe
--- /dev/null
+++ b/src/Components/Facility/DoctorNoteReplyPreviewCard.tsx
@@ -0,0 +1,64 @@
+import React from "react";
+import { PaitentNotesReplyModel } from "./models";
+import { USER_TYPES_MAP } from "../../Common/constants";
+import { formatDateTime, relativeDate } from "../../Utils/utils";
+
+interface Props {
+ parentNote: PaitentNotesReplyModel | undefined;
+ children: React.ReactNode;
+ cancelReply?: () => void;
+}
+
+const DoctorNoteReplyPreviewCard = ({
+ parentNote,
+ children,
+ cancelReply,
+}: Props) => {
+ return (
+
+ {parentNote ? (
+
+
+
+
+
+
+ {parentNote.created_by_object?.first_name || "Unknown"}{" "}
+ {parentNote.created_by_object?.last_name}
+
+ {parentNote.user_type && (
+
+ {`(${USER_TYPES_MAP[parentNote.user_type]})`}
+
+ )}
+
+
+
+
+ {formatDateTime(parentNote.created_date)}
+
+ Created {relativeDate(parentNote.created_date, true)}
+
+
+
+ {cancelReply && (
+
+ Cancel
+
+ )}
+
+
{parentNote.note}
+
+
{children}
+
+ ) : (
+
{children}
+ )}
+
+ );
+};
+
+export default DoctorNoteReplyPreviewCard;
diff --git a/src/Components/Facility/FacilityBlock.tsx b/src/Components/Facility/FacilityBlock.tsx
new file mode 100644
index 00000000000..64c0a24d78d
--- /dev/null
+++ b/src/Components/Facility/FacilityBlock.tsx
@@ -0,0 +1,34 @@
+import { Link } from "raviger";
+import CareIcon from "../../CAREUI/icons/CareIcon";
+import { FacilityModel } from "./models";
+
+export default function FacilityBlock(props: { facility: FacilityModel }) {
+ const { facility } = props;
+
+ return (
+
+
+ {facility.read_cover_image_url ? (
+
+ ) : (
+ <>
+
+ >
+ )}
+
+
+
{facility.name}
+
+ {facility.address} {facility.local_body_object?.name}
+
+
+
+ );
+}
diff --git a/src/Components/Facility/FacilityCreate.tsx b/src/Components/Facility/FacilityCreate.tsx
index 1fe9d2e207e..e9e95fbcdfc 100644
--- a/src/Components/Facility/FacilityCreate.tsx
+++ b/src/Components/Facility/FacilityCreate.tsx
@@ -62,6 +62,7 @@ import routes from "../../Redux/api.js";
import useQuery from "../../Utils/request/useQuery.js";
import { RequestResult } from "../../Utils/request/types.js";
import useAuthUser from "../../Common/hooks/useAuthUser";
+import SpokeFacilityEditor from "./SpokeFacilityEditor.js";
import careConfig from "@careConfig";
const Loading = lazy(() => import("../Common/Loading"));
@@ -247,7 +248,7 @@ export const FacilityCreate = (props: FacilityProps) => {
},
);
- useQuery(routes.getPermittedFacility, {
+ const facilityQuery = useQuery(routes.getPermittedFacility, {
pathParams: {
id: facilityId!,
},
@@ -850,6 +851,14 @@ export const FacilityCreate = (props: FacilityProps) => {
required
types={["mobile", "landline"]}
/>
+
+
{t("spokes")}
+ {facilityId && (
+
+ )}
+
{
});
};
+ const spokesQuery = useQuery(routes.getFacilitySpokes, {
+ pathParams: {
+ id: facilityId,
+ },
+ silent: true,
+ });
+
if (isLoading) {
return ;
}
@@ -276,6 +284,20 @@ export const FacilityHome = ({ facilityId }: Props) => {
/>
+ {!!spokesQuery.data?.results.length && (
+
+
+
+ {t("spokes")}
+
+
+ {spokesQuery.data?.results.map((spoke) => (
+
+ ))}
+
+
+
+ )}
diff --git a/src/Components/Facility/PatientConsultationNotesList.tsx b/src/Components/Facility/PatientConsultationNotesList.tsx
index f81ef122f6c..15238ff189f 100644
--- a/src/Components/Facility/PatientConsultationNotesList.tsx
+++ b/src/Components/Facility/PatientConsultationNotesList.tsx
@@ -14,12 +14,21 @@ interface PatientNotesProps {
setReload?: (value: boolean) => void;
disableEdit?: boolean;
thread: PatientNotesModel["thread"];
+ setReplyTo?: (value: PatientNotesModel | undefined) => void;
}
const pageSize = RESULTS_PER_PAGE_LIMIT;
const PatientConsultationNotesList = (props: PatientNotesProps) => {
- const { state, setState, reload, setReload, disableEdit, thread } = props;
+ const {
+ state,
+ setState,
+ reload,
+ setReload,
+ disableEdit,
+ thread,
+ setReplyTo,
+ } = props;
const consultationId = useSlug("consultation") ?? "";
const [isLoading, setIsLoading] = useState(true);
@@ -95,6 +104,7 @@ const PatientConsultationNotesList = (props: PatientNotesProps) => {
handleNext={handleNext}
setReload={setReload}
disableEdit={disableEdit}
+ setReplyTo={setReplyTo}
/>
);
};
diff --git a/src/Components/Facility/PatientNoteCard.tsx b/src/Components/Facility/PatientNoteCard.tsx
index 7d2a8c6eb70..9ddfbc009e6 100644
--- a/src/Components/Facility/PatientNoteCard.tsx
+++ b/src/Components/Facility/PatientNoteCard.tsx
@@ -23,10 +23,12 @@ const PatientNoteCard = ({
note,
setReload,
disableEdit,
+ setReplyTo,
}: {
note: PatientNotesModel;
setReload: any;
disableEdit?: boolean;
+ setReplyTo?: (reply_to: PatientNotesModel | undefined) => void;
}) => {
const patientId = useSlug("patient");
const [isEditing, setIsEditing] = useState(false);
@@ -128,19 +130,28 @@ const PatientNoteCard = ({
)
}
-
- {!disableEdit &&
- note.created_by_object.id === authUser.id &&
- !isEditing && (
- {
- setIsEditing(true);
- }}
- >
-
-
- )}
+
+ {!disableEdit &&
+ note.created_by_object.id === authUser.id &&
+ !isEditing && (
+ {
+ setIsEditing(true);
+ }}
+ >
+
+
+ )}
+ {
+ setReplyTo && setReplyTo(note);
+ }}
+ >
+
+
+
{
diff --git a/src/Components/Facility/PatientNotesList.tsx b/src/Components/Facility/PatientNotesList.tsx
index 4e1d0a5a7a6..bbd037e866c 100644
--- a/src/Components/Facility/PatientNotesList.tsx
+++ b/src/Components/Facility/PatientNotesList.tsx
@@ -14,12 +14,13 @@ interface PatientNotesProps {
reload?: boolean;
setReload?: any;
thread: PatientNotesModel["thread"];
+ setReplyTo?: (reply_to: PatientNotesModel | undefined) => void;
}
const pageSize = RESULTS_PER_PAGE_LIMIT;
const PatientNotesList = (props: PatientNotesProps) => {
- const { state, setState, reload, setReload, thread } = props;
+ const { state, setState, reload, setReload, thread, setReplyTo } = props;
const [isLoading, setIsLoading] = useState(true);
@@ -83,7 +84,12 @@ const PatientNotesList = (props: PatientNotesProps) => {
}
return (
-
+
);
};
diff --git a/src/Components/Facility/PatientNotesSlideover.tsx b/src/Components/Facility/PatientNotesSlideover.tsx
index d7847c3add7..52f99aee763 100644
--- a/src/Components/Facility/PatientNotesSlideover.tsx
+++ b/src/Components/Facility/PatientNotesSlideover.tsx
@@ -8,11 +8,12 @@ import { useMessageListener } from "../../Common/hooks/useMessageListener";
import PatientConsultationNotesList from "./PatientConsultationNotesList";
import request from "../../Utils/request/request";
import routes from "../../Redux/api";
-import { PatientNoteStateType } from "./models";
+import { PatientNoteStateType, PaitentNotesReplyModel } from "./models";
import useKeyboardShortcut from "use-keyboard-shortcut";
import AutoExpandingTextInputFormField from "../Form/FormFields/AutoExpandingTextInputFormField.js";
import useAuthUser from "../../Common/hooks/useAuthUser";
import { PATIENT_NOTES_THREADS } from "../../Common/constants.js";
+import DoctorNoteReplyPreviewCard from "./DoctorNoteReplyPreviewCard.js";
import useNotificationSubscriptionState from "../../Common/hooks/useNotificationSubscriptionState.js";
import { Link } from "raviger";
import { t } from "i18next";
@@ -36,6 +37,9 @@ export default function PatientNotesSlideover(props: PatientNotesProps) {
const [patientActive, setPatientActive] = useState(true);
const [reload, setReload] = useState(false);
const [focused, setFocused] = useState(false);
+ const [reply_to, setReplyTo] = useState
(
+ undefined,
+ );
useEffect(() => {
if (notificationSubscriptionState === "unsubscribed") {
@@ -79,6 +83,7 @@ export default function PatientNotesSlideover(props: PatientNotesProps) {
note: noteField,
consultation: consultationId,
thread,
+ reply_to: reply_to?.id,
},
});
if (res?.status === 201) {
@@ -86,6 +91,7 @@ export default function PatientNotesSlideover(props: PatientNotesProps) {
setNoteField("");
setState({ ...state, cPage: 1 });
setReload(true);
+ setReplyTo(undefined);
}
};
@@ -216,36 +222,42 @@ export default function PatientNotesSlideover(props: PatientNotesProps) {
setReload={setReload}
disableEdit={!patientActive}
thread={thread}
+ setReplyTo={setReplyTo}
/>
-
-
setNoteField(e.value)}
- className="w-full grow"
- errorClassName="hidden"
- innerClassName="pr-10"
- placeholder={t("notes_placeholder")}
- disabled={!patientActive}
- onFocus={() => setFocused(true)}
- onBlur={() => setFocused(false)}
- />
-
-
-
-
+ setReplyTo(undefined)}
+ >
+
+
setNoteField(e.value)}
+ className="w-full grow"
+ errorClassName="hidden"
+ innerClassName="pr-10"
+ placeholder={t("notes_placeholder")}
+ disabled={!patientActive}
+ onFocus={() => setFocused(true)}
+ onBlur={() => setFocused(false)}
+ />
+
+
+
+
+
)}
diff --git a/src/Components/Facility/SpokeFacilityEditor.tsx b/src/Components/Facility/SpokeFacilityEditor.tsx
new file mode 100644
index 00000000000..197d68da2bf
--- /dev/null
+++ b/src/Components/Facility/SpokeFacilityEditor.tsx
@@ -0,0 +1,154 @@
+import routes from "../../Redux/api";
+import request from "../../Utils/request/request";
+import useQuery from "../../Utils/request/useQuery";
+import { SelectFormField } from "../Form/FormFields/SelectFormField";
+import {
+ FacilityModel,
+ FacilitySpokeErrors,
+ FacilitySpokeModel,
+ FacilitySpokeRequest,
+ SpokeRelationship,
+} from "./models";
+import ModelCrudEditor from "../Form/ModelCrudEditor";
+import { FacilitySelect } from "../Common/FacilitySelect";
+import { useEffect, useState } from "react";
+import { SPOKE_RELATION_TYPES } from "../../Common/constants";
+import FacilityBlock from "./FacilityBlock";
+import { useTranslation } from "react-i18next";
+
+export interface SpokeFacilityEditorProps {
+ facility: Omit & { id: string };
+}
+
+export default function SpokeFacilityEditor(props: SpokeFacilityEditorProps) {
+ const { facility } = props;
+
+ const { t } = useTranslation();
+
+ const spokesQuery = useQuery(routes.getFacilitySpokes, {
+ pathParams: {
+ id: facility.id,
+ },
+ });
+
+ const spokes = spokesQuery.data?.results;
+
+ const createSpoke = (body: FacilitySpokeRequest) =>
+ request(routes.createFacilitySpoke, {
+ body,
+ pathParams: {
+ id: facility.id,
+ },
+ onResponse: ({ res }) => {
+ if (res?.ok) {
+ spokesQuery.refetch();
+ }
+ },
+ });
+
+ const deleteSpoke = (spokeFacilityId: string) =>
+ request(routes.deleteFacilitySpoke, {
+ pathParams: {
+ id: facility.id,
+ spoke_id: spokeFacilityId,
+ },
+ onResponse: ({ res }) => {
+ if (res?.ok) {
+ spokesQuery.refetch();
+ }
+ },
+ });
+
+ const updateSpoke = (spokeFacilityId: string, body: FacilitySpokeRequest) =>
+ request(routes.updateFacilitySpokes, {
+ pathParams: {
+ id: facility.id,
+ spoke_id: spokeFacilityId,
+ },
+ body,
+ onResponse: ({ res }) => {
+ if (res?.ok) {
+ spokesQuery.refetch();
+ }
+ },
+ });
+
+ const FormRender = (
+ item: FacilitySpokeModel | FacilitySpokeRequest,
+ setItem: (item: FacilitySpokeModel | FacilitySpokeRequest) => void,
+ processing: boolean,
+ ) => {
+ const [selectedFacility, setSelectedFacility] = useState();
+
+ useEffect(() => {
+ setItem({ ...item, spoke: selectedFacility?.id });
+ }, [selectedFacility]);
+
+ return (
+
+ {"id" in item ? (
+
+
+
+ ) : (
+
+ v && !Array.isArray(v) && setSelectedFacility(v)
+ }
+ errors=""
+ className="w-full"
+ disabled={processing}
+ filter={(f) =>
+ !!f.id &&
+ facility.id !== f.id &&
+ !spokes?.flatMap((s) => s.spoke_object.id).includes(f.id)
+ }
+ />
+ )}
+ v.text}
+ optionValue={(v) => v.value}
+ value={item.relationship}
+ onChange={(v) => setItem({ ...item, relationship: v.value })}
+ errorClassName="hidden"
+ className="w-full shrink-0 md:w-auto"
+ disabled={processing}
+ />
+
+ );
+ };
+
+ return (
+ <>
+
+ items={spokes}
+ onCreate={createSpoke}
+ onUpdate={updateSpoke}
+ onDelete={deleteSpoke}
+ loading={spokesQuery.loading}
+ errors={{}}
+ emptyText={"No Spokes"}
+ empty={{
+ spoke: "",
+ relationship: SpokeRelationship.REGULAR,
+ }}
+ createText="Add Spoke"
+ allowCreate={(item) => !item.relationship || !item.spoke}
+ >
+ {FormRender}
+
+ >
+ );
+}
diff --git a/src/Components/Facility/models.tsx b/src/Components/Facility/models.tsx
index cdb78a5f712..97d81674658 100644
--- a/src/Components/Facility/models.tsx
+++ b/src/Components/Facility/models.tsx
@@ -12,6 +12,7 @@ import {
AssignedToObjectModel,
BloodPressure,
DailyRoundsModel,
+ FacilityNameModel,
FileUploadModel,
} from "../Patient/models";
import { EncounterSymptom } from "../Symptoms/types";
@@ -79,8 +80,32 @@ export interface FacilityModel {
local_body?: number;
ward?: number;
pincode?: string;
+ latitude?: string;
+ longitude?: string;
+ kasp_empanelled?: boolean;
+ patient_count?: string;
+ bed_count?: string;
+}
+
+export enum SpokeRelationship {
+ REGULAR = 1,
+ TELE_ICU = 2,
}
+export interface FacilitySpokeModel {
+ id: string;
+ hub_object: FacilityNameModel;
+ spoke_object: FacilityNameModel;
+ relationship: SpokeRelationship;
+}
+
+export interface FacilitySpokeRequest {
+ spoke?: string;
+ relationship?: SpokeRelationship;
+}
+
+export interface FacilitySpokeErrors {}
+
export interface CapacityModal {
id?: number;
room_type?: number;
@@ -546,6 +571,14 @@ export interface PatientNotesEditModel {
note: string;
}
+export interface PaitentNotesReplyModel {
+ id: string;
+ note: string;
+ user_type?: UserRole | "RemoteSpecialist";
+ created_by_object: BaseUserModel;
+ created_date: string;
+}
+
export interface PatientNotesModel {
id: string;
note: string;
@@ -556,6 +589,7 @@ export interface PatientNotesModel {
created_date: string;
last_edited_by?: BaseUserModel;
last_edited_date?: string;
+ reply_to_object?: PaitentNotesReplyModel;
}
export interface PatientNoteStateType {
@@ -579,13 +613,7 @@ export type IUserFacilityRequest = {
facility: string;
};
-export type FacilityRequest = Omit & {
- latitude?: string;
- longitude?: string;
- kasp_empanelled?: boolean;
- patient_count?: string;
- bed_count?: string;
-};
+export type FacilityRequest = Omit;
export type InventorySummaryResponse = {
id: string;
diff --git a/src/Components/Form/AutoCompleteAsync.tsx b/src/Components/Form/AutoCompleteAsync.tsx
index 18bffb0e11c..f362918dfc2 100644
--- a/src/Components/Form/AutoCompleteAsync.tsx
+++ b/src/Components/Form/AutoCompleteAsync.tsx
@@ -36,6 +36,7 @@ interface Props {
required?: boolean;
onBlur?: () => void;
onFocus?: () => void;
+ filter?: (data: any) => boolean;
}
const AutoCompleteAsync = (props: Props) => {
@@ -56,6 +57,7 @@ const AutoCompleteAsync = (props: Props) => {
disabled = false,
required = false,
error,
+ filter,
} = props;
const [data, setData] = useState([]);
const [query, setQuery] = useState("");
@@ -69,7 +71,9 @@ const AutoCompleteAsync = (props: Props) => {
() =>
debounce(async (query: string) => {
setLoading(true);
- const data = (await fetchData(query)) || [];
+ const data = ((await fetchData(query)) || [])?.filter((d: any) =>
+ filter ? filter(d) : true,
+ );
if (showNOptions !== undefined) {
setData(data.slice(0, showNOptions));
diff --git a/src/Components/Form/ModelCrudEditor.tsx b/src/Components/Form/ModelCrudEditor.tsx
new file mode 100644
index 00000000000..3ce4b15eba3
--- /dev/null
+++ b/src/Components/Form/ModelCrudEditor.tsx
@@ -0,0 +1,153 @@
+import { useEffect, useState } from "react";
+import { classNames } from "../../Utils/utils";
+import ButtonV2 from "../Common/components/ButtonV2";
+import CareIcon from "../../CAREUI/icons/CareIcon";
+import { useTranslation } from "react-i18next";
+
+interface Identifier {
+ id: string;
+}
+
+export interface ModelCrudEditorProps {
+ onCreate?: (req: TReq) => Promise;
+ onUpdate?: (itemId: string, req: TReq) => Promise;
+ onDelete?: (itemId: string) => Promise;
+ items?: TRes[];
+ children: (
+ item: TRes | TReq,
+ setItem: (item: TRes | TReq) => void,
+ processing: boolean,
+ errors?: TErr,
+ ) => React.ReactNode;
+ loading: boolean;
+ errors: TErr;
+ emptyText?: React.ReactNode;
+ empty: TReq;
+ createText?: React.ReactNode;
+ allowCreate?: (item: TReq) => boolean;
+}
+
+export default function ModelCrudEditor(
+ props: ModelCrudEditorProps,
+) {
+ const { t } = useTranslation();
+
+ const {
+ onCreate,
+ onUpdate,
+ onDelete,
+ items,
+ children,
+ loading,
+ errors,
+ emptyText,
+ empty,
+ createText,
+ allowCreate,
+ } = props;
+ const [creating, setCreating] = useState(false);
+ const [updating, setUpdating] = useState(null);
+
+ const handleUpdate = async (itemId: string, item: TReq) => {
+ if (!onUpdate) return;
+ setUpdating(itemId);
+ await onUpdate(itemId, item);
+ setUpdating(null);
+ };
+
+ const handleDelete = async (itemId: string) => {
+ if (!onDelete) return;
+ setUpdating(itemId);
+ await onDelete(itemId);
+ setUpdating(null);
+ };
+
+ const handleCreate = async (item: TReq) => {
+ if (!onCreate) return;
+ setCreating(true);
+ await onCreate(item);
+ setCreating(false);
+ };
+
+ type FormProps =
+ | {
+ type: "creating";
+ item: TReq;
+ }
+ | {
+ type: "updating";
+ item: TRes;
+ };
+
+ const Form = (props: FormProps) => {
+ const [item, setItem] = useState(props.item);
+ const processing =
+ props.type === "creating" ? creating : props.item.id === updating;
+
+ useEffect(() => {
+ if (
+ props.type === "updating" &&
+ JSON.stringify(item) !== JSON.stringify(props.item)
+ ) {
+ const timeout = setTimeout(() => {
+ handleUpdate(props.item.id, item as TReq);
+ }, 1000);
+ return () => clearTimeout(timeout);
+ }
+ }, [item]);
+
+ return (
+
+ {children(item, setItem, processing, errors)}
+ {props.type === "creating" && (
+ handleCreate(item as TReq)}
+ >
+ {createText || "Create"}
+
+ )}
+ {props.type === "updating" && onDelete && (
+
+ )}
+
+ );
+ };
+
+ return (
+
+
+ {items?.map((item, i) => (
+ -
+
+
+ ))}
+
+ {items?.length === 0 && (
+
+ {emptyText}
+
+ )}
+
+
+
+
+
+ );
+}
diff --git a/src/Components/Patient/ManagePatients.tsx b/src/Components/Patient/ManagePatients.tsx
index 944a5163c96..7a5b0d28a38 100644
--- a/src/Components/Patient/ManagePatients.tsx
+++ b/src/Components/Patient/ManagePatients.tsx
@@ -721,7 +721,8 @@ export const PatientManager = () => {
{patient.last_consultation?.last_daily_round
?.ventilator_interface &&
patient.last_consultation?.last_daily_round
- ?.ventilator_interface !== "UNKNOWN" && (
+ ?.ventilator_interface !== "UNKNOWN" &&
+ !patient.last_consultation?.discharge_date && (
{
RESPIRATORY_SUPPORT.find(
diff --git a/src/Components/Patient/PatientFilter.tsx b/src/Components/Patient/PatientFilter.tsx
index 773a3f333b7..f496a59df6d 100644
--- a/src/Components/Patient/PatientFilter.tsx
+++ b/src/Components/Patient/PatientFilter.tsx
@@ -343,27 +343,25 @@ export default function PatientFilter(props: any) {
/>
- {props.dischargePage || (
-
-
- {props.dischargePage && "Last "}Admitted to (Bed Types)
-
- o.id}
- optionLabel={(o) => o.text}
- onChange={(o) =>
- setFilterState({
- ...filterState,
- last_consultation_admitted_bed_type_list: o,
- })
- }
- />
-
- )}
+
+
+ {props.dischargePage && "Last "}Admitted to (Bed Types)
+
+ o.id}
+ optionLabel={(o) => o.text}
+ onChange={(o) =>
+ setFilterState({
+ ...filterState,
+ last_consultation_admitted_bed_type_list: o,
+ })
+ }
+ />
+
Has consent records for
setOpen(true)}
className="mt-1 px-[10px] py-1"
diff --git a/src/Components/Patient/PatientNotes.tsx b/src/Components/Patient/PatientNotes.tsx
index 7138f4df8e5..da97e5d3f4f 100644
--- a/src/Components/Patient/PatientNotes.tsx
+++ b/src/Components/Patient/PatientNotes.tsx
@@ -6,11 +6,12 @@ import { NonReadOnlyUsers } from "../../Utils/AuthorizeFor";
import PatientNotesList from "../Facility/PatientNotesList";
import Page from "../Common/components/Page";
import { useMessageListener } from "../../Common/hooks/useMessageListener";
-import { PatientNoteStateType } from "../Facility/models";
+import { PatientNoteStateType, PatientNotesModel } from "../Facility/models";
import request from "../../Utils/request/request";
import routes from "../../Redux/api";
import { PATIENT_NOTES_THREADS } from "../../Common/constants.js";
import useAuthUser from "../../Common/hooks/useAuthUser.js";
+import DoctorNoteReplyPreviewCard from "../Facility/DoctorNoteReplyPreviewCard.js";
import { classNames, keysOf } from "../../Utils/utils.js";
import AutoExpandingTextInputFormField from "../Form/FormFields/AutoExpandingTextInputFormField.js";
import { t } from "i18next";
@@ -35,6 +36,9 @@ const PatientNotes = (props: PatientNotesProps) => {
const [reload, setReload] = useState(false);
const [facilityName, setFacilityName] = useState("");
const [patientName, setPatientName] = useState("");
+ const [reply_to, setReplyTo] = useState(
+ undefined,
+ );
const initialData: PatientNoteStateType = {
notes: [],
@@ -56,6 +60,7 @@ const PatientNotes = (props: PatientNotesProps) => {
body: {
note: noteField,
thread,
+ reply_to: reply_to?.id,
},
});
if (res?.status === 201) {
@@ -63,6 +68,7 @@ const PatientNotes = (props: PatientNotesProps) => {
setNoteField("");
setReload(!reload);
setState({ ...state, cPage: 1 });
+ setReplyTo(undefined);
}
};
@@ -130,33 +136,38 @@ const PatientNotes = (props: PatientNotesProps) => {
reload={reload}
setReload={setReload}
thread={thread}
+ setReplyTo={setReplyTo}
/>
-
-
-
setNoteField(e.value)}
- className="w-full grow"
- errorClassName="hidden"
- innerClassName="pr-10"
- placeholder={t("notes_placeholder")}
- disabled={!patientActive}
- />
-
-
-
-
+ setReplyTo(undefined)}
+ >
+
+
setNoteField(e.value)}
+ className="w-full grow"
+ errorClassName="hidden"
+ innerClassName="pr-10"
+ placeholder={t("notes_placeholder")}
+ disabled={!patientActive}
+ />
+
+
+
+
+
);
diff --git a/src/Locale/en/Common.json b/src/Locale/en/Common.json
index fee9e43afe5..7f0b9f51802 100644
--- a/src/Locale/en/Common.json
+++ b/src/Locale/en/Common.json
@@ -175,6 +175,9 @@
"summary": "Summary",
"report": "Report",
"treating_doctor": "Treating Doctor",
+ "hubs": "Hub Facilities",
+ "spokes": "Spoke Facilities",
+ "add_spoke" : "Add Spoke Facility",
"ration_card__NO_CARD": "Non-card holder",
"ration_card__BPL": "BPL",
"ration_card__APL": "APL",
@@ -211,5 +214,21 @@
"delete_item": "Delete {{name}}",
"unsupported_browser": "Unsupported Browser",
"unsupported_browser_description": "Your browser ({{name}} version {{version}}) is not supported. Please update your browser to the latest version or switch to a supported browser for the best experience.",
- "add_remarks": "Add remarks"
-}
+ "add_remarks": "Add remarks",
+ "SORT_OPTIONS__-created_date": "Latest created date first",
+ "SORT_OPTIONS__created_date": "Oldest created date first",
+ "SORT_OPTIONS__-category_severity": "Highest Severity category first",
+ "SORT_OPTIONS__category_severity": "Lowest Severity category first",
+ "SORT_OPTIONS__-modified_date": "Latest updated date first",
+ "SORT_OPTIONS__modified_date": "Oldest updated date first",
+ "SORT_OPTIONS__facility__name,last_consultation__current_bed__bed__name": "Bed No. 1-N",
+ "SORT_OPTIONS__facility__name,-last_consultation__current_bed__bed__name": "Bed No. N-1",
+ "SORT_OPTIONS__-review_time": "Latest review date first",
+ "SORT_OPTIONS__review_time": "Oldest review date first",
+ "SORT_OPTIONS__taken_at": "Oldest taken date first",
+ "SORT_OPTIONS__-taken_at": "Latest taken date first",
+ "SORT_OPTIONS__name": "Patient name A-Z",
+ "SORT_OPTIONS__-name": "Patient name Z-A",
+ "SORT_OPTIONS__bed__name": "Bed No. 1-N",
+ "SORT_OPTIONS__-bed__name": "Bed No. N-1"
+}
\ No newline at end of file
diff --git a/src/Locale/en/SortOptions.json b/src/Locale/en/SortOptions.json
deleted file mode 100644
index 29a8d1e8f4d..00000000000
--- a/src/Locale/en/SortOptions.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
- "-created_date": "Latest created date first",
- "created_date": "Oldest created date first",
- "-category_severity": "Highest Severity category first",
- "category_severity": "Lowest Severity category first",
- "-modified_date": "Latest updated date first",
- "modified_date": "Oldest updated date first",
- "facility__name,last_consultation__current_bed__bed__name": "Bed No. 1-N",
- "facility__name,-last_consultation__current_bed__bed__name": "Bed No. N-1",
- "-review_time": "Latest review date first",
- "review_time": "Oldest review date first",
- "taken_at": "Oldest taken date first",
- "-taken_at": "Latest taken date first",
- "name": "Patient name A-Z",
- "-name": "Patient name Z-A",
- "bed__name": "Bed No. 1-N",
- "-bed__name": "Bed No. N-1"
-}
diff --git a/src/Locale/en/index.js b/src/Locale/en/index.js
index 6452253c179..808520605ed 100644
--- a/src/Locale/en/index.js
+++ b/src/Locale/en/index.js
@@ -18,7 +18,6 @@ import Notifications from "./Notifications.json";
import Patient from "./Patient.json";
import Resource from "./Resource.json";
import Shifting from "./Shifting.json";
-import SortOptions from "./SortOptions.json";
import Users from "./Users.json";
export default {
@@ -43,5 +42,4 @@ export default {
...LogUpdate,
...FileUpload,
...HCX,
- ...SortOptions,
};
diff --git a/src/Locale/hi/Common.json b/src/Locale/hi/Common.json
index e881bb29d75..4cd3bbe3e36 100644
--- a/src/Locale/hi/Common.json
+++ b/src/Locale/hi/Common.json
@@ -203,5 +203,21 @@
"deleted_successfully": "{{name}} सफलतापूर्वक हटा दिया गया",
"delete_item": "{{name}}मिटाएँ",
"unsupported_browser": "असमर्थित ब्राउज़र",
- "unsupported_browser_description": "आपका ब्राउज़र ({{name}} संस्करण {{version}}) समर्थित नहीं है। कृपया अपने ब्राउज़र को नवीनतम संस्करण में अपडेट करें या सर्वोत्तम अनुभव के लिए समर्थित ब्राउज़र पर स्विच करें।"
+ "unsupported_browser_description": "आपका ब्राउज़र ({{name}} संस्करण {{version}}) समर्थित नहीं है। कृपया अपने ब्राउज़र को नवीनतम संस्करण में अपडेट करें या सर्वोत्तम अनुभव के लिए समर्थित ब्राउज़र पर स्विच करें।",
+ "SORT_OPTIONS__-created_date": "नवीनतम निर्माण तिथि पहले",
+ "SORT_OPTIONS__created_date": "सबसे पुरानी निर्माण तिथि पहले",
+ "SORT_OPTIONS__-category_severity": "सर्वोच्च गंभीरता श्रेणी पहले",
+ "SORT_OPTIONS__category_severity": "सबसे कम गंभीरता वाली श्रेणी पहले",
+ "SORT_OPTIONS__-modified_date": "नवीनतम अद्यतन तिथि पहले",
+ "SORT_OPTIONS__modified_date": "सबसे पुरानी अद्यतन तिथि पहले",
+ "SORT_OPTIONS__facility__name,last_consultation__current_bed__bed__name": "बिस्तर नं. 1-एन",
+ "SORT_OPTIONS__facility__name,-last_consultation__current_bed__bed__name": "बिस्तर संख्या एन-1",
+ "SORT_OPTIONS__-review_time": "नवीनतम समीक्षा तिथि पहले",
+ "SORT_OPTIONS__review_time": "सबसे पुरानी समीक्षा तिथि पहले",
+ "SORT_OPTIONS__taken_at": "सबसे पुरानी ली गई तारीख पहले",
+ "SORT_OPTIONS__-taken_at": "नवीनतम ली गई तिथि पहले",
+ "SORT_OPTIONS__name": "मरीज़ का नाम AZ",
+ "SORT_OPTIONS__-name": "मरीज का नाम ZA",
+ "SORT_OPTIONS__bed__name": "बिस्तर नं. 1-एन",
+ "SORT_OPTIONS__-bed__name": "बिस्तर संख्या एन-1"
}
\ No newline at end of file
diff --git a/src/Locale/hi/SortOptions.json b/src/Locale/hi/SortOptions.json
deleted file mode 100644
index 46b319fac69..00000000000
--- a/src/Locale/hi/SortOptions.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
- "-created_date": "नवीनतम निर्माण तिथि पहले",
- "created_date": "सबसे पुरानी निर्माण तिथि पहले",
- "-category_severity": "सर्वोच्च गंभीरता श्रेणी पहले",
- "category_severity": "सबसे कम गंभीरता वाली श्रेणी पहले",
- "-modified_date": "नवीनतम अद्यतन तिथि पहले",
- "modified_date": "सबसे पुरानी अद्यतन तिथि पहले",
- "facility__name,last_consultation__current_bed__bed__name": "बिस्तर नं. 1-एन",
- "facility__name,-last_consultation__current_bed__bed__name": "बिस्तर संख्या एन-1",
- "-review_time": "नवीनतम समीक्षा तिथि पहले",
- "review_time": "सबसे पुरानी समीक्षा तिथि पहले",
- "taken_at": "सबसे पुरानी ली गई तारीख पहले",
- "-taken_at": "नवीनतम ली गई तिथि पहले",
- "name": "मरीज़ का नाम AZ",
- "-name": "मरीज का नाम ZA",
- "bed__name": "बिस्तर नं. 1-एन",
- "-bed__name": "बिस्तर संख्या एन-1"
-}
diff --git a/src/Locale/kn/Common.json b/src/Locale/kn/Common.json
index 6e136b1e906..6eeaa71ea48 100644
--- a/src/Locale/kn/Common.json
+++ b/src/Locale/kn/Common.json
@@ -203,5 +203,21 @@
"deleted_successfully": "{{name}} ಅನ್ನು ಯಶಸ್ವಿಯಾಗಿ ಅಳಿಸಲಾಗಿದೆ",
"delete_item": "{{name}}ಅಳಿಸಿ",
"unsupported_browser": "ಬೆಂಬಲಿತವಲ್ಲದ ಬ್ರೌಸರ್",
- "unsupported_browser_description": "ನಿಮ್ಮ ಬ್ರೌಸರ್ ({{name}} ಆವೃತ್ತಿ {{version}}) ಬೆಂಬಲಿತವಾಗಿಲ್ಲ. ದಯವಿಟ್ಟು ನಿಮ್ಮ ಬ್ರೌಸರ್ ಅನ್ನು ಇತ್ತೀಚಿನ ಆವೃತ್ತಿಗೆ ನವೀಕರಿಸಿ ಅಥವಾ ಉತ್ತಮ ಅನುಭವಕ್ಕಾಗಿ ಬೆಂಬಲಿತ ಬ್ರೌಸರ್ಗೆ ಬದಲಿಸಿ."
+ "SORT_OPTIONS__unsupported_browser_description": "ನಿಮ್ಮ ಬ್ರೌಸರ್ ({{name}} ಆವೃತ್ತಿ {{version}}) ಬೆಂಬಲಿತವಾಗಿಲ್ಲ. ದಯವಿಟ್ಟು ನಿಮ್ಮ ಬ್ರೌಸರ್ ಅನ್ನು ಇತ್ತೀಚಿನ ಆವೃತ್ತಿಗೆ ನವೀಕರಿಸಿ ಅಥವಾ ಉತ್ತಮ ಅನುಭವಕ್ಕಾಗಿ ಬೆಂಬಲಿತ ಬ್ರೌಸರ್ಗೆ ಬದಲಿಸಿ.",
+ "SORT_OPTIONS__-created_date": "ಇತ್ತೀಚಿಗೆ ರಚಿಸಿದ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__created_date": "ಮೊದಲು ರಚಿಸಿದ ಹಳೆಯ ದಿನಾಂಕ",
+ "SORT_OPTIONS__-category_severity": "ಅತ್ಯಧಿಕ ತೀವ್ರತೆಯ ವಿಭಾಗ ಮೊದಲು",
+ "SORT_OPTIONS__category_severity": "ಕಡಿಮೆ ತೀವ್ರತೆಯ ವರ್ಗ ಮೊದಲು",
+ "SORT_OPTIONS__-modified_date": "ಮೊದಲು ಇತ್ತೀಚಿನ ನವೀಕರಿಸಿದ ದಿನಾಂಕ",
+ "SORT_OPTIONS__modified_date": "ಹಳೆಯ ನವೀಕರಿಸಿದ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__facility__name,last_consultation__current_bed__bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ 1-N",
+ "SORT_OPTIONS__facility__name,-last_consultation__current_bed__bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ N-1",
+ "SORT_OPTIONS__-review_time": "ಇತ್ತೀಚಿನ ವಿಮರ್ಶೆ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__review_time": "ಹಳೆಯ ವಿಮರ್ಶೆ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__taken_at": "ಹಳೆಯ ತೆಗೆದ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__-taken_at": "ಇತ್ತೀಚೆಗೆ ತೆಗೆದುಕೊಂಡ ದಿನಾಂಕ ಮೊದಲು",
+ "SORT_OPTIONS__name": "ರೋಗಿಯ ಹೆಸರು AZ",
+ "SORT_OPTIONS__-name": "ರೋಗಿಯ ಹೆಸರು ZA",
+ "SORT_OPTIONS__bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ 1-N",
+ "SORT_OPTIONS__-bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ N-1"
}
\ No newline at end of file
diff --git a/src/Locale/kn/SortOptions.json b/src/Locale/kn/SortOptions.json
deleted file mode 100644
index 1fb870664f2..00000000000
--- a/src/Locale/kn/SortOptions.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
- "-created_date": "ಇತ್ತೀಚಿಗೆ ರಚಿಸಿದ ದಿನಾಂಕ ಮೊದಲು",
- "created_date": "ಮೊದಲು ರಚಿಸಿದ ಹಳೆಯ ದಿನಾಂಕ",
- "-category_severity": "ಅತ್ಯಧಿಕ ತೀವ್ರತೆಯ ವಿಭಾಗ ಮೊದಲು",
- "category_severity": "ಕಡಿಮೆ ತೀವ್ರತೆಯ ವರ್ಗ ಮೊದಲು",
- "-modified_date": "ಮೊದಲು ಇತ್ತೀಚಿನ ನವೀಕರಿಸಿದ ದಿನಾಂಕ",
- "modified_date": "ಹಳೆಯ ನವೀಕರಿಸಿದ ದಿನಾಂಕ ಮೊದಲು",
- "facility__name,last_consultation__current_bed__bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ 1-N",
- "facility__name,-last_consultation__current_bed__bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ N-1",
- "-review_time": "ಇತ್ತೀಚಿನ ವಿಮರ್ಶೆ ದಿನಾಂಕ ಮೊದಲು",
- "review_time": "ಹಳೆಯ ವಿಮರ್ಶೆ ದಿನಾಂಕ ಮೊದಲು",
- "taken_at": "ಹಳೆಯ ತೆಗೆದ ದಿನಾಂಕ ಮೊದಲು",
- "-taken_at": "ಇತ್ತೀಚೆಗೆ ತೆಗೆದುಕೊಂಡ ದಿನಾಂಕ ಮೊದಲು",
- "name": "ರೋಗಿಯ ಹೆಸರು AZ",
- "-name": "ರೋಗಿಯ ಹೆಸರು ZA",
- "bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ 1-N",
- "-bed__name": "ಹಾಸಿಗೆ ಸಂಖ್ಯೆ N-1"
-}
diff --git a/src/Locale/kn/index.js b/src/Locale/kn/index.js
index cbf1d10c3b9..5c2b9219ced 100644
--- a/src/Locale/kn/index.js
+++ b/src/Locale/kn/index.js
@@ -1,11 +1,37 @@
+import Asset from "./Asset.json";
import Auth from "./Auth.json";
+import Bed from "./Bed.json";
import Common from "./Common.json";
+import Consultation from "./Consultation.json";
+import CoverImageEdit from "./CoverImageEdit.json";
+import Diagnosis from "./Diagnosis.json";
import Entities from "./Entities.json";
+import ErrorPages from "./ErrorPages.json";
+import ExternalResult from "./ExternalResult.json";
import Facility from "./Facility.json";
+import FileUpload from "./FileUpload.json";
+import Hub from "./Hub.json";
+import Medicine from "./Medicine.json";
+import Notifications from "./Notifications.json";
+import Shifting from "./Shifting.json";
+import Users from "./Users.json";
export default {
...Auth,
+ ...Asset,
...Common,
+ ...Consultation,
+ ...CoverImageEdit,
...Entities,
+ ...ErrorPages,
+ ...ExternalResult,
...Facility,
+ ...Hub,
+ ...Medicine,
+ ...Diagnosis,
+ ...Notifications,
+ ...Shifting,
+ ...Bed,
+ ...Users,
+ ...FileUpload,
};
diff --git a/src/Locale/ml/Common.json b/src/Locale/ml/Common.json
index 7e77900e2cb..ab1e0db6feb 100644
--- a/src/Locale/ml/Common.json
+++ b/src/Locale/ml/Common.json
@@ -203,5 +203,21 @@
"deleted_successfully": "{{name}} വിജയകരമായി ഇല്ലാതാക്കി",
"delete_item": "{{name}}ഇല്ലാതാക്കുക",
"unsupported_browser": "പിന്തുണയ്ക്കാത്ത ബ്രൗസർ",
- "unsupported_browser_description": "നിങ്ങളുടെ ബ്രൗസർ ({{name}} പതിപ്പ് {{version}}) പിന്തുണയ്ക്കുന്നില്ല. ഏറ്റവും പുതിയ പതിപ്പിലേക്ക് നിങ്ങളുടെ ബ്രൗസർ അപ്ഡേറ്റ് ചെയ്യുക അല്ലെങ്കിൽ മികച്ച അനുഭവത്തിനായി പിന്തുണയ്ക്കുന്ന ബ്രൗസറിലേക്ക് മാറുക."
+ "unsupported_browser_description": "നിങ്ങളുടെ ബ്രൗസർ ({{name}} പതിപ്പ് {{version}}) പിന്തുണയ്ക്കുന്നില്ല. ഏറ്റവും പുതിയ പതിപ്പിലേക്ക് നിങ്ങളുടെ ബ്രൗസർ അപ്ഡേറ്റ് ചെയ്യുക അല്ലെങ്കിൽ മികച്ച അനുഭവത്തിനായി പിന്തുണയ്ക്കുന്ന ബ്രൗസറിലേക്ക് മാറുക.",
+ "SORT_OPTIONS__-created_date": "ആദ്യം സൃഷ്ടിച്ച ഏറ്റവും പുതിയ തീയതി",
+ "SORT_OPTIONS__created_date": "ഏറ്റവും പഴയ സൃഷ്ടിച്ച തീയതി ആദ്യം",
+ "SORT_OPTIONS__-category_severity": "ഏറ്റവും ഉയർന്ന തീവ്രത വിഭാഗം ആദ്യം",
+ "SORT_OPTIONS__category_severity": "ഏറ്റവും കുറഞ്ഞ തീവ്രത വിഭാഗം ആദ്യം",
+ "SORT_OPTIONS__-modified_date": "ഏറ്റവും പുതിയ അപ്ഡേറ്റ് തീയതി ആദ്യം",
+ "SORT_OPTIONS__modified_date": "ഏറ്റവും പഴയ പുതുക്കിയ തീയതി ആദ്യം",
+ "SORT_OPTIONS__facility__name,last_consultation__current_bed__bed__name": "ബെഡ് നമ്പർ 1-N",
+ "SORT_OPTIONS__facility__name,-last_consultation__current_bed__bed__name": "കിടക്ക നമ്പർ N-1",
+ "SORT_OPTIONS__-review_time": "ഏറ്റവും പുതിയ അവലോകന തീയതി ആദ്യം",
+ "SORT_OPTIONS__review_time": "ഏറ്റവും പഴയ അവലോകന തീയതി ആദ്യം",
+ "SORT_OPTIONS__taken_at": "ആദ്യം എടുത്ത ഏറ്റവും പഴയ തീയതി",
+ "SORT_OPTIONS__-taken_at": "ഏറ്റവും പുതിയ തീയതി ആദ്യം",
+ "SORT_OPTIONS__name": "രോഗിയുടെ പേര് AZ",
+ "SORT_OPTIONS__-name": "രോഗിയുടെ പേര് ZA",
+ "SORT_OPTIONS__bed__name": "ബെഡ് നമ്പർ 1-N",
+ "SORT_OPTIONS__-bed__name": "കിടക്ക നമ്പർ N-1"
}
\ No newline at end of file
diff --git a/src/Locale/ml/SortOptions.json b/src/Locale/ml/SortOptions.json
deleted file mode 100644
index 97eb76e6160..00000000000
--- a/src/Locale/ml/SortOptions.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
- "-created_date": "ആദ്യം സൃഷ്ടിച്ച ഏറ്റവും പുതിയ തീയതി",
- "created_date": "ഏറ്റവും പഴയ സൃഷ്ടിച്ച തീയതി ആദ്യം",
- "-category_severity": "ഏറ്റവും ഉയർന്ന തീവ്രത വിഭാഗം ആദ്യം",
- "category_severity": "ഏറ്റവും കുറഞ്ഞ തീവ്രത വിഭാഗം ആദ്യം",
- "-modified_date": "ഏറ്റവും പുതിയ അപ്ഡേറ്റ് തീയതി ആദ്യം",
- "modified_date": "ഏറ്റവും പഴയ പുതുക്കിയ തീയതി ആദ്യം",
- "facility__name,last_consultation__current_bed__bed__name": "ബെഡ് നമ്പർ 1-N",
- "facility__name,-last_consultation__current_bed__bed__name": "കിടക്ക നമ്പർ N-1",
- "-review_time": "ഏറ്റവും പുതിയ അവലോകന തീയതി ആദ്യം",
- "review_time": "ഏറ്റവും പഴയ അവലോകന തീയതി ആദ്യം",
- "taken_at": "ആദ്യം എടുത്ത ഏറ്റവും പഴയ തീയതി",
- "-taken_at": "ഏറ്റവും പുതിയ തീയതി ആദ്യം",
- "name": "രോഗിയുടെ പേര് AZ",
- "-name": "രോഗിയുടെ പേര് ZA",
- "bed__name": "ബെഡ് നമ്പർ 1-N",
- "-bed__name": "കിടക്ക നമ്പർ N-1"
-}
diff --git a/src/Locale/ta/Common.json b/src/Locale/ta/Common.json
index abf6427ce9c..2a9bc4458b5 100644
--- a/src/Locale/ta/Common.json
+++ b/src/Locale/ta/Common.json
@@ -203,5 +203,21 @@
"deleted_successfully": "{{name}} வெற்றிகரமாக நீக்கப்பட்டது",
"delete_item": "{{name}}ஐ நீக்கவும்",
"unsupported_browser": "ஆதரிக்கப்படாத உலாவி",
- "unsupported_browser_description": "உங்கள் உலாவி ({{name}} பதிப்பு {{version}}) ஆதரிக்கப்படவில்லை. உங்கள் உலாவியை சமீபத்திய பதிப்பிற்கு புதுப்பிக்கவும் அல்லது சிறந்த அனுபவத்திற்காக ஆதரிக்கப்படும் உலாவிக்கு மாறவும்."
+ "unsupported_browser_description": "உங்கள் உலாவி ({{name}} பதிப்பு {{version}}) ஆதரிக்கப்படவில்லை. உங்கள் உலாவியை சமீபத்திய பதிப்பிற்கு புதுப்பிக்கவும் அல்லது சிறந்த அனுபவத்திற்காக ஆதரிக்கப்படும் உலாவிக்கு மாறவும்.",
+ "SORT_OPTIONS__-created_date": "புதிதாக உருவாக்கப்பட்ட தேதி முதலில்",
+ "SORT_OPTIONS__created_date": "பழைய உருவாக்கப்பட்ட தேதி முதலில்",
+ "SORT_OPTIONS__-category_severity": "அதிக தீவிரத்தன்மை பிரிவு முதலில்",
+ "SORT_OPTIONS__category_severity": "குறைந்த தீவிரத்தன்மை வகை முதலில்",
+ "SORT_OPTIONS__-modified_date": "முதலில் புதுப்பிக்கப்பட்ட தேதி",
+ "SORT_OPTIONS__modified_date": "பழைய புதுப்பிக்கப்பட்ட தேதி முதலில்",
+ "SORT_OPTIONS__facility__name,last_consultation__current_bed__bed__name": "படுக்கை எண் 1-N",
+ "SORT_OPTIONS__facility__name,-last_consultation__current_bed__bed__name": "படுக்கை எண். N-1",
+ "SORT_OPTIONS__-review_time": "சமீபத்திய மதிப்பாய்வு தேதி முதலில்",
+ "SORT_OPTIONS__review_time": "பழைய மதிப்பாய்வு தேதி முதலில்",
+ "SORT_OPTIONS__taken_at": "முதலில் எடுக்கப்பட்ட பழைய தேதி",
+ "SORT_OPTIONS__-taken_at": "சமீபத்தில் எடுக்கப்பட்ட தேதி முதலில்",
+ "SORT_OPTIONS__name": "நோயாளியின் பெயர் AZ",
+ "SORT_OPTIONS__-name": "நோயாளியின் பெயர் ZA",
+ "SORT_OPTIONS__bed__name": "படுக்கை எண் 1-N",
+ "SORT_OPTIONS__-bed__name": "படுக்கை எண். N-1"
}
\ No newline at end of file
diff --git a/src/Locale/ta/SortOptions.json b/src/Locale/ta/SortOptions.json
deleted file mode 100644
index a2f85b6df49..00000000000
--- a/src/Locale/ta/SortOptions.json
+++ /dev/null
@@ -1,18 +0,0 @@
-{
- "-created_date": "புதிதாக உருவாக்கப்பட்ட தேதி முதலில்",
- "created_date": "பழைய உருவாக்கப்பட்ட தேதி முதலில்",
- "-category_severity": "அதிக தீவிரத்தன்மை பிரிவு முதலில்",
- "category_severity": "குறைந்த தீவிரத்தன்மை வகை முதலில்",
- "-modified_date": "முதலில் புதுப்பிக்கப்பட்ட தேதி",
- "modified_date": "பழைய புதுப்பிக்கப்பட்ட தேதி முதலில்",
- "facility__name,last_consultation__current_bed__bed__name": "படுக்கை எண் 1-N",
- "facility__name,-last_consultation__current_bed__bed__name": "படுக்கை எண். N-1",
- "-review_time": "சமீபத்திய மதிப்பாய்வு தேதி முதலில்",
- "review_time": "பழைய மதிப்பாய்வு தேதி முதலில்",
- "taken_at": "முதலில் எடுக்கப்பட்ட பழைய தேதி",
- "-taken_at": "சமீபத்தில் எடுக்கப்பட்ட தேதி முதலில்",
- "name": "நோயாளியின் பெயர் AZ",
- "-name": "நோயாளியின் பெயர் ZA",
- "bed__name": "படுக்கை எண் 1-N",
- "-bed__name": "படுக்கை எண். N-1"
-}
diff --git a/src/Redux/api.tsx b/src/Redux/api.tsx
index e53342e3d7c..0bedb12dca5 100644
--- a/src/Redux/api.tsx
+++ b/src/Redux/api.tsx
@@ -26,6 +26,8 @@ import {
DoctorModal,
FacilityModel,
FacilityRequest,
+ FacilitySpokeModel,
+ FacilitySpokeRequest,
IFacilityNotificationRequest,
IFacilityNotificationResponse,
IUserFacilityRequest,
@@ -366,7 +368,7 @@ const routes = {
getPermittedFacility: {
path: "/api/v1/facility/{id}/",
method: "GET",
- TRes: Type(),
+ TRes: Type(),
},
getAnyFacility: {
@@ -389,6 +391,38 @@ const routes = {
TBody: Type>(),
},
+ getFacilitySpokes: {
+ path: "/api/v1/facility/{id}/spokes/",
+ method: "GET",
+ TRes: Type>(),
+ },
+
+ updateFacilitySpokes: {
+ path: "/api/v1/facility/{id}/spokes/{spoke_id}/",
+ method: "PATCH",
+ TRes: Type(),
+ TBody: Type(),
+ },
+
+ getFacilitySpoke: {
+ path: "/api/v1/facility/{id}/spokes/{spoke_id}/",
+ method: "GET",
+ TRes: Type(),
+ },
+
+ createFacilitySpoke: {
+ path: "/api/v1/facility/{id}/spokes/",
+ method: "POST",
+ TRes: Type(),
+ TBody: Type>(),
+ },
+
+ deleteFacilitySpoke: {
+ path: "/api/v1/facility/{id}/spokes/{spoke_id}/",
+ method: "DELETE",
+ TRes: Type>(),
+ },
+
deleteFacilityCoverImage: {
path: "/api/v1/facility/{id}/cover_image/",
method: "DELETE",
@@ -774,7 +808,10 @@ const routes = {
method: "POST",
TRes: Type(),
TBody: Type<
- Pick & { consultation?: string }
+ Pick & {
+ consultation?: string;
+ reply_to?: string;
+ }
>(),
},
updatePatientNote: {