In this PR I layout the first steps to migrate Activity to a traditional Standard objects Since this is a big transition, I'd rather split it into several deployments / PRs <img width="1512" alt="image" src="https://github.com/user-attachments/assets/012e2bbf-9d1b-4723-aaf6-269ef588b050"> --------- Co-authored-by: Charles Bochet <charles@twenty.com> Co-authored-by: bosiraphael <71827178+bosiraphael@users.noreply.github.com> Co-authored-by: Weiko <corentin@twenty.com> Co-authored-by: Faisal-imtiyaz123 <142205282+Faisal-imtiyaz123@users.noreply.github.com> Co-authored-by: Prateek Jain <prateekj1171998@gmail.com>
134 lines
4.5 KiB
TypeScript
134 lines
4.5 KiB
TypeScript
import { useApolloClient } from '@apollo/client';
|
|
|
|
import { findActivitiesOperationSignatureFactory } from '@/activities/graphql/operation-signatures/factories/findActivitiesOperationSignatureFactory';
|
|
import { ActivityTargetableObject } from '@/activities/types/ActivityTargetableEntity';
|
|
import { Note } from '@/activities/types/Note';
|
|
import { NoteTarget } from '@/activities/types/NoteTarget';
|
|
import { Task } from '@/activities/types/Task';
|
|
import { TaskTarget } from '@/activities/types/TaskTarget';
|
|
import { useObjectMetadataItem } from '@/object-metadata/hooks/useObjectMetadataItem';
|
|
import { useObjectMetadataItems } from '@/object-metadata/hooks/useObjectMetadataItems';
|
|
import { CoreObjectNameSingular } from '@/object-metadata/types/CoreObjectNameSingular';
|
|
import { useGetRecordFromCache } from '@/object-record/cache/hooks/useGetRecordFromCache';
|
|
import { useUpsertFindManyRecordsQueryInCache } from '@/object-record/cache/hooks/useUpsertFindManyRecordsQueryInCache';
|
|
import { getRecordFromCache } from '@/object-record/cache/utils/getRecordFromCache';
|
|
import { ObjectRecord } from '@/object-record/types/ObjectRecord';
|
|
import { sortByAscString } from '~/utils/array/sortByAscString';
|
|
import { isDefined } from '~/utils/isDefined';
|
|
|
|
export const usePrepareFindManyActivitiesQuery = ({
|
|
activityObjectNameSingular,
|
|
}: {
|
|
activityObjectNameSingular: CoreObjectNameSingular;
|
|
}) => {
|
|
const { objectMetadataItem: objectMetadataItemActivity } =
|
|
useObjectMetadataItem({
|
|
objectNameSingular: activityObjectNameSingular,
|
|
});
|
|
|
|
const getActivityFromCache = useGetRecordFromCache({
|
|
objectNameSingular: activityObjectNameSingular,
|
|
});
|
|
|
|
const cache = useApolloClient().cache;
|
|
const { objectMetadataItems } = useObjectMetadataItems();
|
|
|
|
const { upsertFindManyRecordsQueryInCache: upsertFindManyActivitiesInCache } =
|
|
useUpsertFindManyRecordsQueryInCache({
|
|
objectMetadataItem: objectMetadataItemActivity,
|
|
});
|
|
|
|
const prepareFindManyActivitiesQuery = ({
|
|
targetableObject,
|
|
additionalFilter,
|
|
shouldActivityBeExcluded,
|
|
}: {
|
|
additionalFilter?: Record<string, unknown>;
|
|
targetableObject: ActivityTargetableObject;
|
|
shouldActivityBeExcluded?: (activityTarget: Task | Note) => boolean;
|
|
}) => {
|
|
const targetableObjectMetadataItem = objectMetadataItems.find(
|
|
(objectMetadataItem) =>
|
|
objectMetadataItem.nameSingular ===
|
|
targetableObject.targetObjectNameSingular,
|
|
);
|
|
|
|
if (!targetableObjectMetadataItem) {
|
|
throw new Error(
|
|
`Cannot find object metadata item for targetable object ${targetableObject.targetObjectNameSingular}`,
|
|
);
|
|
}
|
|
|
|
const targetableObjectRecord = getRecordFromCache<ObjectRecord>({
|
|
recordId: targetableObject.id,
|
|
objectMetadataItem: targetableObjectMetadataItem,
|
|
objectMetadataItems,
|
|
cache,
|
|
});
|
|
|
|
const activityTargets: (TaskTarget | NoteTarget)[] =
|
|
targetableObjectRecord?.taskTargets ??
|
|
targetableObjectRecord?.noteTargets ??
|
|
[];
|
|
|
|
const activityTargetIds = [
|
|
...new Set(
|
|
activityTargets
|
|
.map((activityTarget) => activityTarget.id)
|
|
.filter(isDefined),
|
|
),
|
|
];
|
|
|
|
const activities: (Task | Note)[] = activityTargetIds
|
|
.map((activityTargetId) => {
|
|
const activityTarget = activityTargets.find(
|
|
(activityTarget) => activityTarget.id === activityTargetId,
|
|
);
|
|
|
|
if (!activityTarget) {
|
|
return undefined;
|
|
}
|
|
|
|
return getActivityFromCache<Task | Note>(activityTarget.activityId);
|
|
})
|
|
.filter(isDefined);
|
|
|
|
const activityIds = [...new Set(activities.map((activity) => activity.id))];
|
|
|
|
const nextFindManyActivitiesQueryFilter = {
|
|
filter: {
|
|
id: {
|
|
in: [...activityIds].sort(sortByAscString),
|
|
},
|
|
...additionalFilter,
|
|
},
|
|
};
|
|
|
|
const filteredActivities = [
|
|
...activities.filter((activity) => !shouldActivityBeExcluded?.(activity)),
|
|
].sort((a, b) => {
|
|
return a.createdAt > b.createdAt ? -1 : 1;
|
|
});
|
|
|
|
const FIND_ACTIVITIES_OPERATION_SIGNATURE =
|
|
findActivitiesOperationSignatureFactory({
|
|
objectNameSingular: activityObjectNameSingular,
|
|
objectMetadataItems,
|
|
});
|
|
|
|
upsertFindManyActivitiesInCache({
|
|
objectRecordsToOverwrite: filteredActivities,
|
|
queryVariables: {
|
|
...nextFindManyActivitiesQueryFilter,
|
|
orderBy: [{ createdAt: 'DescNullsFirst' }],
|
|
},
|
|
recordGqlFields: FIND_ACTIVITIES_OPERATION_SIGNATURE.fields,
|
|
computeReferences: true,
|
|
});
|
|
};
|
|
|
|
return {
|
|
prepareFindManyActivitiesQuery,
|
|
};
|
|
};
|