Remove old relations (#11993)
This is a first PR to remove old relation logic Next steps: - remove relationMetadata from cache - remove relationMetadata table content and structure - refactor relationDefinition to leverage field.settings instead
This commit is contained in:
@ -6,7 +6,6 @@ import {
|
||||
} from 'typeorm';
|
||||
|
||||
import { ObjectRecordFilter } from 'src/engine/api/graphql/workspace-query-builder/interfaces/object-record.interface';
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
|
||||
import { FieldMetadataMap } from 'src/engine/metadata-modules/types/field-metadata-map';
|
||||
|
||||
@ -20,14 +19,12 @@ export class GraphqlQueryFilterConditionParser {
|
||||
constructor(
|
||||
fieldMetadataMapByName: FieldMetadataMap,
|
||||
fieldMetadataMapByJoinColumnName: FieldMetadataMap,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
this.fieldMetadataMapByName = fieldMetadataMapByName;
|
||||
this.fieldMetadataMapByJoinColumnName = fieldMetadataMapByJoinColumnName;
|
||||
this.queryFilterFieldParser = new GraphqlQueryFilterFieldParser(
|
||||
this.fieldMetadataMapByName,
|
||||
this.fieldMetadataMapByJoinColumnName,
|
||||
featureFlagsMap,
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
@ -2,7 +2,6 @@ import { capitalize } from 'twenty-shared/utils';
|
||||
import { WhereExpressionBuilder } from 'typeorm';
|
||||
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
|
||||
import {
|
||||
GraphqlQueryRunnerException,
|
||||
@ -19,16 +18,13 @@ const ARRAY_OPERATORS = ['in', 'contains', 'notContains'];
|
||||
export class GraphqlQueryFilterFieldParser {
|
||||
private fieldMetadataMapByName: FieldMetadataMap;
|
||||
private fieldMetadataMapByJoinColumnName: FieldMetadataMap;
|
||||
private featureFlagsMap: FeatureFlagMap;
|
||||
|
||||
constructor(
|
||||
fieldMetadataMapByName: FieldMetadataMap,
|
||||
fieldMetadataMapByJoinColumnName: FieldMetadataMap,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
this.fieldMetadataMapByName = fieldMetadataMapByName;
|
||||
this.fieldMetadataMapByJoinColumnName = fieldMetadataMapByJoinColumnName;
|
||||
this.featureFlagsMap = featureFlagsMap;
|
||||
}
|
||||
|
||||
public parse(
|
||||
|
||||
@ -1,25 +1,17 @@
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
|
||||
import {
|
||||
GraphqlQuerySelectedFieldsParser,
|
||||
GraphqlQuerySelectedFieldsResult,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/graphql-query-parsers/graphql-query-selected-fields/graphql-selected-fields.parser';
|
||||
import { getRelationObjectMetadata } from 'src/engine/api/graphql/graphql-query-runner/utils/get-relation-object-metadata.util';
|
||||
import { getTargetObjectMetadataOrThrow } from 'src/engine/api/graphql/graphql-query-runner/utils/get-target-object-metadata.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { ObjectMetadataMaps } from 'src/engine/metadata-modules/types/object-metadata-maps';
|
||||
|
||||
export class GraphqlQuerySelectedFieldsRelationParser {
|
||||
private objectMetadataMaps: ObjectMetadataMaps;
|
||||
private featureFlagsMap: FeatureFlagMap;
|
||||
|
||||
constructor(
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
constructor(objectMetadataMaps: ObjectMetadataMaps) {
|
||||
this.objectMetadataMaps = objectMetadataMaps;
|
||||
this.featureFlagsMap = featureFlagsMap;
|
||||
}
|
||||
|
||||
parseRelationField(
|
||||
@ -34,17 +26,14 @@ export class GraphqlQuerySelectedFieldsRelationParser {
|
||||
|
||||
accumulator.relations[fieldKey] = true;
|
||||
|
||||
const isNewRelationEnabled =
|
||||
this.featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled];
|
||||
|
||||
const targetObjectMetadata = isNewRelationEnabled
|
||||
? getTargetObjectMetadataOrThrow(fieldMetadata, this.objectMetadataMaps)
|
||||
: getRelationObjectMetadata(fieldMetadata, this.objectMetadataMaps);
|
||||
const targetObjectMetadata = getTargetObjectMetadataOrThrow(
|
||||
fieldMetadata,
|
||||
this.objectMetadataMaps,
|
||||
);
|
||||
|
||||
const targetFields = targetObjectMetadata.fieldsByName;
|
||||
const fieldParser = new GraphqlQuerySelectedFieldsParser(
|
||||
this.objectMetadataMaps,
|
||||
this.featureFlagsMap,
|
||||
);
|
||||
const relationAccumulator = fieldParser.parse(fieldValue, targetFields);
|
||||
|
||||
|
||||
@ -1,6 +1,5 @@
|
||||
import { capitalize } from 'twenty-shared/utils';
|
||||
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
|
||||
import { GraphqlQuerySelectedFieldsAggregateParser } from 'src/engine/api/graphql/graphql-query-runner/graphql-query-parsers/graphql-query-selected-fields/graphql-selected-fields-aggregate.parser';
|
||||
@ -21,15 +20,9 @@ export class GraphqlQuerySelectedFieldsParser {
|
||||
private graphqlQuerySelectedFieldsRelationParser: GraphqlQuerySelectedFieldsRelationParser;
|
||||
private aggregateParser: GraphqlQuerySelectedFieldsAggregateParser;
|
||||
|
||||
constructor(
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
constructor(objectMetadataMaps: ObjectMetadataMaps) {
|
||||
this.graphqlQuerySelectedFieldsRelationParser =
|
||||
new GraphqlQuerySelectedFieldsRelationParser(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new GraphqlQuerySelectedFieldsRelationParser(objectMetadataMaps);
|
||||
this.aggregateParser = new GraphqlQuerySelectedFieldsAggregateParser();
|
||||
}
|
||||
|
||||
|
||||
@ -9,8 +9,11 @@ import {
|
||||
ObjectRecordFilter,
|
||||
ObjectRecordOrderBy,
|
||||
} from 'src/engine/api/graphql/workspace-query-builder/interfaces/object-record.interface';
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
|
||||
import {
|
||||
GraphqlQueryRunnerException,
|
||||
GraphqlQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { GraphqlQueryFilterConditionParser } from 'src/engine/api/graphql/graphql-query-runner/graphql-query-parsers/graphql-query-filter/graphql-query-filter-condition.parser';
|
||||
import { GraphqlQueryOrderFieldParser } from 'src/engine/api/graphql/graphql-query-runner/graphql-query-parsers/graphql-query-order/graphql-query-order.parser';
|
||||
import {
|
||||
@ -21,10 +24,6 @@ import { FieldMetadataMap } from 'src/engine/metadata-modules/types/field-metada
|
||||
import { ObjectMetadataItemWithFieldMaps } from 'src/engine/metadata-modules/types/object-metadata-item-with-field-maps';
|
||||
import { ObjectMetadataMaps } from 'src/engine/metadata-modules/types/object-metadata-maps';
|
||||
import { getObjectMetadataMapItemByNameSingular } from 'src/engine/metadata-modules/utils/get-object-metadata-map-item-by-name-singular.util';
|
||||
import {
|
||||
GraphqlQueryRunnerException,
|
||||
GraphqlQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
|
||||
export class GraphqlQueryParser {
|
||||
private fieldMetadataMapByName: FieldMetadataMap;
|
||||
@ -32,22 +31,18 @@ export class GraphqlQueryParser {
|
||||
private objectMetadataMaps: ObjectMetadataMaps;
|
||||
private filterConditionParser: GraphqlQueryFilterConditionParser;
|
||||
private orderFieldParser: GraphqlQueryOrderFieldParser;
|
||||
private featureFlagsMap: FeatureFlagMap;
|
||||
|
||||
constructor(
|
||||
fieldMetadataMapByName: FieldMetadataMap,
|
||||
fieldMetadataMapByJoinColumnName: FieldMetadataMap,
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
this.objectMetadataMaps = objectMetadataMaps;
|
||||
this.fieldMetadataMapByName = fieldMetadataMapByName;
|
||||
this.fieldMetadataMapByJoinColumnName = fieldMetadataMapByJoinColumnName;
|
||||
this.featureFlagsMap = featureFlagsMap;
|
||||
this.filterConditionParser = new GraphqlQueryFilterConditionParser(
|
||||
this.fieldMetadataMapByName,
|
||||
this.fieldMetadataMapByJoinColumnName,
|
||||
featureFlagsMap,
|
||||
);
|
||||
this.orderFieldParser = new GraphqlQueryOrderFieldParser(
|
||||
this.fieldMetadataMapByName,
|
||||
@ -136,7 +131,6 @@ export class GraphqlQueryParser {
|
||||
|
||||
const selectedFieldsParser = new GraphqlQuerySelectedFieldsParser(
|
||||
this.objectMetadataMaps,
|
||||
this.featureFlagsMap,
|
||||
);
|
||||
|
||||
return selectedFieldsParser.parse(graphqlSelectedFields, parentFields);
|
||||
|
||||
@ -6,7 +6,6 @@ import {
|
||||
ObjectRecordOrderBy,
|
||||
} from 'src/engine/api/graphql/workspace-query-builder/interfaces/object-record.interface';
|
||||
import { IConnection } from 'src/engine/api/graphql/workspace-query-runner/interfaces/connection.interface';
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
|
||||
import { CONNECTION_MAX_DEPTH } from 'src/engine/api/graphql/graphql-query-runner/constants/connection-max-depth.constant';
|
||||
@ -15,10 +14,8 @@ import {
|
||||
GraphqlQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { encodeCursor } from 'src/engine/api/graphql/graphql-query-runner/utils/cursors.util';
|
||||
import { getRelationObjectMetadata } from 'src/engine/api/graphql/graphql-query-runner/utils/get-relation-object-metadata.util';
|
||||
import { getTargetObjectMetadataOrThrow } from 'src/engine/api/graphql/graphql-query-runner/utils/get-target-object-metadata.util';
|
||||
import { AggregationField } from 'src/engine/api/graphql/workspace-schema-builder/utils/get-available-aggregations-from-object-fields.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { compositeTypeDefinitions } from 'src/engine/metadata-modules/field-metadata/composite-types';
|
||||
import { isCompositeFieldMetadataType } from 'src/engine/metadata-modules/field-metadata/utils/is-composite-field-metadata-type.util';
|
||||
import { ObjectMetadataMaps } from 'src/engine/metadata-modules/types/object-metadata-maps';
|
||||
@ -29,14 +26,9 @@ import { isPlainObject } from 'src/utils/is-plain-object';
|
||||
|
||||
export class ObjectRecordsToGraphqlConnectionHelper {
|
||||
private objectMetadataMaps: ObjectMetadataMaps;
|
||||
private featureFlagsMap: FeatureFlagMap;
|
||||
|
||||
constructor(
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: FeatureFlagMap,
|
||||
) {
|
||||
constructor(objectMetadataMaps: ObjectMetadataMaps) {
|
||||
this.objectMetadataMaps = objectMetadataMaps;
|
||||
this.featureFlagsMap = featureFlagsMap;
|
||||
}
|
||||
|
||||
public createConnection<T extends ObjectRecord = ObjectRecord>({
|
||||
@ -154,9 +146,6 @@ export class ObjectRecordsToGraphqlConnectionHelper {
|
||||
);
|
||||
}
|
||||
|
||||
const isNewRelationEnabled =
|
||||
this.featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled];
|
||||
|
||||
const objectMetadata = getObjectMetadataMapItemByNameSingular(
|
||||
this.objectMetadataMaps,
|
||||
objectName,
|
||||
@ -181,12 +170,10 @@ export class ObjectRecordsToGraphqlConnectionHelper {
|
||||
|
||||
if (isRelationFieldMetadataType(fieldMetadata.type)) {
|
||||
if (Array.isArray(value)) {
|
||||
const targetObjectMetadata = isNewRelationEnabled
|
||||
? getTargetObjectMetadataOrThrow(
|
||||
fieldMetadata,
|
||||
this.objectMetadataMaps,
|
||||
)
|
||||
: getRelationObjectMetadata(fieldMetadata, this.objectMetadataMaps);
|
||||
const targetObjectMetadata = getTargetObjectMetadataOrThrow(
|
||||
fieldMetadata,
|
||||
this.objectMetadataMaps,
|
||||
);
|
||||
|
||||
processedObjectRecord[key] = this.createConnection({
|
||||
objectRecords: value,
|
||||
@ -206,12 +193,10 @@ export class ObjectRecordsToGraphqlConnectionHelper {
|
||||
depth: depth + 1,
|
||||
});
|
||||
} else if (isPlainObject(value)) {
|
||||
const targetObjectMetadata = isNewRelationEnabled
|
||||
? getTargetObjectMetadataOrThrow(
|
||||
fieldMetadata,
|
||||
this.objectMetadataMaps,
|
||||
)
|
||||
: getRelationObjectMetadata(fieldMetadata, this.objectMetadataMaps);
|
||||
const targetObjectMetadata = getTargetObjectMetadataOrThrow(
|
||||
fieldMetadata,
|
||||
this.objectMetadataMaps,
|
||||
);
|
||||
|
||||
processedObjectRecord[key] = this.processRecord({
|
||||
objectRecord: value,
|
||||
|
||||
@ -324,7 +324,6 @@ export class ProcessNestedRelationsV2Helper {
|
||||
result,
|
||||
targetObjectMetadata,
|
||||
objectMetadataMaps,
|
||||
true,
|
||||
);
|
||||
|
||||
return { relationResults, relationAggregatedFieldsResult };
|
||||
|
||||
@ -1,32 +1,16 @@
|
||||
import { Injectable } from '@nestjs/common';
|
||||
|
||||
import {
|
||||
DataSource,
|
||||
FindOptionsRelations,
|
||||
ObjectLiteral,
|
||||
SelectQueryBuilder,
|
||||
} from 'typeorm';
|
||||
import { FindOptionsRelations, ObjectLiteral } from 'typeorm';
|
||||
|
||||
import { ObjectRecord } from 'src/engine/api/graphql/workspace-query-builder/interfaces/object-record.interface';
|
||||
|
||||
import {
|
||||
GraphqlQueryRunnerException,
|
||||
GraphqlQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ProcessAggregateHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/process-aggregate.helper';
|
||||
import { ProcessNestedRelationsV2Helper } from 'src/engine/api/graphql/graphql-query-runner/helpers/process-nested-relations-v2.helper';
|
||||
import {
|
||||
getRelationMetadata,
|
||||
getRelationObjectMetadata,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/utils/get-relation-object-metadata.util';
|
||||
import { AggregationField } from 'src/engine/api/graphql/workspace-schema-builder/utils/get-available-aggregations-from-object-fields.util';
|
||||
import { AuthContext } from 'src/engine/core-modules/auth/types/auth-context.type';
|
||||
import { ObjectMetadataItemWithFieldMaps } from 'src/engine/metadata-modules/types/object-metadata-item-with-field-maps';
|
||||
import { ObjectMetadataMaps } from 'src/engine/metadata-modules/types/object-metadata-maps';
|
||||
import { getObjectMetadataMapItemByNameSingular } from 'src/engine/metadata-modules/utils/get-object-metadata-map-item-by-name-singular.util';
|
||||
import { WorkspaceDataSource } from 'src/engine/twenty-orm/datasource/workspace.datasource';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
import { deduceRelationDirection } from 'src/engine/utils/deduce-relation-direction.util';
|
||||
|
||||
@Injectable()
|
||||
export class ProcessNestedRelationsHelper {
|
||||
@ -45,7 +29,6 @@ export class ProcessNestedRelationsHelper {
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
}: {
|
||||
@ -58,472 +41,21 @@ export class ProcessNestedRelationsHelper {
|
||||
limit: number;
|
||||
authContext: AuthContext;
|
||||
dataSource: WorkspaceDataSource;
|
||||
isNewRelationEnabled: boolean;
|
||||
shouldBypassPermissionChecks: boolean;
|
||||
roleId?: string;
|
||||
}): Promise<void> {
|
||||
if (isNewRelationEnabled) {
|
||||
return this.processNestedRelationsV2Helper.processNestedRelations({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
});
|
||||
}
|
||||
|
||||
const processRelationTasks = Object.entries(relations).map(
|
||||
([relationName, nestedRelations]) =>
|
||||
this.processRelation({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationName,
|
||||
nestedRelations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
}),
|
||||
);
|
||||
|
||||
await Promise.all(processRelationTasks);
|
||||
}
|
||||
|
||||
private async processRelation<T extends ObjectRecord = ObjectRecord>({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationName,
|
||||
nestedRelations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
}: {
|
||||
objectMetadataMaps: ObjectMetadataMaps;
|
||||
parentObjectMetadataItem: ObjectMetadataItemWithFieldMaps;
|
||||
parentObjectRecords: T[];
|
||||
parentObjectRecordsAggregatedValues: Record<string, any>;
|
||||
relationName: string;
|
||||
nestedRelations: any;
|
||||
aggregate: Record<string, AggregationField>;
|
||||
limit: number;
|
||||
authContext: AuthContext;
|
||||
dataSource: DataSource;
|
||||
isNewRelationEnabled: boolean;
|
||||
shouldBypassPermissionChecks: boolean;
|
||||
roleId?: string;
|
||||
}): Promise<void> {
|
||||
const relationFieldMetadata =
|
||||
parentObjectMetadataItem.fieldsByName[relationName];
|
||||
const relationMetadata = getRelationMetadata(relationFieldMetadata);
|
||||
const relationDirection = deduceRelationDirection(
|
||||
relationFieldMetadata,
|
||||
relationMetadata,
|
||||
);
|
||||
|
||||
const processor =
|
||||
relationDirection === 'to'
|
||||
? this.processToRelation
|
||||
: this.processFromRelation;
|
||||
|
||||
await processor.call(this, {
|
||||
return this.processNestedRelationsV2Helper.processNestedRelations({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationName,
|
||||
nestedRelations,
|
||||
relations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
});
|
||||
}
|
||||
|
||||
private async processFromRelation<T extends ObjectRecord = ObjectRecord>({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationName,
|
||||
nestedRelations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
}: {
|
||||
objectMetadataMaps: ObjectMetadataMaps;
|
||||
parentObjectMetadataItem: ObjectMetadataItemWithFieldMaps;
|
||||
parentObjectRecords: T[];
|
||||
parentObjectRecordsAggregatedValues: Record<string, any>;
|
||||
relationName: string;
|
||||
nestedRelations: any;
|
||||
aggregate: Record<string, AggregationField>;
|
||||
limit: number;
|
||||
authContext: AuthContext;
|
||||
dataSource: WorkspaceDataSource;
|
||||
isNewRelationEnabled: boolean;
|
||||
shouldBypassPermissionChecks: boolean;
|
||||
roleId?: string;
|
||||
}): Promise<void> {
|
||||
const { inverseRelationName, referenceObjectMetadata } =
|
||||
this.getRelationMetadata({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
relationName,
|
||||
});
|
||||
|
||||
const relationRepository = dataSource.getRepository(
|
||||
referenceObjectMetadata.nameSingular,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
);
|
||||
|
||||
const referenceQueryBuilder = relationRepository.createQueryBuilder(
|
||||
referenceObjectMetadata.nameSingular,
|
||||
);
|
||||
|
||||
const relationIds = this.getUniqueIds({
|
||||
records: parentObjectRecords,
|
||||
idField: 'id',
|
||||
});
|
||||
const { relationResults, relationAggregatedFieldsResult } =
|
||||
await this.findRelations({
|
||||
referenceQueryBuilder,
|
||||
column: `"${inverseRelationName}Id"`,
|
||||
ids: relationIds,
|
||||
limit: limit * parentObjectRecords.length,
|
||||
objectMetadataMaps,
|
||||
referenceObjectMetadata,
|
||||
aggregate,
|
||||
relationName,
|
||||
});
|
||||
|
||||
this.assignFromRelationResults({
|
||||
parentRecords: parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationResults,
|
||||
relationAggregatedFieldsResult,
|
||||
relationName,
|
||||
joinField: `${inverseRelationName}Id`,
|
||||
});
|
||||
|
||||
const referenceObjectMetadataItemWithFieldsMaps =
|
||||
getObjectMetadataMapItemByNameSingular(
|
||||
objectMetadataMaps,
|
||||
referenceObjectMetadata.nameSingular,
|
||||
);
|
||||
|
||||
if (!referenceObjectMetadataItemWithFieldsMaps) {
|
||||
throw new GraphqlQueryRunnerException(
|
||||
`Object ${referenceObjectMetadata.nameSingular} not found`,
|
||||
GraphqlQueryRunnerExceptionCode.OBJECT_METADATA_NOT_FOUND,
|
||||
);
|
||||
}
|
||||
|
||||
if (Object.keys(nestedRelations).length > 0) {
|
||||
await this.processNestedRelations({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem: referenceObjectMetadataItemWithFieldsMaps,
|
||||
parentObjectRecords: relationResults as ObjectRecord[],
|
||||
parentObjectRecordsAggregatedValues: relationAggregatedFieldsResult,
|
||||
relations: nestedRelations as Record<
|
||||
string,
|
||||
FindOptionsRelations<ObjectLiteral>
|
||||
>,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private async processToRelation<T extends ObjectRecord = ObjectRecord>({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationName,
|
||||
nestedRelations,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
}: {
|
||||
objectMetadataMaps: ObjectMetadataMaps;
|
||||
parentObjectMetadataItem: ObjectMetadataItemWithFieldMaps;
|
||||
parentObjectRecords: T[];
|
||||
parentObjectRecordsAggregatedValues: Record<string, any>;
|
||||
relationName: string;
|
||||
nestedRelations: any;
|
||||
aggregate: Record<string, AggregationField>;
|
||||
limit: number;
|
||||
authContext: any;
|
||||
dataSource: WorkspaceDataSource;
|
||||
isNewRelationEnabled: boolean;
|
||||
shouldBypassPermissionChecks: boolean;
|
||||
roleId?: string;
|
||||
}): Promise<void> {
|
||||
const { referenceObjectMetadata } = this.getRelationMetadata({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
relationName,
|
||||
});
|
||||
|
||||
const relationRepository = dataSource.getRepository(
|
||||
referenceObjectMetadata.nameSingular,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
);
|
||||
|
||||
const referenceQueryBuilder = relationRepository.createQueryBuilder(
|
||||
referenceObjectMetadata.nameSingular,
|
||||
);
|
||||
|
||||
const relationIds = this.getUniqueIds({
|
||||
records: parentObjectRecords,
|
||||
idField: `${relationName}Id`,
|
||||
});
|
||||
const { relationResults, relationAggregatedFieldsResult } =
|
||||
await this.findRelations({
|
||||
referenceQueryBuilder,
|
||||
column: 'id',
|
||||
ids: relationIds,
|
||||
limit,
|
||||
objectMetadataMaps,
|
||||
referenceObjectMetadata,
|
||||
aggregate,
|
||||
relationName,
|
||||
});
|
||||
|
||||
this.assignToRelationResults({
|
||||
parentRecords: parentObjectRecords,
|
||||
parentObjectRecordsAggregatedValues: parentObjectRecordsAggregatedValues,
|
||||
relationResults,
|
||||
relationAggregatedFieldsResult,
|
||||
relationName,
|
||||
});
|
||||
|
||||
const referenceObjectMetadataItemWithFieldsMaps =
|
||||
getObjectMetadataMapItemByNameSingular(
|
||||
objectMetadataMaps,
|
||||
referenceObjectMetadata.nameSingular,
|
||||
);
|
||||
|
||||
if (!referenceObjectMetadataItemWithFieldsMaps) {
|
||||
throw new GraphqlQueryRunnerException(
|
||||
`Object ${referenceObjectMetadata.nameSingular} not found`,
|
||||
GraphqlQueryRunnerExceptionCode.OBJECT_METADATA_NOT_FOUND,
|
||||
);
|
||||
}
|
||||
|
||||
if (Object.keys(nestedRelations).length > 0) {
|
||||
await this.processNestedRelations({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem: referenceObjectMetadataItemWithFieldsMaps,
|
||||
parentObjectRecords: relationResults as ObjectRecord[],
|
||||
parentObjectRecordsAggregatedValues: relationAggregatedFieldsResult,
|
||||
relations: nestedRelations as Record<
|
||||
string,
|
||||
FindOptionsRelations<ObjectLiteral>
|
||||
>,
|
||||
aggregate,
|
||||
limit,
|
||||
authContext,
|
||||
dataSource,
|
||||
isNewRelationEnabled,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
private getRelationMetadata({
|
||||
objectMetadataMaps,
|
||||
parentObjectMetadataItem,
|
||||
relationName,
|
||||
}: {
|
||||
objectMetadataMaps: ObjectMetadataMaps;
|
||||
parentObjectMetadataItem: ObjectMetadataItemWithFieldMaps;
|
||||
relationName: string;
|
||||
}) {
|
||||
const relationFieldMetadata =
|
||||
parentObjectMetadataItem.fieldsByName[relationName];
|
||||
const relationMetadata = getRelationMetadata(relationFieldMetadata);
|
||||
const referenceObjectMetadata = getRelationObjectMetadata(
|
||||
relationFieldMetadata,
|
||||
objectMetadataMaps,
|
||||
);
|
||||
const inverseRelationName =
|
||||
objectMetadataMaps.byId[relationMetadata.toObjectMetadataId]?.fieldsById[
|
||||
relationMetadata.toFieldMetadataId
|
||||
]?.name;
|
||||
|
||||
return { inverseRelationName, referenceObjectMetadata };
|
||||
}
|
||||
|
||||
private getUniqueIds({
|
||||
records,
|
||||
idField,
|
||||
}: {
|
||||
records: ObjectRecord[];
|
||||
idField: string;
|
||||
}): any[] {
|
||||
return [...new Set(records.map((item) => item[idField]))];
|
||||
}
|
||||
|
||||
private async findRelations({
|
||||
referenceQueryBuilder,
|
||||
column,
|
||||
ids,
|
||||
limit,
|
||||
objectMetadataMaps,
|
||||
referenceObjectMetadata,
|
||||
aggregate,
|
||||
relationName,
|
||||
}: {
|
||||
referenceQueryBuilder: SelectQueryBuilder<any>;
|
||||
column: string;
|
||||
ids: any[];
|
||||
limit: number;
|
||||
objectMetadataMaps: ObjectMetadataMaps;
|
||||
referenceObjectMetadata: ObjectMetadataItemWithFieldMaps;
|
||||
aggregate: Record<string, any>;
|
||||
relationName: string;
|
||||
}): Promise<{ relationResults: any[]; relationAggregatedFieldsResult: any }> {
|
||||
if (ids.length === 0) {
|
||||
return { relationResults: [], relationAggregatedFieldsResult: {} };
|
||||
}
|
||||
|
||||
const aggregateForRelation = aggregate[relationName];
|
||||
let relationAggregatedFieldsResult: Record<string, any> = {};
|
||||
|
||||
if (aggregateForRelation) {
|
||||
const aggregateQueryBuilder = referenceQueryBuilder.clone();
|
||||
|
||||
this.processAggregateHelper.addSelectedAggregatedFieldsQueriesToQueryBuilder(
|
||||
{
|
||||
selectedAggregatedFields: aggregateForRelation,
|
||||
queryBuilder: aggregateQueryBuilder,
|
||||
},
|
||||
);
|
||||
|
||||
const aggregatedFieldsValues = await aggregateQueryBuilder
|
||||
.addSelect(column)
|
||||
.where(`${column} IN (:...ids)`, {
|
||||
ids,
|
||||
})
|
||||
.groupBy(column)
|
||||
.getRawMany();
|
||||
|
||||
relationAggregatedFieldsResult = aggregatedFieldsValues.reduce(
|
||||
(acc, item) => {
|
||||
const columnWithoutQuotes = column.replace(/["']/g, '');
|
||||
const key = item[columnWithoutQuotes];
|
||||
const { [column]: _, ...itemWithoutColumn } = item;
|
||||
|
||||
acc[key] = itemWithoutColumn;
|
||||
|
||||
return acc;
|
||||
},
|
||||
{},
|
||||
);
|
||||
}
|
||||
|
||||
const result = await referenceQueryBuilder
|
||||
.where(`${column} IN (:...ids)`, {
|
||||
ids,
|
||||
})
|
||||
.take(limit)
|
||||
.getMany();
|
||||
|
||||
const relationResults = formatResult<ObjectRecord[]>(
|
||||
result,
|
||||
referenceObjectMetadata,
|
||||
objectMetadataMaps,
|
||||
false,
|
||||
);
|
||||
|
||||
return { relationResults, relationAggregatedFieldsResult };
|
||||
}
|
||||
|
||||
private assignFromRelationResults({
|
||||
parentRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationResults,
|
||||
relationAggregatedFieldsResult,
|
||||
relationName,
|
||||
joinField,
|
||||
}: {
|
||||
parentRecords: ObjectRecord[];
|
||||
parentObjectRecordsAggregatedValues: Record<string, any>;
|
||||
relationResults: any[];
|
||||
relationAggregatedFieldsResult: Record<string, any>;
|
||||
relationName: string;
|
||||
joinField: string;
|
||||
}): void {
|
||||
parentRecords.forEach((item) => {
|
||||
item[relationName] = relationResults.filter(
|
||||
(rel) => rel[joinField] === item.id,
|
||||
);
|
||||
});
|
||||
|
||||
parentObjectRecordsAggregatedValues[relationName] =
|
||||
relationAggregatedFieldsResult;
|
||||
}
|
||||
|
||||
private assignToRelationResults({
|
||||
parentRecords,
|
||||
parentObjectRecordsAggregatedValues,
|
||||
relationResults,
|
||||
relationAggregatedFieldsResult,
|
||||
relationName,
|
||||
}: {
|
||||
parentRecords: ObjectRecord[];
|
||||
parentObjectRecordsAggregatedValues: Record<string, any>;
|
||||
relationResults: any[];
|
||||
relationAggregatedFieldsResult: Record<string, any>;
|
||||
relationName: string;
|
||||
}): void {
|
||||
parentRecords.forEach((item) => {
|
||||
if (relationResults.length === 0) {
|
||||
item[`${relationName}Id`] = null;
|
||||
}
|
||||
item[relationName] =
|
||||
relationResults.find((rel) => rel.id === item[`${relationName}Id`]) ??
|
||||
null;
|
||||
});
|
||||
|
||||
parentObjectRecordsAggregatedValues[relationName] =
|
||||
relationAggregatedFieldsResult;
|
||||
}
|
||||
}
|
||||
|
||||
@ -138,7 +138,6 @@ export abstract class GraphqlQueryBaseResolverService<
|
||||
objectMetadataItemWithFieldMaps.fieldsByName,
|
||||
objectMetadataItemWithFieldMaps.fieldsByJoinColumnName,
|
||||
options.objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
|
||||
const selectedFields = graphqlFields(options.info);
|
||||
@ -170,7 +169,6 @@ export abstract class GraphqlQueryBaseResolverService<
|
||||
objectMetadataItemWithFieldMaps,
|
||||
authContext.workspace.id,
|
||||
options.objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
const resultWithGettersArray = Array.isArray(resultWithGetters)
|
||||
|
||||
@ -14,7 +14,6 @@ import { CreateManyResolverArgs } from 'src/engine/api/graphql/workspace-resolve
|
||||
import { QUERY_MAX_RECORDS } from 'src/engine/api/graphql/graphql-query-runner/constants/query-max-records.constant';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { compositeTypeDefinitions } from 'src/engine/metadata-modules/field-metadata/composite-types';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { ObjectMetadataItemWithFieldMaps } from 'src/engine/metadata-modules/types/object-metadata-item-with-field-maps';
|
||||
@ -30,7 +29,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<CreateManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -44,7 +42,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
objectRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitCreateEvents(
|
||||
@ -60,7 +57,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
upsertedRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
shouldBypassPermissionChecks,
|
||||
roleId,
|
||||
);
|
||||
@ -69,7 +65,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
upsertedRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
}
|
||||
|
||||
@ -305,7 +300,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
objectRecords: InsertResult,
|
||||
objectMetadataItemWithFieldMaps: ObjectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const queryBuilder = executionArgs.repository.createQueryBuilder(
|
||||
objectMetadataItemWithFieldMaps.nameSingular,
|
||||
@ -322,7 +316,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
nonFormattedUpsertedRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
}
|
||||
|
||||
@ -331,7 +324,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
upsertedRecords: ObjectRecord[],
|
||||
objectMetadataItemWithFieldMaps: ObjectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
shouldBypassPermissionChecks: boolean,
|
||||
roleId?: string,
|
||||
): Promise<void> {
|
||||
@ -347,8 +339,6 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext: executionArgs.options.authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks,
|
||||
});
|
||||
@ -358,13 +348,9 @@ export class GraphqlQueryCreateManyResolverService extends GraphqlQueryBaseResol
|
||||
upsertedRecords: ObjectRecord[],
|
||||
objectMetadataItemWithFieldMaps: ObjectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): ObjectRecord[] {
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return upsertedRecords.map((record: ObjectRecord) =>
|
||||
typeORMObjectRecordsParser.processRecord({
|
||||
|
||||
@ -13,7 +13,6 @@ import { CreateOneResolverArgs } from 'src/engine/api/graphql/workspace-resolver
|
||||
import { QUERY_MAX_RECORDS } from 'src/engine/api/graphql/graphql-query-runner/constants/query-max-records.constant';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@ -24,7 +23,6 @@ export class GraphqlQueryCreateOneResolverService extends GraphqlQueryBaseResolv
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<CreateOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataMaps, objectMetadataItemWithFieldMaps } =
|
||||
executionArgs.options;
|
||||
@ -53,7 +51,6 @@ export class GraphqlQueryCreateOneResolverService extends GraphqlQueryBaseResolv
|
||||
nonFormattedUpsertedRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitCreateEvents(
|
||||
@ -71,18 +68,13 @@ export class GraphqlQueryCreateOneResolverService extends GraphqlQueryBaseResolv
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: upsertedRecords[0],
|
||||
|
||||
@ -11,7 +11,6 @@ import { DeleteManyResolverArgs } from 'src/engine/api/graphql/workspace-resolve
|
||||
import { QUERY_MAX_RECORDS } from 'src/engine/api/graphql/graphql-query-runner/constants/query-max-records.constant';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
import { computeTableName } from 'src/engine/utils/compute-table-name.util';
|
||||
@ -23,7 +22,6 @@ export class GraphqlQueryDeleteManyResolverService extends GraphqlQueryBaseResol
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<DeleteManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -54,7 +52,6 @@ export class GraphqlQueryDeleteManyResolverService extends GraphqlQueryBaseResol
|
||||
nonFormattedDeletedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitDeletedEvents(
|
||||
@ -72,18 +69,13 @@ export class GraphqlQueryDeleteManyResolverService extends GraphqlQueryBaseResol
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return formattedDeletedRecords.map((record: ObjectRecord) =>
|
||||
typeORMObjectRecordsParser.processRecord({
|
||||
|
||||
@ -15,7 +15,6 @@ import {
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@ -26,7 +25,6 @@ export class GraphqlQueryDeleteOneResolverService extends GraphqlQueryBaseResolv
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<DeleteOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -47,7 +45,6 @@ export class GraphqlQueryDeleteOneResolverService extends GraphqlQueryBaseResolv
|
||||
nonFormattedDeletedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitDeletedEvents(
|
||||
@ -74,18 +71,13 @@ export class GraphqlQueryDeleteOneResolverService extends GraphqlQueryBaseResolv
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: deletedRecord,
|
||||
|
||||
@ -10,7 +10,6 @@ import { DestroyManyResolverArgs } from 'src/engine/api/graphql/workspace-resolv
|
||||
|
||||
import { QUERY_MAX_RECORDS } from 'src/engine/api/graphql/graphql-query-runner/constants/query-max-records.constant';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
import { computeTableName } from 'src/engine/utils/compute-table-name.util';
|
||||
|
||||
@ -21,7 +20,6 @@ export class GraphqlQueryDestroyManyResolverService extends GraphqlQueryBaseReso
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<DestroyManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -52,7 +50,6 @@ export class GraphqlQueryDestroyManyResolverService extends GraphqlQueryBaseReso
|
||||
nonFormattedDeletedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitDestroyEvents(
|
||||
@ -70,18 +67,13 @@ export class GraphqlQueryDestroyManyResolverService extends GraphqlQueryBaseReso
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return deletedRecords.map((record: ObjectRecord) =>
|
||||
typeORMObjectRecordsParser.processRecord({
|
||||
|
||||
@ -14,7 +14,6 @@ import {
|
||||
GraphqlQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@Injectable()
|
||||
@ -24,7 +23,6 @@ export class GraphqlQueryDestroyOneResolverService extends GraphqlQueryBaseResol
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<DestroyOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -52,7 +50,6 @@ export class GraphqlQueryDestroyOneResolverService extends GraphqlQueryBaseResol
|
||||
nonFormattedDeletedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitDestroyEvents(
|
||||
@ -70,18 +67,13 @@ export class GraphqlQueryDestroyOneResolverService extends GraphqlQueryBaseResol
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: deletedRecords[0],
|
||||
|
||||
@ -23,7 +23,6 @@ import {
|
||||
import { GraphqlQueryParser } from 'src/engine/api/graphql/graphql-query-runner/graphql-query-parsers/graphql-query.parser';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { settings } from 'src/engine/constants/settings';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { ObjectMetadataItemWithFieldMaps } from 'src/engine/metadata-modules/types/object-metadata-item-with-field-maps';
|
||||
import { getObjectMetadataMapItemByNameSingular } from 'src/engine/metadata-modules/utils/get-object-metadata-map-item-by-name-singular.util';
|
||||
import { formatData } from 'src/engine/twenty-orm/utils/format-data.util';
|
||||
@ -39,7 +38,6 @@ export class GraphqlQueryFindDuplicatesResolverService extends GraphqlQueryBaseR
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<FindDuplicatesResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<IConnection<ObjectRecord>[]> {
|
||||
const { objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -66,14 +64,10 @@ export class GraphqlQueryFindDuplicatesResolverService extends GraphqlQueryBaseR
|
||||
objectMetadataItemWithFieldsMaps?.fieldsByName,
|
||||
objectMetadataItemWithFieldsMaps?.fieldsByJoinColumnName,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
let objectRecords: Partial<ObjectRecord>[] = [];
|
||||
|
||||
@ -86,7 +80,6 @@ export class GraphqlQueryFindDuplicatesResolverService extends GraphqlQueryBaseR
|
||||
nonFormattedObjectRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
} else if (executionArgs.args.data && !isEmpty(executionArgs.args.data)) {
|
||||
objectRecords = formatData(
|
||||
@ -133,7 +126,6 @@ export class GraphqlQueryFindDuplicatesResolverService extends GraphqlQueryBaseR
|
||||
nonFormattedDuplicates,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
return typeORMObjectRecordsParser.createConnection({
|
||||
|
||||
@ -28,7 +28,6 @@ import {
|
||||
getCursor,
|
||||
getPaginationInfo,
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/utils/cursors.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@Injectable()
|
||||
@ -42,7 +41,6 @@ export class GraphqlQueryFindManyResolverService extends GraphqlQueryBaseResolve
|
||||
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<FindManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<IConnection<ObjectRecord>> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -130,7 +128,6 @@ export class GraphqlQueryFindManyResolverService extends GraphqlQueryBaseResolve
|
||||
nonFormattedObjectRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
const { hasNextPage, hasPreviousPage } = getPaginationInfo(
|
||||
@ -157,18 +154,13 @@ export class GraphqlQueryFindManyResolverService extends GraphqlQueryBaseResolve
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.createConnection({
|
||||
objectRecords,
|
||||
|
||||
@ -21,7 +21,6 @@ import {
|
||||
WorkspaceQueryRunnerException,
|
||||
WorkspaceQueryRunnerExceptionCode,
|
||||
} from 'src/engine/api/graphql/workspace-query-runner/workspace-query-runner.exception';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@Injectable()
|
||||
@ -31,7 +30,6 @@ export class GraphqlQueryFindOneResolverService extends GraphqlQueryBaseResolver
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<FindOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -59,7 +57,6 @@ export class GraphqlQueryFindOneResolverService extends GraphqlQueryBaseResolver
|
||||
nonFormattedObjectRecord,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
if (!objectRecord) {
|
||||
@ -80,18 +77,13 @@ export class GraphqlQueryFindOneResolverService extends GraphqlQueryBaseResolver
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: objectRecords[0],
|
||||
|
||||
@ -11,7 +11,6 @@ import { RestoreManyResolverArgs } from 'src/engine/api/graphql/workspace-resolv
|
||||
import { QUERY_MAX_RECORDS } from 'src/engine/api/graphql/graphql-query-runner/constants/query-max-records.constant';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
import { computeTableName } from 'src/engine/utils/compute-table-name.util';
|
||||
@ -23,7 +22,6 @@ export class GraphqlQueryRestoreManyResolverService extends GraphqlQueryBaseReso
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<RestoreManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -54,7 +52,6 @@ export class GraphqlQueryRestoreManyResolverService extends GraphqlQueryBaseReso
|
||||
nonFormattedRestoredObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitRestoreEvents(
|
||||
@ -72,18 +69,13 @@ export class GraphqlQueryRestoreManyResolverService extends GraphqlQueryBaseReso
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return formattedRestoredRecords.map((record: ObjectRecord) =>
|
||||
typeORMObjectRecordsParser.processRecord({
|
||||
|
||||
@ -15,7 +15,6 @@ import {
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
|
||||
@ -26,7 +25,6 @@ export class GraphqlQueryRestoreOneResolverService extends GraphqlQueryBaseResol
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<RestoreOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -47,7 +45,6 @@ export class GraphqlQueryRestoreOneResolverService extends GraphqlQueryBaseResol
|
||||
nonFormattedRestoredObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitRestoreEvents(
|
||||
@ -74,18 +71,13 @@ export class GraphqlQueryRestoreOneResolverService extends GraphqlQueryBaseResol
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: restoredRecord,
|
||||
|
||||
@ -17,7 +17,6 @@ import {
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatData } from 'src/engine/twenty-orm/utils/format-data.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
@ -30,7 +29,6 @@ export class GraphqlQueryUpdateManyResolverService extends GraphqlQueryBaseResol
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<UpdateManyResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord[]> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -55,7 +53,6 @@ export class GraphqlQueryUpdateManyResolverService extends GraphqlQueryBaseResol
|
||||
existingRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
if (isEmpty(formattedExistingRecords)) {
|
||||
@ -90,7 +87,6 @@ export class GraphqlQueryUpdateManyResolverService extends GraphqlQueryBaseResol
|
||||
nonFormattedUpdatedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitUpdateEvents(
|
||||
@ -110,18 +106,13 @@ export class GraphqlQueryUpdateManyResolverService extends GraphqlQueryBaseResol
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return formattedUpdatedRecords.map((record: ObjectRecord) =>
|
||||
typeORMObjectRecordsParser.processRecord({
|
||||
|
||||
@ -17,7 +17,6 @@ import {
|
||||
} from 'src/engine/api/graphql/graphql-query-runner/errors/graphql-query-runner.exception';
|
||||
import { ObjectRecordsToGraphqlConnectionHelper } from 'src/engine/api/graphql/graphql-query-runner/helpers/object-records-to-graphql-connection.helper';
|
||||
import { assertIsValidUuid } from 'src/engine/api/graphql/workspace-query-runner/utils/assert-is-valid-uuid.util';
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { assertMutationNotOnRemoteObject } from 'src/engine/metadata-modules/object-metadata/utils/assert-mutation-not-on-remote-object.util';
|
||||
import { formatData } from 'src/engine/twenty-orm/utils/format-data.util';
|
||||
import { formatResult } from 'src/engine/twenty-orm/utils/format-result.util';
|
||||
@ -29,7 +28,6 @@ export class GraphqlQueryUpdateOneResolverService extends GraphqlQueryBaseResolv
|
||||
> {
|
||||
async resolve(
|
||||
executionArgs: GraphqlQueryResolverExecutionArgs<UpdateOneResolverArgs>,
|
||||
featureFlagsMap: Record<FeatureFlagKey, boolean>,
|
||||
): Promise<ObjectRecord> {
|
||||
const { authContext, objectMetadataItemWithFieldMaps, objectMetadataMaps } =
|
||||
executionArgs.options;
|
||||
@ -55,7 +53,6 @@ export class GraphqlQueryUpdateOneResolverService extends GraphqlQueryBaseResolv
|
||||
existingRecords,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
if (isEmpty(formattedExistingRecords)) {
|
||||
@ -75,7 +72,6 @@ export class GraphqlQueryUpdateOneResolverService extends GraphqlQueryBaseResolv
|
||||
nonFormattedUpdatedObjectRecords.raw,
|
||||
objectMetadataItemWithFieldMaps,
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
);
|
||||
|
||||
this.apiEventEmitterService.emitUpdateEvents(
|
||||
@ -104,18 +100,13 @@ export class GraphqlQueryUpdateOneResolverService extends GraphqlQueryBaseResolv
|
||||
limit: QUERY_MAX_RECORDS,
|
||||
authContext,
|
||||
dataSource: executionArgs.dataSource,
|
||||
isNewRelationEnabled:
|
||||
featureFlagsMap[FeatureFlagKey.IsNewRelationEnabled],
|
||||
roleId,
|
||||
shouldBypassPermissionChecks: executionArgs.isExecutedByApiKey,
|
||||
});
|
||||
}
|
||||
|
||||
const typeORMObjectRecordsParser =
|
||||
new ObjectRecordsToGraphqlConnectionHelper(
|
||||
objectMetadataMaps,
|
||||
featureFlagsMap,
|
||||
);
|
||||
new ObjectRecordsToGraphqlConnectionHelper(objectMetadataMaps);
|
||||
|
||||
return typeORMObjectRecordsParser.processRecord({
|
||||
objectRecord: updatedRecord,
|
||||
|
||||
@ -1,48 +0,0 @@
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
|
||||
import { RelationMetadataEntity } from 'src/engine/metadata-modules/relation-metadata/relation-metadata.entity';
|
||||
import { ObjectMetadataMaps } from 'src/engine/metadata-modules/types/object-metadata-maps';
|
||||
import {
|
||||
deduceRelationDirection,
|
||||
RelationDirection,
|
||||
} from 'src/engine/utils/deduce-relation-direction.util';
|
||||
|
||||
export const getRelationObjectMetadata = (
|
||||
fieldMetadata: FieldMetadataInterface,
|
||||
objectMetadataMaps: ObjectMetadataMaps,
|
||||
) => {
|
||||
const relationMetadata = getRelationMetadata(fieldMetadata);
|
||||
|
||||
const relationDirection = deduceRelationDirection(
|
||||
fieldMetadata,
|
||||
relationMetadata,
|
||||
);
|
||||
|
||||
const referencedObjectMetadata =
|
||||
relationDirection === RelationDirection.TO
|
||||
? objectMetadataMaps.byId[relationMetadata.fromObjectMetadataId]
|
||||
: objectMetadataMaps.byId[relationMetadata.toObjectMetadataId];
|
||||
|
||||
if (!referencedObjectMetadata) {
|
||||
throw new Error(
|
||||
`Referenced object metadata not found for relation ${relationMetadata.id}`,
|
||||
);
|
||||
}
|
||||
|
||||
return referencedObjectMetadata;
|
||||
};
|
||||
|
||||
export const getRelationMetadata = (
|
||||
fieldMetadata: FieldMetadataInterface,
|
||||
): RelationMetadataEntity => {
|
||||
const relationMetadata =
|
||||
fieldMetadata.fromRelationMetadata ?? fieldMetadata.toRelationMetadata;
|
||||
|
||||
if (!relationMetadata) {
|
||||
throw new Error(
|
||||
`Relation metadata not found for field ${fieldMetadata.name}`,
|
||||
);
|
||||
}
|
||||
|
||||
return relationMetadata;
|
||||
};
|
||||
Reference in New Issue
Block a user