diff --git a/packages/framework/esm-api/src/attachments.ts b/packages/framework/esm-api/src/attachments.ts new file mode 100644 index 000000000..4b7d45780 --- /dev/null +++ b/packages/framework/esm-api/src/attachments.ts @@ -0,0 +1,42 @@ +/** @module @category API */ +import type { UploadedFile } from './types'; +import { openmrsFetch } from './openmrs-fetch'; + +export const attachmentUrl = '/ws/rest/v1/attachment'; + +export function getAttachmentByUuid(attachmentUuid: string, abortController: AbortController) { + return openmrsFetch(`${attachmentUrl}/${attachmentUuid}`, { + signal: abortController.signal, + }); +} + +export function getAttachments(patientUuid: string, includeEncounterless: boolean, abortController: AbortController) { + return openmrsFetch(`${attachmentUrl}?patient=${patientUuid}&includeEncounterless=${includeEncounterless}`, { + signal: abortController.signal, + }); +} + +export async function createAttachment(patientUuid: string, fileToUpload: UploadedFile) { + const formData = new FormData(); + + formData.append('fileCaption', fileToUpload.fileName); + formData.append('patient', patientUuid); + + if (fileToUpload.file) { + formData.append('file', fileToUpload.file); + } else { + formData.append('file', new File([''], fileToUpload.fileName), fileToUpload.fileName); + formData.append('base64Content', fileToUpload.base64Content); + } + return openmrsFetch(`${attachmentUrl}`, { + method: 'POST', + body: formData, + }); +} + +export function deleteAttachmentPermanently(attachmentUuid: string, abortController: AbortController) { + return openmrsFetch(`${attachmentUrl}/${attachmentUuid}`, { + method: 'DELETE', + signal: abortController.signal, + }); +} diff --git a/packages/framework/esm-api/src/index.ts b/packages/framework/esm-api/src/index.ts index 819417cf6..0359cf486 100644 --- a/packages/framework/esm-api/src/index.ts +++ b/packages/framework/esm-api/src/index.ts @@ -1,4 +1,5 @@ export * from './types'; +export * from './attachments'; export * from './openmrs-fetch'; export * from './setup'; diff --git a/packages/framework/esm-api/src/public.ts b/packages/framework/esm-api/src/public.ts index 94bc6956a..7d46fdd20 100644 --- a/packages/framework/esm-api/src/public.ts +++ b/packages/framework/esm-api/src/public.ts @@ -1,5 +1,6 @@ export * from './types'; export * from './openmrs-fetch'; +export * from './attachments'; export * from './shared-api-objects/current-user'; export * from './shared-api-objects/current-patient'; diff --git a/packages/framework/esm-api/src/types/attachments-types.ts b/packages/framework/esm-api/src/types/attachments-types.ts new file mode 100644 index 000000000..3193d896e --- /dev/null +++ b/packages/framework/esm-api/src/types/attachments-types.ts @@ -0,0 +1,25 @@ +export interface UploadedFile { + file?: File; + base64Content: string; + fileName: string; + fileType: string; + fileDescription: string; + status?: 'uploading' | 'complete'; +} + +export interface Attachment { + id: string; + src: string; + title: string; + description: string; + dateTime: string; + bytesMimeType: string; + bytesContentFamily: string; +} +export interface AttachmentResponse { + bytesContentFamily: string; + bytesMimeType: string; + comment: string; + dateTime: string; + uuid: string; +} diff --git a/packages/framework/esm-api/src/types/index.ts b/packages/framework/esm-api/src/types/index.ts index 1791a78c4..2ea7a7389 100644 --- a/packages/framework/esm-api/src/types/index.ts +++ b/packages/framework/esm-api/src/types/index.ts @@ -1,3 +1,4 @@ +export * from './attachments-types'; export * from './fetch'; export * from './fhir-resource'; export * from './openmrs-resource'; diff --git a/packages/framework/esm-framework/docs/API.md b/packages/framework/esm-framework/docs/API.md index 64ae9601a..4035911bd 100644 --- a/packages/framework/esm-framework/docs/API.md +++ b/packages/framework/esm-framework/docs/API.md @@ -7,7 +7,11 @@ ### API Functions - [clearCurrentUser](API.md#clearcurrentuser) +- [createAttachment](API.md#createattachment) +- [deleteAttachmentPermanently](API.md#deleteattachmentpermanently) - [fetchCurrentPatient](API.md#fetchcurrentpatient) +- [getAttachmentByUuid](API.md#getattachmentbyuuid) +- [getAttachments](API.md#getattachments) - [getCurrentUser](API.md#getcurrentuser) - [getLocations](API.md#getlocations) - [getLoggedInUser](API.md#getloggedinuser) @@ -159,6 +163,7 @@ ### Other Functions - [ExtensionSlot](API.md#extensionslot) +- [useAttachments](API.md#useattachments) ### Store Functions @@ -737,6 +742,16 @@ ___ ___ +### attachmentUrl + +• `Const` **attachmentUrl**: ``"/ws/rest/v1/attachment"`` + +#### Defined in + +[packages/framework/esm-api/src/attachments.ts:5](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/attachments.ts#L5) + +___ + ### defaultVisitCustomRepresentation • `Const` **defaultVisitCustomRepresentation**: `string` @@ -935,6 +950,48 @@ ___ ___ +### createAttachment + +▸ **createAttachment**(`patientUuid`, `fileToUpload`): `Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Parameters + +| Name | Type | +| :------ | :------ | +| `patientUuid` | `string` | +| `fileToUpload` | [`UploadedFile`](interfaces/UploadedFile.md) | + +#### Returns + +`Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Defined in + +[packages/framework/esm-api/src/attachments.ts:19](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/attachments.ts#L19) + +___ + +### deleteAttachmentPermanently + +▸ **deleteAttachmentPermanently**(`attachmentUuid`, `abortController`): `Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Parameters + +| Name | Type | +| :------ | :------ | +| `attachmentUuid` | `string` | +| `abortController` | `AbortController` | + +#### Returns + +`Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Defined in + +[packages/framework/esm-api/src/attachments.ts:37](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/attachments.ts#L37) + +___ + ### fetchCurrentPatient ▸ **fetchCurrentPatient**(`patientUuid`, `fetchInit?`, `includeOfflinePatients?`): `Promise`<`fhir.Patient` \| ``null``\> @@ -957,6 +1014,49 @@ ___ ___ +### getAttachmentByUuid + +▸ **getAttachmentByUuid**(`attachmentUuid`, `abortController`): `Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Parameters + +| Name | Type | +| :------ | :------ | +| `attachmentUuid` | `string` | +| `abortController` | `AbortController` | + +#### Returns + +`Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Defined in + +[packages/framework/esm-api/src/attachments.ts:7](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/attachments.ts#L7) + +___ + +### getAttachments + +▸ **getAttachments**(`patientUuid`, `includeEncounterless`, `abortController`): `Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Parameters + +| Name | Type | +| :------ | :------ | +| `patientUuid` | `string` | +| `includeEncounterless` | `boolean` | +| `abortController` | `AbortController` | + +#### Returns + +`Promise`<[`FetchResponse`](interfaces/FetchResponse.md)<`any`\>\> + +#### Defined in + +[packages/framework/esm-api/src/attachments.ts:13](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/attachments.ts#L13) + +___ + ### getCurrentUser ▸ **getCurrentUser**(): `Observable`<[`Session`](interfaces/Session.md)\> @@ -3957,6 +4057,35 @@ Passing a function as children ___ +### useAttachments + +▸ **useAttachments**(`patientUuid`, `includeEncounterless`): `Object` + +#### Parameters + +| Name | Type | +| :------ | :------ | +| `patientUuid` | `string` | +| `includeEncounterless` | `boolean` | + +#### Returns + +`Object` + +| Name | Type | +| :------ | :------ | +| `data` | [`AttachmentResponse`](interfaces/AttachmentResponse.md)[] | +| `error` | `any` | +| `isLoading` | `boolean` | +| `isValidating` | `boolean` | +| `mutate` | `KeyedMutator`<[`FetchResponse`](interfaces/FetchResponse.md)<{ `results`: [`AttachmentResponse`](interfaces/AttachmentResponse.md)[] }\>\> | + +#### Defined in + +[packages/framework/esm-react-utils/src/useAttachments.ts:5](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-react-utils/src/useAttachments.ts#L5) + +___ + ## Store Functions ### createGlobalStore diff --git a/packages/framework/esm-framework/docs/interfaces/Attachment.md b/packages/framework/esm-framework/docs/interfaces/Attachment.md new file mode 100644 index 000000000..eec6eef2b --- /dev/null +++ b/packages/framework/esm-framework/docs/interfaces/Attachment.md @@ -0,0 +1,85 @@ +[@openmrs/esm-framework](../API.md) / Attachment + +# Interface: Attachment + +## Table of contents + +### Properties + +- [bytesContentFamily](Attachment.md#bytescontentfamily) +- [bytesMimeType](Attachment.md#bytesmimetype) +- [dateTime](Attachment.md#datetime) +- [description](Attachment.md#description) +- [id](Attachment.md#id) +- [src](Attachment.md#src) +- [title](Attachment.md#title) + +## Properties + +### bytesContentFamily + +• **bytesContentFamily**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:17](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L17) + +___ + +### bytesMimeType + +• **bytesMimeType**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:16](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L16) + +___ + +### dateTime + +• **dateTime**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:15](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L15) + +___ + +### description + +• **description**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:14](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L14) + +___ + +### id + +• **id**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:11](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L11) + +___ + +### src + +• **src**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:12](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L12) + +___ + +### title + +• **title**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:13](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L13) diff --git a/packages/framework/esm-framework/docs/interfaces/AttachmentResponse.md b/packages/framework/esm-framework/docs/interfaces/AttachmentResponse.md new file mode 100644 index 000000000..5267564f2 --- /dev/null +++ b/packages/framework/esm-framework/docs/interfaces/AttachmentResponse.md @@ -0,0 +1,63 @@ +[@openmrs/esm-framework](../API.md) / AttachmentResponse + +# Interface: AttachmentResponse + +## Table of contents + +### Properties + +- [bytesContentFamily](AttachmentResponse.md#bytescontentfamily) +- [bytesMimeType](AttachmentResponse.md#bytesmimetype) +- [comment](AttachmentResponse.md#comment) +- [dateTime](AttachmentResponse.md#datetime) +- [uuid](AttachmentResponse.md#uuid) + +## Properties + +### bytesContentFamily + +• **bytesContentFamily**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:20](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L20) + +___ + +### bytesMimeType + +• **bytesMimeType**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:21](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L21) + +___ + +### comment + +• **comment**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:22](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L22) + +___ + +### dateTime + +• **dateTime**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:23](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L23) + +___ + +### uuid + +• **uuid**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:24](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L24) diff --git a/packages/framework/esm-framework/docs/interfaces/UploadedFile.md b/packages/framework/esm-framework/docs/interfaces/UploadedFile.md new file mode 100644 index 000000000..c68875f7f --- /dev/null +++ b/packages/framework/esm-framework/docs/interfaces/UploadedFile.md @@ -0,0 +1,74 @@ +[@openmrs/esm-framework](../API.md) / UploadedFile + +# Interface: UploadedFile + +## Table of contents + +### Properties + +- [base64Content](UploadedFile.md#base64content) +- [file](UploadedFile.md#file) +- [fileDescription](UploadedFile.md#filedescription) +- [fileName](UploadedFile.md#filename) +- [fileType](UploadedFile.md#filetype) +- [status](UploadedFile.md#status) + +## Properties + +### base64Content + +• **base64Content**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:3](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L3) + +___ + +### file + +• `Optional` **file**: `File` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:2](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L2) + +___ + +### fileDescription + +• **fileDescription**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:6](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L6) + +___ + +### fileName + +• **fileName**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:4](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L4) + +___ + +### fileType + +• **fileType**: `string` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:5](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L5) + +___ + +### status + +• `Optional` **status**: ``"uploading"`` \| ``"complete"`` + +#### Defined in + +[packages/framework/esm-api/src/types/attachments-types.ts:7](https://github.com/openmrs/openmrs-esm-core/blob/main/packages/framework/esm-api/src/types/attachments-types.ts#L7) diff --git a/packages/framework/esm-framework/mock.tsx b/packages/framework/esm-framework/mock.tsx index d6b5149fd..c490e89ee 100644 --- a/packages/framework/esm-framework/mock.tsx +++ b/packages/framework/esm-framework/mock.tsx @@ -1,9 +1,9 @@ import React from 'react'; import type {} from '@openmrs/esm-globals'; -import { createStore, StoreApi } from 'zustand'; +import { createStore, type StoreApi } from 'zustand'; import { NEVER, of } from 'rxjs'; import { interpolateUrl } from '@openmrs/esm-config'; -import { SessionStore } from '@openmrs/esm-api'; +import { type SessionStore } from '@openmrs/esm-api'; export { parseDate, formatDate, formatDatetime, formatTime, age } from '@openmrs/esm-utils'; export { interpolateString, interpolateUrl, validators, validator } from '@openmrs/esm-config'; @@ -56,6 +56,16 @@ export const newWorkspaceItem = jest.fn(); export const fhirBaseUrl = '/ws/fhir2/R4'; +export const attachmentUrl = '/ws/rest/v1/attachment'; + +export const getAttachmentByUuid = jest.fn(); + +export const getAttachments = jest.fn(); + +export const createAttachment = jest.fn(); + +export const deleteAttachmentPermanently = jest.fn(); + /* esm-state */ interface StoreEntity { value: StoreApi; @@ -205,6 +215,14 @@ export const ComponentContext = React.createContext(null); export const openmrsComponentDecorator = jest.fn().mockImplementation(() => (component) => component); +export const useAttachments = jest.fn(() => ({ + isLoading: true, + data: [], + error: null, + mutate: jest.fn(), + isValidating: true, +})); + export const useCurrentPatient = jest.fn(() => []); export const usePatient = jest.fn(() => ({ diff --git a/packages/framework/esm-react-utils/src/index.ts b/packages/framework/esm-react-utils/src/index.ts index ba63c9873..8b47fd1c4 100644 --- a/packages/framework/esm-react-utils/src/index.ts +++ b/packages/framework/esm-react-utils/src/index.ts @@ -8,6 +8,7 @@ export * from './openmrsComponentDecorator'; export * from './useAbortController'; export * from './useAssignedExtensions'; export * from './useAssignedExtensionIds'; +export * from './useAttachments'; export * from './useBodyScrollLock'; export * from './useConfig'; export * from './useConnectedExtensions'; diff --git a/packages/framework/esm-react-utils/src/public.ts b/packages/framework/esm-react-utils/src/public.ts index 52097275f..a4e8eab9c 100644 --- a/packages/framework/esm-react-utils/src/public.ts +++ b/packages/framework/esm-react-utils/src/public.ts @@ -7,6 +7,7 @@ export * from './getLifecycle'; export * from './useAbortController'; export * from './useAssignedExtensions'; export * from './useAssignedExtensionIds'; +export * from './useAttachments'; export * from './useBodyScrollLock'; export * from './useConfig'; export * from './useConnectedExtensions'; diff --git a/packages/framework/esm-react-utils/src/useAttachments.ts b/packages/framework/esm-react-utils/src/useAttachments.ts new file mode 100644 index 000000000..978c5494d --- /dev/null +++ b/packages/framework/esm-react-utils/src/useAttachments.ts @@ -0,0 +1,22 @@ +import { useMemo } from 'react'; +import useSWR from 'swr'; +import type { FetchResponse, AttachmentResponse } from '@openmrs/esm-api'; +import { attachmentUrl, openmrsFetch } from '@openmrs/esm-api'; +export function useAttachments(patientUuid: string, includeEncounterless: boolean) { + const { data, error, mutate, isLoading, isValidating } = useSWR< + FetchResponse<{ results: Array }> + >(`${attachmentUrl}?patient=${patientUuid}&includeEncounterless=${includeEncounterless}`, openmrsFetch); + + const results = useMemo( + () => ({ + isLoading, + data: data?.data.results ?? [], + error, + mutate, + isValidating, + }), + [data, error, isLoading, isValidating, mutate], + ); + + return results; +}