Migrate page layout to v2 (#16364)

This commit is contained in:
Raphaël Bosi
2025-12-08 15:11:24 +01:00
committed by GitHub
parent 86df188e83
commit 5fb7e76005
65 changed files with 1474 additions and 84 deletions
@@ -31,6 +31,7 @@ export const fromWorkspaceMigrationBuilderExceptionToMetadataValidationResponseE
invalidViewGroup: 0,
invalidRole: 0,
invalidRoleTarget: 0,
invalidPageLayout: 0,
invalidPageLayoutWidget: 0,
totalErrors: 0,
invalidPageLayoutTab: 0,
@@ -21,6 +21,8 @@ import { WorkspaceMigrationV2FieldActionsBuilderService } from 'src/engine/works
import { WorkspaceMigrationV2IndexActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/index/workspace-migration-v2-index-actions-builder.service';
import { WorkspaceMigrationV2ObjectActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/object/workspace-migration-v2-object-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutTabActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout-tab/workspace-migration-v2-page-layout-tab-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutWidgetActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout-widget/workspace-migration-v2-page-layout-widget-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/workspace-migration-v2-page-layout-actions-builder.service';
import { WorkspaceMigrationV2RoleTargetActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/role-target/workspace-migration-v2-role-target-actions-builder.service';
import { WorkspaceMigrationV2RoleActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/role/workspace-migration-v2-role-actions-builder.service';
import { WorkspaceMigrationV2RouteTriggerActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/route-trigger/workspace-migration-v2-route-trigger-actions-builder.service';
@@ -47,6 +49,8 @@ export class WorkspaceMigrationBuildOrchestratorService {
private readonly workspaceMigrationV2FieldActionsBuilderService: WorkspaceMigrationV2FieldActionsBuilderService,
private readonly workspaceMigrationV2RoleActionsBuilderService: WorkspaceMigrationV2RoleActionsBuilderService,
private readonly workspaceMigrationV2AgentActionsBuilderService: WorkspaceMigrationV2AgentActionsBuilderService,
private readonly workspaceMigrationV2PageLayoutActionsBuilderService: WorkspaceMigrationV2PageLayoutActionsBuilderService,
private readonly workspaceMigrationV2PageLayoutWidgetActionsBuilderService: WorkspaceMigrationV2PageLayoutWidgetActionsBuilderService,
private readonly workspaceMigrationV2PageLayoutTabActionsBuilderService: WorkspaceMigrationV2PageLayoutTabActionsBuilderService,
) {}
@@ -139,6 +143,8 @@ export class WorkspaceMigrationBuildOrchestratorService {
flatRoleMaps,
flatRoleTargetMaps,
flatAgentMaps,
flatPageLayoutMaps,
flatPageLayoutWidgetMaps,
flatPageLayoutTabMaps,
} = fromToAllFlatEntityMaps;
@@ -614,6 +620,74 @@ export class WorkspaceMigrationBuildOrchestratorService {
}
}
if (isDefined(flatPageLayoutMaps)) {
const { from: fromFlatPageLayoutMaps, to: toFlatPageLayoutMaps } =
flatPageLayoutMaps;
const pageLayoutResult =
this.workspaceMigrationV2PageLayoutActionsBuilderService.validateAndBuild(
{
from: fromFlatPageLayoutMaps,
to: toFlatPageLayoutMaps,
buildOptions,
dependencyOptimisticFlatEntityMaps: undefined,
workspaceId,
},
);
this.mergeFlatEntityMapsAndRelatedFlatEntityMapsInAllFlatEntityMapsThroughMutation(
{
allFlatEntityMaps: optimisticAllFlatEntityMaps,
flatEntityMapsAndRelatedFlatEntityMaps:
pageLayoutResult.optimisticFlatEntityMapsAndRelatedFlatEntityMaps,
},
);
if (pageLayoutResult.status === 'fail') {
orchestratorFailureReport.pageLayout.push(...pageLayoutResult.errors);
} else {
orchestratorActionsReport.pageLayout = pageLayoutResult.actions;
}
}
if (isDefined(flatPageLayoutWidgetMaps)) {
const {
from: fromFlatPageLayoutWidgetMaps,
to: toFlatPageLayoutWidgetMaps,
} = flatPageLayoutWidgetMaps;
const pageLayoutWidgetResult =
this.workspaceMigrationV2PageLayoutWidgetActionsBuilderService.validateAndBuild(
{
from: fromFlatPageLayoutWidgetMaps,
to: toFlatPageLayoutWidgetMaps,
buildOptions,
dependencyOptimisticFlatEntityMaps: {
flatPageLayoutTabMaps:
optimisticAllFlatEntityMaps.flatPageLayoutTabMaps,
},
workspaceId,
},
);
this.mergeFlatEntityMapsAndRelatedFlatEntityMapsInAllFlatEntityMapsThroughMutation(
{
allFlatEntityMaps: optimisticAllFlatEntityMaps,
flatEntityMapsAndRelatedFlatEntityMaps:
pageLayoutWidgetResult.optimisticFlatEntityMapsAndRelatedFlatEntityMaps,
},
);
if (pageLayoutWidgetResult.status === 'fail') {
orchestratorFailureReport.pageLayoutWidget.push(
...pageLayoutWidgetResult.errors,
);
} else {
orchestratorActionsReport.pageLayoutWidget =
pageLayoutWidgetResult.actions;
}
}
if (isDefined(flatPageLayoutTabMaps)) {
const { from: fromFlatPageLayoutTabMaps, to: toFlatPageLayoutTabMaps } =
flatPageLayoutTabMaps;
@@ -624,7 +698,10 @@ export class WorkspaceMigrationBuildOrchestratorService {
from: fromFlatPageLayoutTabMaps,
to: toFlatPageLayoutTabMaps,
buildOptions,
dependencyOptimisticFlatEntityMaps: undefined,
dependencyOptimisticFlatEntityMaps: {
flatPageLayoutMaps:
optimisticAllFlatEntityMaps.flatPageLayoutMaps,
},
workspaceId,
},
);
@@ -735,12 +812,24 @@ export class WorkspaceMigrationBuildOrchestratorService {
...aggregatedOrchestratorActionsReport.roleTarget.updated,
///
//
// Agents
...aggregatedOrchestratorActionsReport.agent.deleted,
...aggregatedOrchestratorActionsReport.agent.created,
...aggregatedOrchestratorActionsReport.agent.updated,
///
// Page layouts
...aggregatedOrchestratorActionsReport.pageLayout.deleted,
...aggregatedOrchestratorActionsReport.pageLayout.created,
...aggregatedOrchestratorActionsReport.pageLayout.updated,
///
// Page layout widgets
...aggregatedOrchestratorActionsReport.pageLayoutWidget.deleted,
...aggregatedOrchestratorActionsReport.pageLayoutWidget.created,
...aggregatedOrchestratorActionsReport.pageLayoutWidget.updated,
///
// Page layout tabs
...aggregatedOrchestratorActionsReport.pageLayoutTab.deleted,
...aggregatedOrchestratorActionsReport.pageLayoutTab.created,
@@ -0,0 +1,18 @@
import { type FlatPageLayout } from 'src/engine/metadata-modules/flat-page-layout/types/flat-page-layout.type';
import { type FlatEntityPropertiesUpdates } from 'src/engine/metadata-modules/flat-entity/types/flat-entity-properties-updates.type';
export type UpdatePageLayoutAction = {
type: 'update_page_layout';
flatEntityId: string;
flatEntityUpdates: FlatEntityPropertiesUpdates<'pageLayout'>;
};
export type CreatePageLayoutAction = {
type: 'create_page_layout';
flatEntity: FlatPageLayout;
};
export type DeletePageLayoutAction = {
type: 'delete_page_layout';
flatEntityId: string;
};
@@ -0,0 +1,105 @@
import { Injectable } from '@nestjs/common';
import { ALL_METADATA_NAME } from 'twenty-shared/metadata';
import { UpdatePageLayoutAction } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/types/workspace-migration-page-layout-action-v2.type';
import { WorkspaceEntityMigrationBuilderV2Service } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/services/workspace-entity-migration-builder-v2.service';
import { FlatEntityUpdateValidationArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/types/flat-entity-update-validation-args.type';
import { FlatEntityValidationArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/types/flat-entity-validation-args.type';
import { FlatEntityValidationReturnType } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/types/flat-entity-validation-result.type';
import { FlatPageLayoutValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-page-layout-validator.service';
@Injectable()
export class WorkspaceMigrationV2PageLayoutActionsBuilderService extends WorkspaceEntityMigrationBuilderV2Service<
typeof ALL_METADATA_NAME.pageLayout
> {
constructor(
private readonly flatPageLayoutValidatorService: FlatPageLayoutValidatorService,
) {
super(ALL_METADATA_NAME.pageLayout);
}
protected validateFlatEntityCreation(
args: FlatEntityValidationArgs<typeof ALL_METADATA_NAME.pageLayout>,
): FlatEntityValidationReturnType<
typeof ALL_METADATA_NAME.pageLayout,
'created'
> {
const validationResult =
this.flatPageLayoutValidatorService.validateFlatPageLayoutCreation(args);
if (validationResult.errors.length > 0) {
return {
status: 'fail',
...validationResult,
};
}
const { flatEntityToValidate: flatPageLayoutToValidate } = args;
return {
status: 'success',
action: {
type: 'create_page_layout',
flatEntity: flatPageLayoutToValidate,
},
};
}
protected validateFlatEntityDeletion(
args: FlatEntityValidationArgs<typeof ALL_METADATA_NAME.pageLayout>,
): FlatEntityValidationReturnType<
typeof ALL_METADATA_NAME.pageLayout,
'deleted'
> {
const validationResult =
this.flatPageLayoutValidatorService.validateFlatPageLayoutDeletion(args);
if (validationResult.errors.length > 0) {
return {
status: 'fail',
...validationResult,
};
}
const { flatEntityToValidate: flatPageLayoutToValidate } = args;
return {
status: 'success',
action: {
type: 'delete_page_layout',
flatEntityId: flatPageLayoutToValidate.id,
},
};
}
protected validateFlatEntityUpdate(
args: FlatEntityUpdateValidationArgs<typeof ALL_METADATA_NAME.pageLayout>,
): FlatEntityValidationReturnType<
typeof ALL_METADATA_NAME.pageLayout,
'updated'
> {
const validationResult =
this.flatPageLayoutValidatorService.validateFlatPageLayoutUpdate(args);
if (validationResult.errors.length > 0) {
return {
status: 'fail',
...validationResult,
};
}
const { flatEntityId, flatEntityUpdates } = args;
const updatePageLayoutAction: UpdatePageLayoutAction = {
type: 'update_page_layout',
flatEntityId,
flatEntityUpdates,
};
return {
status: 'success',
action: updatePageLayoutAction,
};
}
}
@@ -0,0 +1,104 @@
import { Injectable } from '@nestjs/common';
import { msg, t } from '@lingui/core/macro';
import { type ALL_METADATA_NAME } from 'twenty-shared/metadata';
import { isDefined } from 'twenty-shared/utils';
import { type FlatPageLayout } from 'src/engine/metadata-modules/flat-page-layout/types/flat-page-layout.type';
import { findFlatEntityByIdInFlatEntityMaps } from 'src/engine/metadata-modules/flat-entity/utils/find-flat-entity-by-id-in-flat-entity-maps.util';
import { type FailedFlatEntityValidation } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/types/failed-flat-entity-validation.type';
import { type FlatEntityUpdateValidationArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/types/flat-entity-update-validation-args.type';
import { type FlatEntityValidationArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/types/flat-entity-validation-args.type';
const PAGE_LAYOUT_EXCEPTION_CODE = {
PAGE_LAYOUT_NOT_FOUND: 'PAGE_LAYOUT_NOT_FOUND',
} as const;
@Injectable()
export class FlatPageLayoutValidatorService {
public validateFlatPageLayoutCreation({
flatEntityToValidate: flatPageLayout,
}: FlatEntityValidationArgs<
typeof ALL_METADATA_NAME.pageLayout
>): FailedFlatEntityValidation<FlatPageLayout> {
const validationResult: FailedFlatEntityValidation<FlatPageLayout> = {
type: 'create_page_layout',
errors: [],
flatEntityMinimalInformation: {
id: flatPageLayout.id,
name: flatPageLayout.name,
},
};
return validationResult;
}
public validateFlatPageLayoutDeletion({
flatEntityToValidate,
optimisticFlatEntityMapsAndRelatedFlatEntityMaps: {
flatPageLayoutMaps: optimisticFlatPageLayoutMaps,
},
}: FlatEntityValidationArgs<
typeof ALL_METADATA_NAME.pageLayout
>): FailedFlatEntityValidation<FlatPageLayout> {
const validationResult: FailedFlatEntityValidation<FlatPageLayout> = {
type: 'delete_page_layout',
errors: [],
flatEntityMinimalInformation: {
id: flatEntityToValidate.id,
name: flatEntityToValidate.name,
},
};
const existingPageLayout = findFlatEntityByIdInFlatEntityMaps({
flatEntityId: flatEntityToValidate.id,
flatEntityMaps: optimisticFlatPageLayoutMaps,
});
if (!isDefined(existingPageLayout)) {
validationResult.errors.push({
code: PAGE_LAYOUT_EXCEPTION_CODE.PAGE_LAYOUT_NOT_FOUND,
message: t`Page layout not found`,
userFriendlyMessage: msg`Page layout not found`,
});
return validationResult;
}
return validationResult;
}
public validateFlatPageLayoutUpdate({
flatEntityId,
optimisticFlatEntityMapsAndRelatedFlatEntityMaps: {
flatPageLayoutMaps: optimisticFlatPageLayoutMaps,
},
}: FlatEntityUpdateValidationArgs<
typeof ALL_METADATA_NAME.pageLayout
>): FailedFlatEntityValidation<FlatPageLayout> {
const validationResult: FailedFlatEntityValidation<FlatPageLayout> = {
type: 'update_page_layout',
errors: [],
flatEntityMinimalInformation: {
id: flatEntityId,
},
};
const fromFlatPageLayout = findFlatEntityByIdInFlatEntityMaps({
flatEntityId,
flatEntityMaps: optimisticFlatPageLayoutMaps,
});
if (!isDefined(fromFlatPageLayout)) {
validationResult.errors.push({
code: PAGE_LAYOUT_EXCEPTION_CODE.PAGE_LAYOUT_NOT_FOUND,
message: t`Page layout not found`,
userFriendlyMessage: msg`Page layout not found`,
});
return validationResult;
}
return validationResult;
}
}
@@ -3,6 +3,7 @@ import { Module } from '@nestjs/common';
import { FeatureFlagModule } from 'src/engine/core-modules/feature-flag/feature-flag.module';
import { FlatFieldMetadataTypeValidatorService } from 'src/engine/metadata-modules/flat-field-metadata/services/flat-field-metadata-type-validator.service';
import { FlatAgentValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-agent-validator.service';
import { FlatPageLayoutValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-page-layout-validator.service';
import { FlatCronTriggerValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-cron-trigger-validator.service';
import { FlatDatabaseEventTriggerValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-database-event-trigger-validator.service';
import { FlatFieldMetadataValidatorService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/validators/services/flat-field-metadata-validator.service';
@@ -37,6 +38,7 @@ import { FlatViewValidatorService } from 'src/engine/workspace-manager/workspace
FlatRoleValidatorService,
FlatRoleTargetValidatorService,
FlatAgentValidatorService,
FlatPageLayoutValidatorService,
FlatPageLayoutWidgetValidatorService,
FlatPageLayoutTabValidatorService,
],
@@ -56,6 +58,7 @@ import { FlatViewValidatorService } from 'src/engine/workspace-manager/workspace
FlatRoleValidatorService,
FlatRoleTargetValidatorService,
FlatAgentValidatorService,
FlatPageLayoutValidatorService,
FlatPageLayoutWidgetValidatorService,
FlatPageLayoutTabValidatorService,
],
@@ -8,6 +8,7 @@ import { WorkspaceMigrationV2DatabaseEventTriggerActionsBuilderService } from 's
import { WorkspaceMigrationV2FieldActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/field/workspace-migration-v2-field-actions-builder.service';
import { WorkspaceMigrationV2IndexActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/index/workspace-migration-v2-index-actions-builder.service';
import { WorkspaceMigrationV2ObjectActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/object/workspace-migration-v2-object-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/workspace-migration-v2-page-layout-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutTabActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout-tab/workspace-migration-v2-page-layout-tab-actions-builder.service';
import { WorkspaceMigrationV2PageLayoutWidgetActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout-widget/workspace-migration-v2-page-layout-widget-actions-builder.service';
import { WorkspaceMigrationV2RoleTargetActionsBuilderService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/role-target/workspace-migration-v2-role-target-actions-builder.service';
@@ -38,6 +39,7 @@ import { WorkspaceMigrationBuilderValidatorsModule } from 'src/engine/workspace-
WorkspaceMigrationV2RoleActionsBuilderService,
WorkspaceMigrationV2RoleTargetActionsBuilderService,
WorkspaceMigrationV2AgentActionsBuilderService,
WorkspaceMigrationV2PageLayoutActionsBuilderService,
WorkspaceMigrationV2PageLayoutWidgetActionsBuilderService,
WorkspaceMigrationV2PageLayoutTabActionsBuilderService,
],
@@ -56,6 +58,7 @@ import { WorkspaceMigrationBuilderValidatorsModule } from 'src/engine/workspace-
WorkspaceMigrationV2RoleActionsBuilderService,
WorkspaceMigrationV2RoleTargetActionsBuilderService,
WorkspaceMigrationV2AgentActionsBuilderService,
WorkspaceMigrationV2PageLayoutActionsBuilderService,
WorkspaceMigrationV2PageLayoutWidgetActionsBuilderService,
WorkspaceMigrationV2PageLayoutTabActionsBuilderService,
FlatFieldMetadataTypeValidatorService,
@@ -0,0 +1,59 @@
import { Injectable } from '@nestjs/common';
import {
OptimisticallyApplyActionOnAllFlatEntityMapsArgs,
WorkspaceMigrationRunnerActionHandler,
} from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/interfaces/workspace-migration-runner-action-handler-service.interface';
import { AllFlatEntityMaps } from 'src/engine/metadata-modules/flat-entity/types/all-flat-entity-maps.type';
import { addFlatEntityToFlatEntityMapsOrThrow } from 'src/engine/metadata-modules/flat-entity/utils/add-flat-entity-to-flat-entity-maps-or-throw.util';
import { PageLayoutEntity } from 'src/engine/metadata-modules/page-layout/entities/page-layout.entity';
import { CreatePageLayoutAction } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/types/workspace-migration-page-layout-action-v2.type';
import { WorkspaceMigrationActionRunnerArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/types/workspace-migration-action-runner-args.type';
@Injectable()
export class CreatePageLayoutActionHandlerService extends WorkspaceMigrationRunnerActionHandler(
'create_page_layout',
) {
constructor() {
super();
}
optimisticallyApplyActionOnAllFlatEntityMaps({
action,
allFlatEntityMaps,
}: OptimisticallyApplyActionOnAllFlatEntityMapsArgs<CreatePageLayoutAction>): Partial<AllFlatEntityMaps> {
const { flatPageLayoutMaps } = allFlatEntityMaps;
const { flatEntity } = action;
const updatedFlatPageLayoutMaps = addFlatEntityToFlatEntityMapsOrThrow({
flatEntity,
flatEntityMaps: flatPageLayoutMaps,
});
return {
flatPageLayoutMaps: updatedFlatPageLayoutMaps,
};
}
async executeForMetadata(
context: WorkspaceMigrationActionRunnerArgs<CreatePageLayoutAction>,
): Promise<void> {
const { action, queryRunner, workspaceId } = context;
const { flatEntity } = action;
const pageLayoutRepository =
queryRunner.manager.getRepository<PageLayoutEntity>(PageLayoutEntity);
await pageLayoutRepository.insert({
...flatEntity,
workspaceId,
});
}
async executeForWorkspaceSchema(
_context: WorkspaceMigrationActionRunnerArgs<CreatePageLayoutAction>,
): Promise<void> {
return;
}
}
@@ -0,0 +1,58 @@
import { Injectable } from '@nestjs/common';
import {
OptimisticallyApplyActionOnAllFlatEntityMapsArgs,
WorkspaceMigrationRunnerActionHandler,
} from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/interfaces/workspace-migration-runner-action-handler-service.interface';
import { AllFlatEntityMaps } from 'src/engine/metadata-modules/flat-entity/types/all-flat-entity-maps.type';
import { deleteFlatEntityFromFlatEntityMapsOrThrow } from 'src/engine/metadata-modules/flat-entity/utils/delete-flat-entity-from-flat-entity-maps-or-throw.util';
import { PageLayoutEntity } from 'src/engine/metadata-modules/page-layout/entities/page-layout.entity';
import { DeletePageLayoutAction } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/types/workspace-migration-page-layout-action-v2.type';
import { WorkspaceMigrationActionRunnerArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/types/workspace-migration-action-runner-args.type';
@Injectable()
export class DeletePageLayoutActionHandlerService extends WorkspaceMigrationRunnerActionHandler(
'delete_page_layout',
) {
constructor() {
super();
}
optimisticallyApplyActionOnAllFlatEntityMaps({
action,
allFlatEntityMaps,
}: OptimisticallyApplyActionOnAllFlatEntityMapsArgs<DeletePageLayoutAction>): Partial<AllFlatEntityMaps> {
const { flatPageLayoutMaps } = allFlatEntityMaps;
const { flatEntityId } = action;
const updatedFlatPageLayoutMaps = deleteFlatEntityFromFlatEntityMapsOrThrow(
{
entityToDeleteId: flatEntityId,
flatEntityMaps: flatPageLayoutMaps,
},
);
return {
flatPageLayoutMaps: updatedFlatPageLayoutMaps,
};
}
async executeForMetadata(
context: WorkspaceMigrationActionRunnerArgs<DeletePageLayoutAction>,
): Promise<void> {
const { action, queryRunner, workspaceId } = context;
const { flatEntityId } = action;
const pageLayoutRepository =
queryRunner.manager.getRepository<PageLayoutEntity>(PageLayoutEntity);
await pageLayoutRepository.delete({ id: flatEntityId, workspaceId });
}
async executeForWorkspaceSchema(
_context: WorkspaceMigrationActionRunnerArgs<DeletePageLayoutAction>,
): Promise<void> {
return;
}
}
@@ -0,0 +1,71 @@
import { Injectable } from '@nestjs/common';
import {
OptimisticallyApplyActionOnAllFlatEntityMapsArgs,
WorkspaceMigrationRunnerActionHandler,
} from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/interfaces/workspace-migration-runner-action-handler-service.interface';
import { AllFlatEntityMaps } from 'src/engine/metadata-modules/flat-entity/types/all-flat-entity-maps.type';
import { findFlatEntityByIdInFlatEntityMapsOrThrow } from 'src/engine/metadata-modules/flat-entity/utils/find-flat-entity-by-id-in-flat-entity-maps-or-throw.util';
import { replaceFlatEntityInFlatEntityMapsOrThrow } from 'src/engine/metadata-modules/flat-entity/utils/replace-flat-entity-in-flat-entity-maps-or-throw.util';
import { PageLayoutEntity } from 'src/engine/metadata-modules/page-layout/entities/page-layout.entity';
import { UpdatePageLayoutAction } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-builder-v2/builders/page-layout/types/workspace-migration-page-layout-action-v2.type';
import { WorkspaceMigrationActionRunnerArgs } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/types/workspace-migration-action-runner-args.type';
import { fromFlatEntityPropertiesUpdatesToPartialFlatEntity } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/utils/from-flat-entity-properties-updates-to-partial-flat-entity';
@Injectable()
export class UpdatePageLayoutActionHandlerService extends WorkspaceMigrationRunnerActionHandler(
'update_page_layout',
) {
optimisticallyApplyActionOnAllFlatEntityMaps({
action,
allFlatEntityMaps,
}: OptimisticallyApplyActionOnAllFlatEntityMapsArgs<UpdatePageLayoutAction>): Partial<AllFlatEntityMaps> {
const { flatPageLayoutMaps } = allFlatEntityMaps;
const { flatEntityId, flatEntityUpdates } = action;
const existingPageLayout = findFlatEntityByIdInFlatEntityMapsOrThrow({
flatEntityId,
flatEntityMaps: flatPageLayoutMaps,
});
const updatedPageLayout = {
...existingPageLayout,
...fromFlatEntityPropertiesUpdatesToPartialFlatEntity({
updates: flatEntityUpdates,
}),
};
const updatedFlatPageLayoutMaps = replaceFlatEntityInFlatEntityMapsOrThrow({
flatEntity: updatedPageLayout,
flatEntityMaps: flatPageLayoutMaps,
});
return {
flatPageLayoutMaps: updatedFlatPageLayoutMaps,
};
}
async executeForMetadata(
context: WorkspaceMigrationActionRunnerArgs<UpdatePageLayoutAction>,
): Promise<void> {
const { action, queryRunner, workspaceId } = context;
const { flatEntityId, flatEntityUpdates } = action;
const pageLayoutRepository =
queryRunner.manager.getRepository<PageLayoutEntity>(PageLayoutEntity);
await pageLayoutRepository.update(
{ id: flatEntityId, workspaceId },
fromFlatEntityPropertiesUpdatesToPartialFlatEntity({
updates: flatEntityUpdates,
}),
);
}
async executeForWorkspaceSchema(
_context: WorkspaceMigrationActionRunnerArgs<UpdatePageLayoutAction>,
): Promise<void> {
return;
}
}
@@ -4,6 +4,9 @@ import { WorkspaceSchemaManagerModule } from 'src/engine/twenty-orm/workspace-sc
import { CreateAgentActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/agent/services/create-agent-action-handler.service';
import { DeleteAgentActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/agent/services/delete-agent-action-handler.service';
import { UpdateAgentActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/agent/services/update-agent-action-handler.service';
import { CreatePageLayoutActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/page-layout/services/create-page-layout-action-handler.service';
import { DeletePageLayoutActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/page-layout/services/delete-page-layout-action-handler.service';
import { UpdatePageLayoutActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/page-layout/services/update-page-layout-action-handler.service';
import { CreateCronTriggerActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/cron-trigger/services/create-cron-trigger-action-handler.service';
import { DeleteCronTriggerActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/cron-trigger/services/delete-cron-trigger-action-handler.service';
import { UpdateCronTriggerActionHandlerService } from 'src/engine/workspace-manager/workspace-migration-v2/workspace-migration-runner-v2/action-handlers/cron-trigger/services/update-cron-trigger-action-handler.service';
@@ -107,6 +110,10 @@ import { UpdateViewActionHandlerService } from 'src/engine/workspace-manager/wor
UpdateAgentActionHandlerService,
DeleteAgentActionHandlerService,
CreatePageLayoutActionHandlerService,
UpdatePageLayoutActionHandlerService,
DeletePageLayoutActionHandlerService,
CreatePageLayoutWidgetActionHandlerService,
UpdatePageLayoutWidgetActionHandlerService,
DeletePageLayoutWidgetActionHandlerService,