Skip to content

Commit

Permalink
Merge pull request #6417 from coronasafe/develop
Browse files Browse the repository at this point in the history
Production Release; Oct Week 2
  • Loading branch information
mathew-alex authored Oct 8, 2023
2 parents 7eb0a87 + 83597f1 commit ce4154a
Show file tree
Hide file tree
Showing 57 changed files with 1,307 additions and 716 deletions.
4 changes: 2 additions & 2 deletions cypress/pageobject/Patient/PatientConsultation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -49,15 +49,15 @@ export class PatientConsultationPage {
.click()
.type("1A");
cy.get("#icd11_diagnoses_object [role='option']")
.contains("1A03 Intestinal infections due to Escherichia coli")
.contains("1A00 Cholera")
.scrollIntoView()
.click();
cy.get("label[for='icd11_diagnoses_object']").click();
cy.wait("@getIcdResults").its("response.statusCode").should("eq", 200);

cy.get("#icd11_principal_diagnosis [role='combobox']").click().type("1A");
cy.get("#icd11_principal_diagnosis [role='option']")
.contains("1A03 Intestinal infections due to Escherichia coli")
.contains("1A00 Cholera")
.click();

cy.get("#consultation_notes").click().type(consulationNotes);
Expand Down
2 changes: 1 addition & 1 deletion cypress/support/commands.ts
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ Cypress.Commands.add(

Cypress.Commands.add("verifyNotification", (text) => {
cy.get(".pnotify-container").should("exist").contains(text);
return cy.get(".pnotify-container").click({ force: true });
return cy.get(".pnotify-container").contains(text).click({ force: true });
});

Cypress.on("uncaught:exception", () => {
Expand Down
16 changes: 0 additions & 16 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

18 changes: 13 additions & 5 deletions src/CAREUI/display/RecordMeta.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,28 +11,30 @@ interface Props {
last_name: string;
last_login: string | undefined;
};
inlineUser?: boolean;
}

/**
* A generic component to display relative time along with a tooltip and a user
* if provided.
*/
const RecordMeta = ({ time, user, prefix, className }: Props) => {
const RecordMeta = ({ time, user, prefix, className, inlineUser }: Props) => {
const isOnline = user && isUserOnline(user);

let child = (
<div className="tooltip">
<span className="underline">{relativeTime(time)}</span>
<span className="tooltip-text tooltip-bottom flex -translate-x-1/2 gap-1 text-xs font-medium tracking-wider">
{formatDateTime(time)}
{user && (
<>
{user && !inlineUser && (
<span className="flex items-center gap-1">
by
<CareIcon className="care-l-user" />
{user.first_name} {user.last_name}
{isOnline && (
<div className="h-1 w-1 rounded-full bg-primary-500" />
<div className="h-1.5 w-1.5 rounded-full bg-primary-400" />
)}
</>
</span>
)}
</span>
</div>
Expand All @@ -43,7 +45,13 @@ const RecordMeta = ({ time, user, prefix, className }: Props) => {
<div className="flex items-center gap-1">
{prefix}
{child}
{user && inlineUser && <span>by</span>}
{user && <CareIcon className="care-l-user" />}
{user && inlineUser && (
<span className="font-medium">
{user.first_name} {user.last_name}
</span>
)}
</div>
);
}
Expand Down
45 changes: 45 additions & 0 deletions src/Common/hooks/useSlug.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import { usePath } from "raviger";

/**
* Returns the slug from the current path.
* @param prefix The prefix of the slug.
* @returns The slug.
* @example
* // Current path: /consultation/94b9a
* const consultation = useSlug("consultation"); // consultation = "94b9a"
*/
export default function useSlug(prefix: string) {
const path = usePath() ?? "";
return findSlug(path.split("/"), prefix);
}

/**
* Returns the slugs from the current path.
* @param prefix The prefixes of the slug.
* @returns The slugs
* @example
* // Current path: /facility/5b0a/consultation/94b9a
* const [facility, consultation] = useSlug("facility", "consultation");
* // facility = "5b0a"
* // consultation = "94b9a"
*/
export const useSlugs = (...prefix: string[]) => {
const path = usePath() ?? "";
return prefix.map((p) => findSlug(path.split("/"), p));
};

const findSlug = (segments: string[], prefix: string) => {
const index = segments.findIndex((segment) => segment === prefix);
if (index === -1) {
throw new Error(
`Prefix "${prefix}" not found in path "${segments.join("/")}"`
);
}

const slug = segments[index + 1];
if (!slug) {
throw new Error(`Slug not found in path "${segments.join("/")}"`);
}

return slug;
};
68 changes: 43 additions & 25 deletions src/Components/Assets/AssetImportModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import { Cancel, Submit } from "../Common/components/ButtonV2";
import { listFacilityAssetLocation } from "../../Redux/actions";
import { useDispatch } from "react-redux";
import { Link } from "raviger";
import SelectMenuV2 from "../Form/SelectMenuV2";
import readXlsxFile from "read-excel-file";
import {
LocalStorageKeys,
Expand All @@ -17,6 +16,7 @@ import {
import { parseCsvFile } from "../../Utils/utils";
import useConfig from "../../Common/hooks/useConfig";
import DialogModal from "../Common/Dialog";
import { SelectFormField } from "../Form/FormFields/SelectFormField";

interface Props {
open: boolean;
Expand All @@ -25,14 +25,18 @@ interface Props {
}

const AssetImportModal = ({ open, onClose, facility }: Props) => {
const [isImporting, setIsUploading] = useState(false);
const [isImporting, setIsImporting] = useState(false);
const [selectedFile, setSelectedFile] = useState<any>();
const [preview, setPreview] =
useState<(AssetData & { notes?: string; last_serviced_on?: string })[]>();
const [location, setLocation] = useState("");
const [errors, setErrors] = useState<any>({
location: "",
});
const [locations, setLocations] = useState<any>([]);
const dispatchAction: any = useDispatch();
const { sample_format_asset_import } = useConfig();
const [locationsLoading, setLocationsLoading] = useState(false);

const closeModal = () => {
setPreview(undefined);
Expand All @@ -41,9 +45,11 @@ const AssetImportModal = ({ open, onClose, facility }: Props) => {
};

useEffect(() => {
setLocationsLoading(true);
dispatchAction(
listFacilityAssetLocation({}, { facility_external_id: facility.id })
).then(({ data }: any) => {
setLocationsLoading(false);
if (data.count > 0) {
setLocations(data.results);
}
Expand Down Expand Up @@ -110,7 +116,16 @@ const AssetImportModal = ({ open, onClose, facility }: Props) => {
closeModal();
return;
}
if (!location) {
setErrors({
...errors,
location: "Please select a location",
});
return;
}
setIsImporting(true);
let error = false;
Notification.Success({ msg: "Importing assets..." });

for (const asset of preview || []) {
const asset_data: any = {
Expand Down Expand Up @@ -156,16 +171,22 @@ const AssetImportModal = ({ open, onClose, facility }: Props) => {
});
error = true;
} else {
if (preview) setPreview(preview.filter((a) => a.id !== asset.id));
setPreview((preview) => {
return preview?.slice(1);
});
}
}
if (!error) {
Notification.Success({ msg: "Assets imported successfully" });
await sleep(1000);
setIsUploading(false);
closeModal();
setIsImporting(false);
window.location.reload();
} else Notification.Error({ msg: "Error importing some assets" });
} else {
Notification.Error({ msg: "Error importing some assets" });
await sleep(1000);
setIsImporting(false);
closeModal();
}
};

const dragProps = useDragAndDrop();
Expand Down Expand Up @@ -193,7 +214,7 @@ const AssetImportModal = ({ open, onClose, facility }: Props) => {
fixedWidth={false}
>
<span className="mt-1 text-gray-700">{facility.name}</span>
{locations.length === 0 ? (
{!locationsLoading && locations.length === 0 ? (
<>
<div className="flex h-full flex-col items-center justify-center">
<h1 className="m-7 text-2xl font-medium text-gray-700">
Expand All @@ -218,31 +239,28 @@ const AssetImportModal = ({ open, onClose, facility }: Props) => {
{preview && preview?.length > 0 ? (
<div className="flex flex-col items-center justify-center rounded-lg">
<h1 className="m-7 text-2xl font-medium text-gray-700">
{preview.length} assets will be imported
{preview.length} assets {isImporting ? "are being" : "will be"}{" "}
imported
</h1>
<div className="w-1/2 p-4">
<label htmlFor="asset-location">
Select location for import *
<label htmlFor="asset-location" className="flex gap-1">
Select location for import{" "}
<p className="font-semibold text-danger-500">*</p>
</label>
<div className="mt-2" data-testid="select-import-location">
<SelectMenuV2
required
options={[
{
title: "Select",
description: "Select the location",
value: "0",
},
...locations.map((location: any) => ({
title: location.name,
description: location.facility.name,
value: location.id,
})),
]}
<SelectFormField
name="asset-import-location"
options={locations.map((location: any) => ({
title: location.name,
description: location.facility.name,
value: location.id,
}))}
optionLabel={(o) => o.title}
optionValue={(o) => o.value}
placeholder="Select a location"
value={location}
onChange={(e) => setLocation(e)}
onChange={({ value }) => setLocation(value)}
error={errors.location}
/>
</div>
</div>
Expand Down
Loading

1 comment on commit ce4154a

@vercel
Copy link

@vercel vercel bot commented on ce4154a Oct 8, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Successfully deployed to the following URLs:

care-storybook – ./

care-storybook-git-master-ohcnetwork.vercel.app
care-storybook-ohcnetwork.vercel.app

Please sign in to comment.