Optimize metadata queries (#7013)
In this PR: 1. Refactor guards to avoid duplicated queries: WorkspaceAuthGuard and UserAuthGuard only check for existence of workspace and user in the request without querying the database
This commit is contained in:
committed by
Charles Bochet
parent
cf8b1161cc
commit
523df5398a
@ -2,15 +2,15 @@ import { Injectable } from '@nestjs/common';
|
||||
|
||||
import { ColumnType, EntitySchemaColumnOptions } from 'typeorm';
|
||||
|
||||
import { FieldMetadataInterface } from 'src/engine/metadata-modules/field-metadata/interfaces/field-metadata.interface';
|
||||
|
||||
import { compositeTypeDefinitions } from 'src/engine/metadata-modules/field-metadata/composite-types';
|
||||
import {
|
||||
FieldMetadataEntity,
|
||||
FieldMetadataType,
|
||||
} from 'src/engine/metadata-modules/field-metadata/field-metadata.entity';
|
||||
import { FieldMetadataType } from 'src/engine/metadata-modules/field-metadata/field-metadata.entity';
|
||||
import { computeCompositeColumnName } from 'src/engine/metadata-modules/field-metadata/utils/compute-column-name.util';
|
||||
import { isCompositeFieldMetadataType } from 'src/engine/metadata-modules/field-metadata/utils/is-composite-field-metadata-type.util';
|
||||
import { isEnumFieldMetadataType } from 'src/engine/metadata-modules/field-metadata/utils/is-enum-field-metadata-type.util';
|
||||
import { serializeDefaultValue } from 'src/engine/metadata-modules/field-metadata/utils/serialize-default-value';
|
||||
import { FieldMetadataMap } from 'src/engine/metadata-modules/utils/generate-object-metadata-map.util';
|
||||
import { fieldMetadataTypeToColumnType } from 'src/engine/metadata-modules/workspace-migration/utils/field-metadata-type-to-column-type.util';
|
||||
import { isRelationFieldMetadataType } from 'src/engine/utils/is-relation-field-metadata-type.util';
|
||||
|
||||
@ -21,11 +21,13 @@ type EntitySchemaColumnMap = {
|
||||
@Injectable()
|
||||
export class EntitySchemaColumnFactory {
|
||||
create(
|
||||
fieldMetadataCollection: FieldMetadataEntity[],
|
||||
fieldMetadataMap: FieldMetadataMap,
|
||||
softDelete: boolean,
|
||||
): EntitySchemaColumnMap {
|
||||
let entitySchemaColumnMap: EntitySchemaColumnMap = {};
|
||||
|
||||
const fieldMetadataCollection = Object.values(fieldMetadataMap);
|
||||
|
||||
for (const fieldMetadata of fieldMetadataCollection) {
|
||||
const key = fieldMetadata.name;
|
||||
|
||||
@ -102,7 +104,7 @@ export class EntitySchemaColumnFactory {
|
||||
}
|
||||
|
||||
private createCompositeColumns(
|
||||
fieldMetadata: FieldMetadataEntity,
|
||||
fieldMetadata: FieldMetadataInterface,
|
||||
): EntitySchemaColumnMap {
|
||||
const entitySchemaColumnMap: EntitySchemaColumnMap = {};
|
||||
const compositeType = compositeTypeDefinitions.get(fieldMetadata.type);
|
||||
|
||||
@ -2,10 +2,12 @@ import { Injectable } from '@nestjs/common';
|
||||
|
||||
import { EntitySchemaRelationOptions } from 'typeorm';
|
||||
|
||||
import { FieldMetadataEntity } from 'src/engine/metadata-modules/field-metadata/field-metadata.entity';
|
||||
import {
|
||||
FieldMetadataMap,
|
||||
ObjectMetadataMap,
|
||||
} from 'src/engine/metadata-modules/utils/generate-object-metadata-map.util';
|
||||
import { determineRelationDetails } from 'src/engine/twenty-orm/utils/determine-relation-details.util';
|
||||
import { isRelationFieldMetadataType } from 'src/engine/utils/is-relation-field-metadata-type.util';
|
||||
import { WorkspaceCacheStorageService } from 'src/engine/workspace-cache-storage/workspace-cache-storage.service';
|
||||
|
||||
type EntitySchemaRelationMap = {
|
||||
[key: string]: EntitySchemaRelationOptions;
|
||||
@ -13,17 +15,16 @@ type EntitySchemaRelationMap = {
|
||||
|
||||
@Injectable()
|
||||
export class EntitySchemaRelationFactory {
|
||||
constructor(
|
||||
private readonly workspaceCacheStorageService: WorkspaceCacheStorageService,
|
||||
) {}
|
||||
constructor() {}
|
||||
|
||||
async create(
|
||||
workspaceId: string,
|
||||
metadataVersion: number,
|
||||
fieldMetadataCollection: FieldMetadataEntity[],
|
||||
fieldMetadataMap: FieldMetadataMap,
|
||||
objectMetadataMap: ObjectMetadataMap,
|
||||
): Promise<EntitySchemaRelationMap> {
|
||||
const entitySchemaRelationMap: EntitySchemaRelationMap = {};
|
||||
|
||||
const fieldMetadataCollection = Object.values(fieldMetadataMap);
|
||||
|
||||
for (const fieldMetadata of fieldMetadataCollection) {
|
||||
if (!isRelationFieldMetadataType(fieldMetadata.type)) {
|
||||
continue;
|
||||
@ -38,20 +39,10 @@ export class EntitySchemaRelationFactory {
|
||||
);
|
||||
}
|
||||
|
||||
const objectMetadataCollection =
|
||||
await this.workspaceCacheStorageService.getObjectMetadataCollection(
|
||||
workspaceId,
|
||||
metadataVersion,
|
||||
);
|
||||
|
||||
if (!objectMetadataCollection) {
|
||||
throw new Error('Object metadata collection not found');
|
||||
}
|
||||
|
||||
const relationDetails = await determineRelationDetails(
|
||||
fieldMetadata,
|
||||
relationMetadata,
|
||||
objectMetadataCollection,
|
||||
objectMetadataMap,
|
||||
);
|
||||
|
||||
entitySchemaRelationMap[fieldMetadata.name] = {
|
||||
|
||||
@ -2,7 +2,10 @@ import { Injectable } from '@nestjs/common';
|
||||
|
||||
import { EntitySchema } from 'typeorm';
|
||||
|
||||
import { ObjectMetadataEntity } from 'src/engine/metadata-modules/object-metadata/object-metadata.entity';
|
||||
import {
|
||||
ObjectMetadataMap,
|
||||
ObjectMetadataMapItem,
|
||||
} from 'src/engine/metadata-modules/utils/generate-object-metadata-map.util';
|
||||
import { EntitySchemaColumnFactory } from 'src/engine/twenty-orm/factories/entity-schema-column.factory';
|
||||
import { EntitySchemaRelationFactory } from 'src/engine/twenty-orm/factories/entity-schema-relation.factory';
|
||||
import { WorkspaceEntitiesStorage } from 'src/engine/twenty-orm/storage/workspace-entities.storage';
|
||||
@ -18,7 +21,8 @@ export class EntitySchemaFactory {
|
||||
async create(
|
||||
workspaceId: string,
|
||||
metadataVersion: number,
|
||||
objectMetadata: ObjectMetadataEntity,
|
||||
objectMetadata: ObjectMetadataMapItem,
|
||||
objectMetadataMap: ObjectMetadataMap,
|
||||
): Promise<EntitySchema> {
|
||||
const columns = this.entitySchemaColumnFactory.create(
|
||||
objectMetadata.fields,
|
||||
@ -26,9 +30,8 @@ export class EntitySchemaFactory {
|
||||
);
|
||||
|
||||
const relations = await this.entitySchemaRelationFactory.create(
|
||||
workspaceId,
|
||||
metadataVersion,
|
||||
objectMetadata.fields,
|
||||
objectMetadataMap,
|
||||
);
|
||||
|
||||
const entitySchema = new EntitySchema({
|
||||
|
||||
@ -56,20 +56,20 @@ export class WorkspaceDatasourceFactory {
|
||||
const workspaceDataSource = await this.cacheManager.execute(
|
||||
`${workspaceId}-${desiredWorkspaceMetadataVersion}`,
|
||||
async () => {
|
||||
const cachedObjectMetadataCollection =
|
||||
await this.workspaceCacheStorageService.getObjectMetadataCollection(
|
||||
const cachedObjectMetadataMap =
|
||||
await this.workspaceCacheStorageService.getObjectMetadataMap(
|
||||
workspaceId,
|
||||
desiredWorkspaceMetadataVersion,
|
||||
);
|
||||
|
||||
if (!cachedObjectMetadataCollection) {
|
||||
if (!cachedObjectMetadataMap) {
|
||||
await this.workspaceMetadataCacheService.recomputeMetadataCache(
|
||||
workspaceId,
|
||||
true,
|
||||
);
|
||||
|
||||
throw new TwentyORMException(
|
||||
`Object metadata collection not found for workspace ${workspaceId}`,
|
||||
`Object metadata map not found for workspace ${workspaceId}`,
|
||||
TwentyORMExceptionCode.METADATA_COLLECTION_NOT_FOUND,
|
||||
);
|
||||
}
|
||||
@ -100,11 +100,12 @@ export class WorkspaceDatasourceFactory {
|
||||
);
|
||||
} else {
|
||||
const entitySchemas = await Promise.all(
|
||||
cachedObjectMetadataCollection.map((objectMetadata) =>
|
||||
Object.values(cachedObjectMetadataMap).map((objectMetadata) =>
|
||||
this.entitySchemaFactory.create(
|
||||
workspaceId,
|
||||
desiredWorkspaceMetadataVersion,
|
||||
objectMetadata,
|
||||
cachedObjectMetadataMap,
|
||||
),
|
||||
),
|
||||
);
|
||||
@ -121,7 +122,7 @@ export class WorkspaceDatasourceFactory {
|
||||
const workspaceDataSource = new WorkspaceDataSource(
|
||||
{
|
||||
workspaceId,
|
||||
objectMetadataCollection: cachedObjectMetadataCollection,
|
||||
objectMetadataMap: cachedObjectMetadataMap,
|
||||
},
|
||||
{
|
||||
url:
|
||||
|
||||
Reference in New Issue
Block a user