Morph relation v2 delete: retrieve related field metadata to delete (#14142)

close https://github.com/twentyhq/core-team-issues/issues/1411
This commit is contained in:
Paul Rastoin
2025-08-29 11:59:32 +02:00
committed by GitHub
parent 0bdd1c4803
commit b5114a5fa3
5 changed files with 106 additions and 11 deletions
@@ -1,12 +1,8 @@
import { FieldMetadataType } from 'twenty-shared/types';
const relationFieldTypes = [
export const RELATION_FIELD_TYPES = [
FieldMetadataType.RELATION,
FieldMetadataType.MORPH_RELATION,
] as const;
export type RelationFieldMetadataType = (typeof relationFieldTypes)[number];
export const RELATION_FIELD_TYPES: FieldMetadataType[] = [
...relationFieldTypes,
];
export type RelationFieldMetadataType = (typeof RELATION_FIELD_TYPES)[number];
@@ -0,0 +1,67 @@
import { FieldMetadataType } from 'twenty-shared/types';
import { isDefined } from 'twenty-shared/utils';
import { type FlatFieldMetadata } from 'src/engine/metadata-modules/flat-field-metadata/types/flat-field-metadata.type';
import { findRelationFlatFieldMetadataTargetFlatFieldMetadataOrThrow } from 'src/engine/metadata-modules/flat-field-metadata/utils/find-relation-flat-field-metadatas-target-flat-field-metadata-or-throw.util';
import { isFlatFieldMetadataEntityOfType } from 'src/engine/metadata-modules/flat-field-metadata/utils/is-flat-field-metadata-of-type.util';
import {
FlatObjectMetadataMapsException,
FlatObjectMetadataMapsExceptionCode,
} from 'src/engine/metadata-modules/flat-object-metadata-maps/flat-object-metadata-maps.exception';
import { type FlatObjectMetadataMaps } from 'src/engine/metadata-modules/flat-object-metadata-maps/types/flat-object-metadata-maps.type';
export type FindFlatFieldMetadatasRelatedToMorphRelationOrThrowArgs = {
flatObjectMetadataMaps: FlatObjectMetadataMaps;
flatFieldMetadata: FlatFieldMetadata<FieldMetadataType.MORPH_RELATION>;
};
export const findFlatFieldMetadatasRelatedToMorphRelationOrThrow = ({
flatObjectMetadataMaps,
flatFieldMetadata: morphRelationFlatFieldMetadata,
}: FindFlatFieldMetadatasRelatedToMorphRelationOrThrowArgs): FlatFieldMetadata[] => {
const flatObjectMetadataWithFlatFieldMaps =
flatObjectMetadataMaps.byId[
morphRelationFlatFieldMetadata.objectMetadataId
];
if (!isDefined(flatObjectMetadataWithFlatFieldMaps)) {
throw new FlatObjectMetadataMapsException(
'Morph field relation object metadata not found',
FlatObjectMetadataMapsExceptionCode.OBJECT_METADATA_NOT_FOUND,
);
}
if (
!isDefined(
flatObjectMetadataWithFlatFieldMaps.fieldsById[
morphRelationFlatFieldMetadata.id
],
)
) {
throw new FlatObjectMetadataMapsException(
'Morph relation field not found in related object metadata',
FlatObjectMetadataMapsExceptionCode.FIELD_METADATA_NOT_FOUND,
);
}
return flatObjectMetadataWithFlatFieldMaps.flatFieldMetadatas.flatMap(
(flatFieldMetadata) => {
if (
!isFlatFieldMetadataEntityOfType(
flatFieldMetadata,
FieldMetadataType.MORPH_RELATION,
) ||
flatFieldMetadata.name !== morphRelationFlatFieldMetadata.name
) {
return [];
}
const relationTargetFlatFieldMetadata =
findRelationFlatFieldMetadataTargetFlatFieldMetadataOrThrow({
flatFieldMetadata,
flatObjectMetadataMaps,
});
return [flatFieldMetadata, relationTargetFlatFieldMetadata];
},
);
};
@@ -10,6 +10,7 @@ import {
FieldMetadataExceptionCode,
} from 'src/engine/metadata-modules/field-metadata/field-metadata.exception';
import { type FlatFieldMetadata } from 'src/engine/metadata-modules/flat-field-metadata/types/flat-field-metadata.type';
import { findFlatFieldMetadatasRelatedToMorphRelationOrThrow } from 'src/engine/metadata-modules/flat-field-metadata/utils/find-flat-field-metadatas-related-to-morph-relation-or-throw.util';
import { findRelationFlatFieldMetadataTargetFlatFieldMetadataOrThrow } from 'src/engine/metadata-modules/flat-field-metadata/utils/find-relation-flat-field-metadatas-target-flat-field-metadata-or-throw.util';
import { isFlatFieldMetadataEntityOfType } from 'src/engine/metadata-modules/flat-field-metadata/utils/is-flat-field-metadata-of-type.util';
import { type FlatObjectMetadataMaps } from 'src/engine/metadata-modules/flat-object-metadata-maps/types/flat-object-metadata-maps.type';
@@ -45,11 +46,23 @@ export const fromDeleteFieldInputToFlatFieldMetadatasToDelete = ({
if (
isFlatFieldMetadataEntityOfType(
flatFieldMetadataToDelete,
FieldMetadataType.RELATION,
) ||
FieldMetadataType.MORPH_RELATION,
)
) {
return findFlatFieldMetadatasRelatedToMorphRelationOrThrow({
flatObjectMetadataMaps: existingFlatObjectMetadataMaps,
flatFieldMetadata: flatFieldMetadataToDelete,
});
}
if (
isFlatFieldMetadataEntityOfType(
flatFieldMetadataToDelete,
FieldMetadataType.MORPH_RELATION,
FieldMetadataType.RELATION,
) &&
isFlatFieldMetadataEntityOfType(
flatFieldMetadataToDelete.flatRelationTargetFieldMetadata,
FieldMetadataType.RELATION,
)
) {
const relationTargetFlatFieldMetadata =
@@ -61,5 +74,22 @@ export const fromDeleteFieldInputToFlatFieldMetadatasToDelete = ({
return [flatFieldMetadataToDelete, relationTargetFlatFieldMetadata];
}
if (
isFlatFieldMetadataEntityOfType(
flatFieldMetadataToDelete,
FieldMetadataType.RELATION,
) &&
isFlatFieldMetadataEntityOfType(
flatFieldMetadataToDelete.flatRelationTargetFieldMetadata,
FieldMetadataType.MORPH_RELATION,
)
) {
return findFlatFieldMetadatasRelatedToMorphRelationOrThrow({
flatObjectMetadataMaps: existingFlatObjectMetadataMaps,
flatFieldMetadata:
flatFieldMetadataToDelete.flatRelationTargetFieldMetadata,
});
}
return [flatFieldMetadataToDelete];
};
@@ -8,4 +8,6 @@ import { isFlatFieldMetadataEntityOfTypes } from 'src/engine/metadata-modules/fl
export const isRelationFlatFieldMetadata = (
flatFieldMetadata: FlatFieldMetadata,
): flatFieldMetadata is FlatFieldMetadata<RelationFieldMetadataType> =>
isFlatFieldMetadataEntityOfTypes(flatFieldMetadata, RELATION_FIELD_TYPES);
isFlatFieldMetadataEntityOfTypes(flatFieldMetadata, [
...RELATION_FIELD_TYPES,
]);
@@ -7,5 +7,5 @@ import {
export const isRelationFieldMetadataType = (
type: FieldMetadataType,
): type is RelationFieldMetadataType => {
return RELATION_FIELD_TYPES.includes(type);
return RELATION_FIELD_TYPES.includes(type as RelationFieldMetadataType);
};