,
+ previousValue?: string,
+ currentValue?: string,
+ classes: {
+ container: string,
+ valueContainer: string,
+ buttonContainer: string,
+ previousValue: string,
+ currentValue: string,
+ updatePreviousValue: string,
+ updateCurrentValue: string,
+ updateArrow: string,
+ viewButton: string,
+ },
+};
+
+const styles = {
+ container: {
+ display: 'flex',
+ flexDirection: 'row',
+ alignItems: 'center',
+ whiteSpace: 'normal',
+ height: '100%',
+ },
+ buttonContainer: {
+ display: 'flex',
+ alignItems: 'center',
+ justifyContent: 'center',
+ },
+ previousValue: {
+ color: colors.grey700,
+ wordBreak: 'break-word',
+ },
+ currentValue: {
+ color: colors.grey900,
+ wordBreak: 'break-word',
+ },
+ updateArrow: {
+ display: 'inline-flex',
+ alignItems: 'center',
+ margin: spacers.dp4,
+ },
+ viewButton: {
+ background: 'none',
+ border: 'none',
+ cursor: 'pointer',
+ color: colors.grey800,
+ display: 'flex',
+ alignItems: 'center',
+ '&:hover': {
+ textDecoration: 'underline',
+ color: 'black',
+ },
+ },
+};
+
+export const ChangelogValueCellPlain = ({
+ dataItemId,
+ changeType,
+ currentValue,
+ previousValue,
+ classes,
+}: Props) => {
+ if (!currentValue) { return null; }
+ const isPolygon = dataItemId === 'geometry' && currentValue.length > 2;
+ const ComponentsByChangeType = isPolygon
+ ? PlygonChangelogComponentsByChangeType
+ : DefaultChangelogComponentsByChangeType;
+
+ const ChangelogComponent = ComponentsByChangeType[changeType];
+
+ if (!ChangelogComponent) {
+ console.error(`No component found for change type: ${changeType}`);
+ return null;
+ }
+
+ return (
+
+ );
+};
+
+export const ChangelogValueCell = withStyles(styles)(ChangelogValueCellPlain);
+
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellComponents.types.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellComponents.types.js
new file mode 100644
index 0000000000..784a342da4
--- /dev/null
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellComponents.types.js
@@ -0,0 +1,13 @@
+// @flow
+export type ChangelogValueCellProps = {
+ previousValue?: string,
+ currentValue?: string,
+ classes: {
+ container: string,
+ buttonContainer: string,
+ previousValue: string,
+ currentValue: string,
+ updateArrow: string,
+ viewButton: string,
+ },
+ };
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellDefault.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellDefault.js
new file mode 100644
index 0000000000..53d47340eb
--- /dev/null
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellDefault.js
@@ -0,0 +1,33 @@
+// @flow
+import React from 'react';
+import { IconArrowRight16 } from '@dhis2/ui';
+import { CHANGE_TYPES } from '../../../../Changelog/Changelog.constants';
+import type { ChangelogValueCellProps } from './ChangelogValueCellComponents.types';
+
+const Updated = ({ previousValue, currentValue, classes }: ChangelogValueCellProps) => (
+
+ {previousValue}
+
+
+
+ {currentValue}
+
+);
+
+const Created = ({ currentValue, classes }: ChangelogValueCellProps) => (
+
+ {currentValue}
+
+);
+
+const Deleted = ({ previousValue, classes }: ChangelogValueCellProps) => (
+
+ {previousValue}
+
+);
+
+export const DefaultChangelogComponentsByChangeType = Object.freeze({
+ [CHANGE_TYPES.UPDATED]: Updated,
+ [CHANGE_TYPES.CREATED]: Created,
+ [CHANGE_TYPES.DELETED]: Deleted,
+});
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellPolygon.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellPolygon.js
new file mode 100644
index 0000000000..2dd45fe46c
--- /dev/null
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/ChangelogValueCellPolygon.js
@@ -0,0 +1,93 @@
+// @flow
+import React, { useState } from 'react';
+import { IconArrowRight16, IconChevronUp16, IconChevronDown16 } from '@dhis2/ui';
+import { CHANGE_TYPES } from '../../../../Changelog/Changelog.constants';
+import type { ChangelogValueCellProps } from './ChangelogValueCellComponents.types';
+
+const ValueDisplay = ({ value, showMore, className }) => (
+ {showMore ? value : value?.slice(0, 1)}
+);
+
+const ViewMoreButton = ({ showMore, onClick, classes }) => (
+
+);
+
+const Updated = ({ previousValue, currentValue, classes }: ChangelogValueCellProps) => {
+ const [showMore, setShowMore] = useState(false);
+
+ return (
+ <>
+
+
+
+
+
+
+
+
+ setShowMore(!showMore)}
+ classes={classes}
+ />
+
+ >
+
+ );
+};
+
+
+const Created = ({ currentValue, classes }: ChangelogValueCellProps) => {
+ const [showMore, setShowMore] = useState(false);
+
+ return (
+
+
+ setShowMore(!showMore)}
+ classes={classes}
+ />
+
+ );
+};
+
+const Deleted = ({ previousValue, classes }: ChangelogValueCellProps) => {
+ const [showMore, setShowMore] = useState(false);
+
+ return (
+
+
+ setShowMore(!showMore)}
+ classes={classes}
+ />
+
+ );
+};
+
+export const PlygonChangelogComponentsByChangeType = Object.freeze({
+ [CHANGE_TYPES.UPDATED]: Updated,
+ [CHANGE_TYPES.CREATED]: Created,
+ [CHANGE_TYPES.DELETED]: Deleted,
+});
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/index.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/index.js
new file mode 100644
index 0000000000..fc72eca0e2
--- /dev/null
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/ChangelogValueCellComponents/index.js
@@ -0,0 +1,6 @@
+// @flow
+
+export { DefaultChangelogComponentsByChangeType } from './ChangelogValueCellDefault';
+export { PlygonChangelogComponentsByChangeType } from './ChangelogValueCellPolygon';
+
+export type { ChangelogValueCellProps } from './ChangelogValueCellComponents.types';
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/index.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/index.js
new file mode 100644
index 0000000000..88dbf63fb0
--- /dev/null
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogCells/ChangelogValueCell/index.js
@@ -0,0 +1,3 @@
+// @flow
+
+export { ChangelogValueCell } from './ChangelogValueCell';
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogTableRow.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogTableRow.js
index 3169194fc1..e93571cbf2 100644
--- a/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogTableRow.js
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/ChangelogTable/ChangelogTableRow.js
@@ -13,11 +13,13 @@ type Props = {
},
classes: {
dataItemColumn: string,
+ valueColumn: string,
},
};
const styles = {
dataItemColumn: { wordWrap: 'break-word', hyphens: 'auto' },
+ valueColumn: { wordWrap: 'break-word' },
};
const ChangelogTableRowPlain = ({ record, classes }: Props) => (
@@ -26,7 +28,7 @@ const ChangelogTableRowPlain = ({ record, classes }: Props) => (
{record.user}
{record.dataItemLabel}
-
+
);
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/index.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/index.js
index 7d2911cd6d..1cc9b74cc8 100644
--- a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/index.js
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/index.js
@@ -1,4 +1,3 @@
// @flow
export { useChangelogData } from './useChangelogData';
-export { useListDataValues } from './useListDataValues';
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useChangelogData.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useChangelogData.js
index f9562cf4ac..3599cf48b2 100644
--- a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useChangelogData.js
+++ b/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useChangelogData.js
@@ -1,31 +1,48 @@
// @flow
-import { useState } from 'react';
+import moment from 'moment';
+import { v4 as uuid } from 'uuid';
+import log from 'loglevel';
+import { errorCreator } from 'capture-core-utils';
+import { useMemo, useState } from 'react';
+import { useTimeZoneConversion } from '@dhis2/app-runtime';
import { useApiDataQuery } from '../../../../utils/reactQueryHelpers';
-import {
- CHANGELOG_ENTITY_TYPES,
- QUERY_KEYS_BY_ENTITY_TYPE,
-} from '../Changelog/Changelog.constants';
-import type {
- SortDirection,
-} from '../Changelog/Changelog.types';
+import { CHANGELOG_ENTITY_TYPES, QUERY_KEYS_BY_ENTITY_TYPE } from '../Changelog/Changelog.constants';
+import type { Change, ChangelogRecord, ItemDefinitions, SortDirection } from '../Changelog/Changelog.types';
+import { convertServerToClient } from '../../../../converters';
+import { convert } from '../../../../converters/clientToList';
type Props = {
entityId: string,
programId?: string,
entityType: $Values,
-};
+ dataItemDefinitions: ItemDefinitions,
+}
const DEFAULT_PAGE_SIZE = 10;
const DEFAULT_SORT_DIRECTION = 'default';
+const getMetadataItemDefinition = (
+ elementKey: string,
+ change: Change,
+ dataItemDefinitions: ItemDefinitions,
+) => {
+ const { dataElement, attribute, property } = change;
+ const fieldId = dataElement ?? attribute ?? property;
+ const metadataElement = fieldId ? dataItemDefinitions[fieldId] : dataItemDefinitions[elementKey];
+
+ return { metadataElement, fieldId };
+};
+
export const useChangelogData = ({
entityId,
entityType,
programId,
+ dataItemDefinitions,
}: Props) => {
- const [sortDirection, setSortDirection] = useState(DEFAULT_SORT_DIRECTION);
- const [page, setPage] = useState(1);
- const [pageSize, setPageSize] = useState(DEFAULT_PAGE_SIZE);
+ const [page, setPage] = useState < number >(1);
+ const [pageSize, setPageSize] = useState < number >(DEFAULT_PAGE_SIZE);
+ const [sortDirection, setSortDirection] = useState < SortDirection >(DEFAULT_SORT_DIRECTION);
+ const { fromServerDate } = useTimeZoneConversion();
const handleChangePageSize = (newPageSize: number) => {
setPage(1);
@@ -33,7 +50,7 @@ export const useChangelogData = ({
};
const { data, isLoading, isError } = useApiDataQuery(
- ['changelog', entityType, entityId, 'rawData', { sortDirection, page, pageSize, programId }],
+ ['changelog', entityType, entityId, { sortDirection, page, pageSize, programId }],
{
resource: `tracker/${QUERY_KEYS_BY_ENTITY_TYPE[entityType]}/${entityId}/changeLogs`,
params: {
@@ -50,15 +67,164 @@ export const useChangelogData = ({
},
);
+ const mockData: any = useMemo(() => [
+ {
+ createdAt: '2024-11-14T11:03:08.269',
+ createdBy: {
+ uid: 'xE7jOejl9FI',
+ username: 'admin',
+ firstName: 'John',
+ surname: 'Traore',
+ },
+ type: 'UPDATE',
+ change: {
+ eventProperty: {
+ property: 'geometry',
+ previousValue: [-11.420051, 8.101209],
+ currentValue: [-11.450123, 8.125678],
+ },
+ },
+ },
+ {
+ createdAt: '2024-11-14T11:05:47.437',
+ createdBy: {
+ uid: 'xE7jOejl9FI',
+ username: 'admin',
+ firstName: 'John',
+ surname: 'Traore',
+ },
+ type: 'UPDATE',
+ change: {
+ eventProperty: {
+ property: 'geometry',
+ previousValue: [
+ [-11.437732, 8.110726],
+ [-11.396705, 8.109876],
+ [-11.398421, 8.089143],
+ [-11.414729, 8.084894],
+ [-11.436873, 8.088803],
+ [-11.437732, 8.110726],
+ ],
+ currentValue: [
+ [-11.440000, 8.120000],
+ [-11.400000, 8.115000],
+ [-11.402000, 8.095000],
+ [-11.418000, 8.090000],
+ [-11.440000, 8.120000],
+ ],
+ },
+ },
+ },
+ {
+ createdAt: '2024-11-14T11:09:47.437',
+ createdBy: {
+ uid: 'xE7jOejl9FI',
+ username: 'admin',
+ firstName: 'John',
+ surname: 'Traore',
+ },
+ type: 'UPDATE',
+ change: {
+ eventProperty: {
+ property: 'occurredAt',
+ previousValue: '2024-01-30T00:00:00.000',
+ currentValue: '2024-01-31T00:00:00.000',
+ },
+ },
+ },
+ {
+ createdAt: '2024-11-14T11:15:00.000',
+ createdBy: {
+ uid: 'xE7jOejl9FI',
+ username: 'admin',
+ firstName: 'John',
+ surname: 'Traore',
+ },
+ type: 'UPDATE',
+ change: {
+ eventProperty: {
+ property: 'scheduledAt',
+ previousValue: '2024-01-29T00:00:00.000',
+ currentValue: '2024-01-30T00:00:00.000',
+ },
+ },
+ },
+ {
+ createdAt: '2019-09-27T00:02:11.604',
+ createdBy: {
+ uid: 'AIK2aQOJIbj',
+ username: 'tracker',
+ firstName: 'Tracker name',
+ surname: 'Tracker surname',
+ },
+ type: 'UPDATE',
+ change: {
+ dataValue: {
+ dataElement: 'X8zyunlgUfM',
+ previousValue: 'Replacement',
+ currentValue: 'Fresh',
+ },
+ },
+ },
+ ], []);
+
+
+ const records: ?Array = useMemo(() => {
+ if (!data) return undefined;
+
+ return mockData.map((changelog) => {
+ const { change: apiChange, createdAt, createdBy } = changelog;
+ const elementKey = Object.keys(apiChange)[0];
+ const change = apiChange[elementKey];
+
+ const { metadataElement, fieldId } = getMetadataItemDefinition(
+ elementKey,
+ change,
+ dataItemDefinitions,
+ );
+
+ if (!metadataElement) {
+ log.error(errorCreator('Could not find metadata for element')({
+ ...changelog,
+ }));
+ return null;
+ }
+
+ const { firstName, surname, username } = createdBy;
+ const { options } = metadataElement;
+
+ const previousValue = convert(
+ convertServerToClient(change.previousValue, metadataElement.type),
+ metadataElement.type,
+ options,
+ );
+
+ const currentValue = convert(
+ convertServerToClient(change.currentValue, metadataElement.type),
+ metadataElement.type,
+ options,
+ );
+
+ return {
+ reactKey: uuid(),
+ date: moment(fromServerDate(createdAt)).format('YYYY-MM-DD HH:mm'),
+ user: `${firstName} ${surname} (${username})`,
+ dataItemId: fieldId,
+ changeType: changelog.type,
+ dataItemLabel: metadataElement.name,
+ previousValue,
+ currentValue,
+ };
+ }).filter(Boolean);
+ }, [data, dataItemDefinitions, fromServerDate, mockData]);
+
return {
- rawRecords: data,
+ records,
pager: data?.pager,
setPage,
setPageSize: handleChangePageSize,
sortDirection,
setSortDirection,
- page,
- pageSize,
isLoading,
isError,
};
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useListDataValues.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useListDataValues.js
deleted file mode 100644
index e94bf94a88..0000000000
--- a/src/core_modules/capture-core/components/WidgetsChangelog/common/hooks/useListDataValues.js
+++ /dev/null
@@ -1,177 +0,0 @@
-// @flow
-import { useMemo } from 'react';
-import log from 'loglevel';
-import { useTimeZoneConversion, useConfig, useDataEngine } from '@dhis2/app-runtime';
-import { useQuery } from 'react-query';
-import { errorCreator, buildUrl, pipe } from 'capture-core-utils';
-import { ReactQueryAppNamespace } from 'capture-core/utils/reactQueryHelpers';
-import { dataElementTypes } from '../../../../metaData';
-import { CHANGELOG_ENTITY_TYPES } from '../Changelog/Changelog.constants';
-import type { Change, ItemDefinitions, SortDirection } from '../Changelog/Changelog.types';
-import { convertServerToClient } from '../../../../converters';
-import { convert as convertClientToList } from '../../../../converters/clientToList';
-import { RECORD_TYPE, subValueGetterByElementType } from '../utils/getSubValueForChangelogData';
-import { makeQuerySingleResource } from '../../../../utils/api';
-import { attributeOptionsKey } from '../../../DataEntryDhis2Helpers';
-
-
-type Props = {
- rawRecords: Object,
- dataItemDefinitions: ItemDefinitions,
- entityId: string,
- entityData: Object,
- entityType: $Values,
- programId?: string,
- sortDirection: SortDirection,
- page: number,
- pageSize: number,
-};
-
-const fetchFormattedValues = async ({
- rawRecords,
- dataItemDefinitions,
- entityId,
- entityData,
- entityType,
- programId,
- absoluteApiPath,
- querySingleResource,
- fromServerDate,
-}) => {
- if (!rawRecords) return [];
-
- const getMetadataItemDefinition = (
- elementKey: string,
- change: Change,
- ) => {
- const fieldId = change.dataElement || change.attribute;
- if (!fieldId) {
- log.error('Could not find fieldId in change:', change);
- return { metadataElement: null, fieldId: null };
- }
- const metadataElement = dataItemDefinitions[fieldId];
- return { metadataElement, fieldId };
- };
-
-
- const fetchedRecords = await Promise.all(
- rawRecords.changeLogs.map(async (changelog) => {
- const { change: apiChange, createdAt, createdBy, type } = changelog;
- const elementKey = Object.keys(apiChange)[0];
- const change = apiChange[elementKey];
-
- const { metadataElement, fieldId } = getMetadataItemDefinition(
- elementKey,
- change,
- );
-
- if (!metadataElement) {
- log.error(
- errorCreator('Could not find metadata for element')({ ...changelog }),
- );
- return null;
- }
-
- const getSubValue = subValueGetterByElementType[RECORD_TYPE[entityType]]?.[metadataElement.type];
-
- const getValue = async (value, latestValue) => {
- if (!getSubValue) {
- return convertServerToClient(value, metadataElement.type);
- }
- if (entityType === RECORD_TYPE.trackedEntity) {
- return getSubValue({
- trackedEntity: { teiId: entityId, value },
- programId,
- attributeId: fieldId,
- absoluteApiPath,
- querySingleResource,
- latestValue,
- });
- }
- if (entityType === RECORD_TYPE.event) {
- return getSubValue({
- dataElement: { id: fieldId, value },
- eventId: entityId,
- absoluteApiPath,
- querySingleResource,
- latestValue,
- });
- }
- return null;
- };
-
- const [previousValueClient, currentValueClient] = await Promise.all([
- change.previousValue ? getValue(change.previousValue, false) : null,
- getValue(change.currentValue, entityData?.[change.attribute ?? change.dataElement]?.value === change.currentValue),
- ]);
-
- const { firstName, surname, username } = createdBy;
- const { options } = metadataElement;
-
- const previousValue = convertClientToList(previousValueClient, metadataElement.type, options);
- const currentValue = convertClientToList(currentValueClient, metadataElement.type, options);
-
- return {
- reactKey: fieldId ? `${createdAt}-${fieldId}` : attributeOptionsKey,
- date: pipe(convertServerToClient, convertClientToList)(fromServerDate(createdAt), dataElementTypes.DATETIME),
- user: `${firstName} ${surname} (${username})`,
- changeType: type,
- dataItemLabel: metadataElement.name,
- previousValue,
- currentValue,
- };
- }),
- );
-
- return fetchedRecords.filter(Boolean);
-};
-
-export const useListDataValues = ({
- rawRecords,
- dataItemDefinitions,
- entityId,
- entityData,
- entityType,
- programId,
- sortDirection,
- page,
- pageSize,
-}: Props) => {
- const dataEngine = useDataEngine();
- const { baseUrl, apiVersion } = useConfig();
- const { fromServerDate } = useTimeZoneConversion();
- const absoluteApiPath = buildUrl(baseUrl, `api/${apiVersion}`);
-
- const querySingleResource = useMemo(
- () => makeQuerySingleResource(dataEngine.query.bind(dataEngine)),
- [dataEngine],
- );
-
- const queryKey = [ReactQueryAppNamespace, 'changelog', entityType, entityId, 'formattedData', { sortDirection, page, pageSize, programId }];
-
- const { data: processedRecords, isError, isLoading } = useQuery(
- queryKey,
- () => fetchFormattedValues({
- rawRecords,
- dataItemDefinitions,
- entityId,
- entityData,
- entityType,
- programId,
- absoluteApiPath,
- querySingleResource,
- fromServerDate,
- }),
- {
- enabled: !!rawRecords && !!dataItemDefinitions && !!entityId && !!entityType,
- staleTime: Infinity,
- cacheTime: Infinity,
- },
- );
-
- return {
- processedRecords,
- isError,
- isLoading,
- };
-};
diff --git a/src/core_modules/capture-core/components/WidgetsChangelog/common/utils/getSubValueForChangelogData.js b/src/core_modules/capture-core/components/WidgetsChangelog/common/utils/getSubValueForChangelogData.js
deleted file mode 100644
index 85b13724e2..0000000000
--- a/src/core_modules/capture-core/components/WidgetsChangelog/common/utils/getSubValueForChangelogData.js
+++ /dev/null
@@ -1,148 +0,0 @@
-// @flow
-import log from 'loglevel';
-import i18n from '@dhis2/d2-i18n';
-import { errorCreator } from 'capture-core-utils';
-import { dataElementTypes } from '../../../../metaData';
-import type { QuerySingleResource } from '../../../../utils/api';
-
-type SubValueTEAProps = {
- trackedEntity: Object,
- attributeId: string,
- programId: string,
- absoluteApiPath: string,
- querySingleResource: QuerySingleResource,
- latestValue?: boolean,
-};
-
-type SubValuesDataElementProps = {
- dataElement: Object,
- querySingleResource: QuerySingleResource,
- eventId: string,
- absoluteApiPath: string,
- latestValue?: boolean,
-};
-
-const buildTEAUrlByElementType: {|
-[string]: Function,
-|} = {
- [dataElementTypes.FILE_RESOURCE]: async ({
- trackedEntity,
- attributeId,
- programId,
- absoluteApiPath,
- querySingleResource,
- latestValue,
- }: SubValueTEAProps) => {
- const { teiId, value } = trackedEntity;
- if (!value) return null;
- try {
- if (!latestValue) {
- return i18n.t('File');
- }
-
- const { id, displayName: name } = await querySingleResource({ resource: `fileResources/${value}` });
-
- return {
- id,
- name,
- url: `${absoluteApiPath}/tracker/trackedEntities/${teiId}/attributes/${attributeId}/file?program=${programId}`,
- };
- } catch (error) {
- log.error(
- errorCreator('Error fetching file resource')({ error }),
- );
- return null;
- }
- },
- [dataElementTypes.IMAGE]: async ({
- trackedEntity,
- attributeId,
- programId,
- absoluteApiPath,
- latestValue,
- querySingleResource,
- }: SubValueTEAProps) => {
- const { teiId, value } = trackedEntity;
- if (!value) return null;
- try {
- if (!latestValue) {
- return i18n.t('Image');
- }
- const { id, displayName: name } = await querySingleResource({ resource: `fileResources/${value}` });
-
- return {
- id,
- name,
- url: `${absoluteApiPath}/tracker/trackedEntities/${teiId}/attributes/${attributeId}/image?program=${programId}`,
- previewUrl: `${absoluteApiPath}/tracker/trackedEntities/${teiId}/attributes/${attributeId}/image?program=${programId}&dimension=small`,
- };
- } catch (error) {
- log.error(
- errorCreator('Error fetching image resource')({ error }),
- );
- return null;
- }
- },
-};
-
-const buildDataElementUrlByElementType: {|
-[string]: Function,
-|} = {
- [dataElementTypes.FILE_RESOURCE]: async ({ dataElement, querySingleResource, eventId, absoluteApiPath, latestValue }: SubValuesDataElementProps) => {
- const { id: dataElementId, value } = dataElement;
- if (!value) return null;
-
- try {
- if (!latestValue) {
- return i18n.t('File');
- }
-
- const { id, displayName: name } = await querySingleResource({ resource: `fileResources/${value}` });
-
- return {
- id,
- name,
- url: `${absoluteApiPath}/tracker/events/${eventId}/dataValues/${dataElementId}/file`,
- };
- } catch (error) {
- log.error(
- errorCreator('Error fetching file resource')({ error }),
- );
- return null;
- }
- },
- [dataElementTypes.IMAGE]: async ({ dataElement, querySingleResource, eventId, absoluteApiPath, latestValue }: SubValuesDataElementProps) => {
- const { id: dataElementId, value } = dataElement;
- if (!value) return null;
-
- try {
- if (!latestValue) {
- return i18n.t('Image');
- }
-
- const { id, displayName: name } = await querySingleResource({ resource: `fileResources/${value}` });
-
- return {
- id,
- name,
- url: `${absoluteApiPath}/tracker/events/${eventId}/dataValues/${dataElementId}/image`,
- previewUrl: `${absoluteApiPath}/tracker/events/${eventId}/dataValues/${dataElementId}/image?dimension=small`,
- };
- } catch (error) {
- log.error(
- errorCreator('Error fetching image resource')({ error }),
- );
- return null;
- }
- },
-};
-
-export const RECORD_TYPE = Object.freeze({
- event: 'event',
- trackedEntity: 'trackedEntity',
-});
-
-export const subValueGetterByElementType = Object.freeze({
- [RECORD_TYPE.trackedEntity]: buildTEAUrlByElementType,
- [RECORD_TYPE.event]: buildDataElementUrlByElementType,
-});