Activity cache injection (#3791)
* WIP * Minor fixes * Added TODO * Fix post merge * Fix * Fixed warnings * Fixed comments * Fixed comments * Fixed naming * Removed comment * WIP * WIP 2 * Finished working version * Fixes * Fixed typing * Fixes * Fixes * Fixes * Naming fixes * WIP * Fix import * WIP * Working version on title * Fixed create record id overwrite * Removed unecessary callback * Masterpiece * Fixed delete on click outside drawer or delete * Cleaned * Cleaned * Cleaned * Minor fixes * Fixes * Fixed naming * WIP * Fix * Fixed create from target inline cell * Removed console.log * Fixed delete activity optimistic effect * Fixed no title * Fixed debounce and title body creation --------- Co-authored-by: Charles Bochet <charles@twenty.com>
This commit is contained in:
@ -1,89 +0,0 @@
|
||||
import { useApolloClient } from '@apollo/client';
|
||||
import { isNonEmptyString } from '@sniptt/guards';
|
||||
|
||||
import { makeTimelineActivitiesQueryVariables } from '@/activities/timeline/utils/makeTimelineActivitiesQueryVariables';
|
||||
import { Activity } from '@/activities/types/Activity';
|
||||
import { ActivityTarget } from '@/activities/types/ActivityTarget';
|
||||
import { useObjectMetadataItem } from '@/object-metadata/hooks/useObjectMetadataItem';
|
||||
import { CoreObjectNameSingular } from '@/object-metadata/types/CoreObjectNameSingular';
|
||||
import { getRecordConnectionFromRecords } from '@/object-record/cache/utils/getRecordConnectionFromRecords';
|
||||
import { getRecordsFromRecordConnection } from '@/object-record/cache/utils/getRecordsFromRecordConnection';
|
||||
import { ObjectRecordConnection } from '@/object-record/types/ObjectRecordConnection';
|
||||
|
||||
export const useInjectIntoTimelineActivitiesQuery = () => {
|
||||
const apolloClient = useApolloClient();
|
||||
|
||||
const {
|
||||
objectMetadataItem: objectMetadataItemActivity,
|
||||
findManyRecordsQuery: findManyActivitiesQuery,
|
||||
} = useObjectMetadataItem({
|
||||
objectNameSingular: CoreObjectNameSingular.Activity,
|
||||
});
|
||||
|
||||
const injectIntoTimelineActivitiesQuery = ({
|
||||
activityTargets,
|
||||
activityToInject,
|
||||
}: {
|
||||
activityTargets: ActivityTarget[];
|
||||
activityToInject: Activity;
|
||||
}) => {
|
||||
const activityIds = activityTargets
|
||||
?.map((activityTarget) => activityTarget.activityId)
|
||||
.filter(isNonEmptyString);
|
||||
|
||||
const timelineActivitiesQueryVariables =
|
||||
makeTimelineActivitiesQueryVariables({
|
||||
activityIds,
|
||||
});
|
||||
|
||||
const exitistingActivitiesQueryResult = apolloClient.readQuery({
|
||||
query: findManyActivitiesQuery,
|
||||
variables: timelineActivitiesQueryVariables,
|
||||
});
|
||||
|
||||
const extistingActivities = exitistingActivitiesQueryResult
|
||||
? getRecordsFromRecordConnection({
|
||||
recordConnection: exitistingActivitiesQueryResult[
|
||||
objectMetadataItemActivity.namePlural
|
||||
] as ObjectRecordConnection<Activity>,
|
||||
})
|
||||
: [];
|
||||
|
||||
const newActivity = {
|
||||
...activityToInject,
|
||||
__typename: 'Activity',
|
||||
};
|
||||
|
||||
const newActivitiesSortedAsActivitiesQuery = [
|
||||
newActivity,
|
||||
...extistingActivities,
|
||||
];
|
||||
|
||||
const newActivityIdsSortedAsActivityTargetsQuery = [
|
||||
...extistingActivities,
|
||||
newActivity,
|
||||
].map((activity) => activity.id);
|
||||
|
||||
const newTimelineActivitiesQueryVariables =
|
||||
makeTimelineActivitiesQueryVariables({
|
||||
activityIds: newActivityIdsSortedAsActivityTargetsQuery,
|
||||
});
|
||||
|
||||
const newActivityConnectionForCache = getRecordConnectionFromRecords({
|
||||
objectNameSingular: CoreObjectNameSingular.Activity,
|
||||
records: newActivitiesSortedAsActivitiesQuery,
|
||||
});
|
||||
|
||||
apolloClient.writeQuery({
|
||||
query: findManyActivitiesQuery,
|
||||
variables: newTimelineActivitiesQueryVariables,
|
||||
data: {
|
||||
[objectMetadataItemActivity.namePlural]: newActivityConnectionForCache,
|
||||
},
|
||||
});
|
||||
};
|
||||
|
||||
return {
|
||||
injectIntoTimelineActivitiesNextQuery: injectIntoTimelineActivitiesQuery,
|
||||
};
|
||||
};
|
||||
@ -0,0 +1,124 @@
|
||||
import { isNonEmptyString } from '@sniptt/guards';
|
||||
|
||||
import { makeTimelineActivitiesQueryVariables } from '@/activities/timeline/utils/makeTimelineActivitiesQueryVariables';
|
||||
import { Activity } from '@/activities/types/Activity';
|
||||
import { ActivityTarget } from '@/activities/types/ActivityTarget';
|
||||
import { ActivityTargetableObject } from '@/activities/types/ActivityTargetableEntity';
|
||||
import { getActivityTargetObjectFieldIdName } from '@/activities/utils/getTargetObjectFilterFieldName';
|
||||
import { useObjectMetadataItemOnly } from '@/object-metadata/hooks/useObjectMetadataItemOnly';
|
||||
import { CoreObjectNameSingular } from '@/object-metadata/types/CoreObjectNameSingular';
|
||||
import { useReadFindManyRecordsQueryInCache } from '@/object-record/cache/hooks/useReadFindManyRecordsQueryInCache';
|
||||
import { useUpsertFindManyRecordsQueryInCache } from '@/object-record/cache/hooks/useUpsertFindManyRecordsQueryInCache';
|
||||
|
||||
export const useInjectIntoTimelineActivitiesQueryAfterDrawerMount = () => {
|
||||
const { objectMetadataItem: objectMetadataItemActivity } =
|
||||
useObjectMetadataItemOnly({
|
||||
objectNameSingular: CoreObjectNameSingular.Activity,
|
||||
});
|
||||
|
||||
const {
|
||||
upsertFindManyRecordsQueryInCache: overwriteFindManyActivitiesInCache,
|
||||
} = useUpsertFindManyRecordsQueryInCache({
|
||||
objectMetadataItem: objectMetadataItemActivity,
|
||||
});
|
||||
|
||||
const { objectMetadataItem: objectMetadataItemActivityTarget } =
|
||||
useObjectMetadataItemOnly({
|
||||
objectNameSingular: CoreObjectNameSingular.ActivityTarget,
|
||||
});
|
||||
|
||||
const {
|
||||
readFindManyRecordsQueryInCache: readFindManyActivityTargetsQueryInCache,
|
||||
} = useReadFindManyRecordsQueryInCache({
|
||||
objectMetadataItem: objectMetadataItemActivityTarget,
|
||||
});
|
||||
|
||||
const {
|
||||
readFindManyRecordsQueryInCache: readFindManyActivitiesQueryInCache,
|
||||
} = useReadFindManyRecordsQueryInCache({
|
||||
objectMetadataItem: objectMetadataItemActivity,
|
||||
});
|
||||
|
||||
const {
|
||||
upsertFindManyRecordsQueryInCache:
|
||||
overwriteFindManyActivityTargetsQueryInCache,
|
||||
} = useUpsertFindManyRecordsQueryInCache({
|
||||
objectMetadataItem: objectMetadataItemActivityTarget,
|
||||
});
|
||||
|
||||
const injectIntoTimelineActivitiesQueryAfterDrawerMount = ({
|
||||
activityToInject,
|
||||
activityTargetsToInject,
|
||||
timelineTargetableObject,
|
||||
}: {
|
||||
activityToInject: Activity;
|
||||
activityTargetsToInject: ActivityTarget[];
|
||||
timelineTargetableObject: ActivityTargetableObject;
|
||||
}) => {
|
||||
const newActivity = {
|
||||
...activityToInject,
|
||||
__typename: 'Activity',
|
||||
};
|
||||
|
||||
const targetObjectFieldName = getActivityTargetObjectFieldIdName({
|
||||
nameSingular: timelineTargetableObject.targetObjectNameSingular,
|
||||
});
|
||||
|
||||
const activitiyTargetsForTargetableObjectQueryVariables = {
|
||||
filter: {
|
||||
[targetObjectFieldName]: {
|
||||
eq: timelineTargetableObject.id,
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
const existingActivityTargetsForTargetableObject =
|
||||
readFindManyActivityTargetsQueryInCache({
|
||||
queryVariables: activitiyTargetsForTargetableObjectQueryVariables,
|
||||
});
|
||||
|
||||
const newActivityTargetsForTargetableObject = [
|
||||
...existingActivityTargetsForTargetableObject,
|
||||
...activityTargetsToInject,
|
||||
];
|
||||
|
||||
const existingActivityIds = existingActivityTargetsForTargetableObject
|
||||
?.map((activityTarget) => activityTarget.activityId)
|
||||
.filter(isNonEmptyString);
|
||||
|
||||
const timelineActivitiesQueryVariablesBeforeDrawerMount =
|
||||
makeTimelineActivitiesQueryVariables({
|
||||
activityIds: existingActivityIds,
|
||||
});
|
||||
|
||||
const existingActivities = readFindManyActivitiesQueryInCache({
|
||||
queryVariables: timelineActivitiesQueryVariablesBeforeDrawerMount,
|
||||
});
|
||||
|
||||
const activityIdsAfterDrawerMount = [
|
||||
...existingActivityIds,
|
||||
newActivity.id,
|
||||
];
|
||||
|
||||
const timelineActivitiesQueryVariablesAfterDrawerMount =
|
||||
makeTimelineActivitiesQueryVariables({
|
||||
activityIds: activityIdsAfterDrawerMount,
|
||||
});
|
||||
|
||||
overwriteFindManyActivityTargetsQueryInCache({
|
||||
objectRecordsToOverwrite: newActivityTargetsForTargetableObject,
|
||||
queryVariables: activitiyTargetsForTargetableObjectQueryVariables,
|
||||
});
|
||||
|
||||
const newActivities = [newActivity, ...existingActivities];
|
||||
|
||||
overwriteFindManyActivitiesInCache({
|
||||
objectRecordsToOverwrite: newActivities,
|
||||
queryVariables: timelineActivitiesQueryVariablesAfterDrawerMount,
|
||||
});
|
||||
};
|
||||
|
||||
return {
|
||||
injectIntoTimelineActivitiesQueryAfterDrawerMount,
|
||||
};
|
||||
};
|
||||
@ -1,7 +1,7 @@
|
||||
import { useEffect, useState } from 'react';
|
||||
import { isNonEmptyArray, isNonEmptyString } from '@sniptt/guards';
|
||||
|
||||
import { useActivityTargets } from '@/activities/hooks/useActivityTargets';
|
||||
import { useActivityTargetsForTargetableObject } from '@/activities/hooks/useActivityTargetsForTargetableObject';
|
||||
import { makeTimelineActivitiesQueryVariables } from '@/activities/timeline/utils/makeTimelineActivitiesQueryVariables';
|
||||
import { Activity } from '@/activities/types/Activity';
|
||||
import { ActivityTargetableObject } from '@/activities/types/ActivityTargetableEntity';
|
||||
@ -17,14 +17,12 @@ export const useTimelineActivities = ({
|
||||
activityTargets,
|
||||
loadingActivityTargets,
|
||||
initialized: initializedActivityTargets,
|
||||
} = useActivityTargets({
|
||||
} = useActivityTargetsForTargetableObject({
|
||||
targetableObject,
|
||||
});
|
||||
|
||||
const [initialized, setInitialized] = useState(false);
|
||||
|
||||
const [activities, setActivities] = useState<Activity[]>([]);
|
||||
|
||||
const activityIds = activityTargets
|
||||
?.map((activityTarget) => activityTarget.activityId)
|
||||
.filter(isNonEmptyString);
|
||||
@ -35,7 +33,7 @@ export const useTimelineActivities = ({
|
||||
},
|
||||
);
|
||||
|
||||
const { records: activitiesFromRequest, loading: loadingActivities } =
|
||||
const { records: activities, loading: loadingActivities } =
|
||||
useFindManyRecords<Activity>({
|
||||
skip: loadingActivityTargets || !isNonEmptyArray(activityTargets),
|
||||
objectNameSingular: CoreObjectNameSingular.Activity,
|
||||
@ -48,12 +46,6 @@ export const useTimelineActivities = ({
|
||||
},
|
||||
});
|
||||
|
||||
useEffect(() => {
|
||||
if (!loadingActivities) {
|
||||
setActivities(activitiesFromRequest);
|
||||
}
|
||||
}, [activitiesFromRequest, loadingActivities]);
|
||||
|
||||
const noActivityTargets =
|
||||
initializedActivityTargets && !isNonEmptyArray(activityTargets);
|
||||
|
||||
|
||||
Reference in New Issue
Block a user