diff --git a/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command.ts b/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command.ts new file mode 100644 index 0000000000..8fc34e5a29 --- /dev/null +++ b/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command.ts @@ -0,0 +1,77 @@ +import { Logger } from '@nestjs/common'; +import { InjectRepository } from '@nestjs/typeorm'; + +import { Command } from 'nest-commander'; +import { Repository } from 'typeorm'; + +import { ActiveOrSuspendedWorkspacesMigrationCommandRunner } from 'src/database/commands/command-runners/active-or-suspended-workspaces-migration.command-runner'; +import { RunOnWorkspaceArgs } from 'src/database/commands/command-runners/workspaces-migration.command-runner'; +import { FileEntity } from 'src/engine/core-modules/file/entities/file.entity'; +import { WorkspaceEntity } from 'src/engine/core-modules/workspace/workspace.entity'; +import { DataSourceService } from 'src/engine/metadata-modules/data-source/data-source.service'; +import { GlobalWorkspaceOrmManager } from 'src/engine/twenty-orm/global-workspace-datasource/global-workspace-orm.manager'; + +@Command({ + name: 'upgrade:delete-file-records', + description: 'Delete all file records from FileRepository for workspace', +}) +export class DeleteFileRecordsCommand extends ActiveOrSuspendedWorkspacesMigrationCommandRunner { + protected readonly logger = new Logger(DeleteFileRecordsCommand.name); + + constructor( + @InjectRepository(WorkspaceEntity) + protected readonly workspaceRepository: Repository, + @InjectRepository(FileEntity) + private readonly fileRepository: Repository, + protected readonly twentyORMGlobalManager: GlobalWorkspaceOrmManager, + protected readonly dataSourceService: DataSourceService, + ) { + super(workspaceRepository, twentyORMGlobalManager, dataSourceService); + } + + override async runOnWorkspace({ + workspaceId, + options, + }: RunOnWorkspaceArgs): Promise { + const isDryRun = options.dryRun || false; + + this.logger.log( + `${isDryRun ? '[DRY RUN] ' : ''}Starting deletion of file records for workspace ${workspaceId}`, + ); + + const files = await this.fileRepository.find({ + where: { workspaceId }, + withDeleted: true, + }); + + if (files.length === 0) { + this.logger.log( + `No file records found for workspace ${workspaceId}, skipping`, + ); + + return; + } + + this.logger.log( + `${isDryRun ? '[DRY RUN] Would delete' : 'Deleting'} ${files.length} file record(s) for workspace ${workspaceId}`, + ); + + if (isDryRun) { + return; + } + + try { + await this.fileRepository.delete({ workspaceId }); + + this.logger.log( + `Successfully deleted ${files.length} file record(s) for workspace ${workspaceId}`, + ); + } catch (error) { + this.logger.error( + `Failed to delete file records for workspace ${workspaceId}: ${error.message}`, + ); + + throw error; + } + } +} diff --git a/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-upgrade-version-command.module.ts b/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-upgrade-version-command.module.ts index 8ff081c9d1..c49f283d4c 100644 --- a/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-upgrade-version-command.module.ts +++ b/packages/twenty-server/src/database/commands/upgrade-version-command/1-16/1-16-upgrade-version-command.module.ts @@ -3,6 +3,7 @@ import { TypeOrmModule } from '@nestjs/typeorm'; import { BackfillOpportunityOwnerFieldCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-backfill-opportunity-owner-field.command'; import { BackfillStandardPageLayoutsCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-backfill-standard-page-layouts.command'; +import { DeleteFileRecordsCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command'; import { FlushV2CacheAndIncrementMetadataVersionCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-flush-v2-cache-and-increment-metadata-version.command'; import { IdentifyAgentMetadataCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-identify-agent-metadata.command'; import { IdentifyFieldMetadataCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-identify-field-metadata.command'; @@ -26,6 +27,7 @@ import { MakeViewGroupUniversalIdentifierAndApplicationIdNotNullableMigrationCom import { MakeViewUniversalIdentifierAndApplicationIdNotNullableMigrationCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-make-view-universal-identifier-and-application-id-not-nullable-migration.command'; import { UpdateTaskOnDeleteActionCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-update-task-on-delete-action.command'; import { ApplicationModule } from 'src/engine/core-modules/application/application.module'; +import { FileEntity } from 'src/engine/core-modules/file/entities/file.entity'; import { WorkspaceEntity } from 'src/engine/core-modules/workspace/workspace.entity'; import { AgentEntity } from 'src/engine/metadata-modules/ai/ai-agent/entities/agent.entity'; import { DataSourceModule } from 'src/engine/metadata-modules/data-source/data-source.module'; @@ -58,6 +60,7 @@ import { WorkspaceMigrationModule } from 'src/engine/workspace-manager/workspace ViewFieldEntity, ViewFilterEntity, ViewGroupEntity, + FileEntity, ]), DataSourceModule, WorkspaceCacheModule, @@ -73,6 +76,7 @@ import { WorkspaceMigrationModule } from 'src/engine/workspace-manager/workspace UpdateTaskOnDeleteActionCommand, BackfillOpportunityOwnerFieldCommand, BackfillStandardPageLayoutsCommand, + DeleteFileRecordsCommand, IdentifyAgentMetadataCommand, IdentifyFieldMetadataCommand, IdentifyIndexMetadataCommand, @@ -99,6 +103,7 @@ import { WorkspaceMigrationModule } from 'src/engine/workspace-manager/workspace UpdateTaskOnDeleteActionCommand, BackfillOpportunityOwnerFieldCommand, BackfillStandardPageLayoutsCommand, + DeleteFileRecordsCommand, IdentifyAgentMetadataCommand, IdentifyFieldMetadataCommand, IdentifyIndexMetadataCommand, diff --git a/packages/twenty-server/src/database/commands/upgrade-version-command/1-17/1-17-upgrade-version-command.module.ts b/packages/twenty-server/src/database/commands/upgrade-version-command/1-17/1-17-upgrade-version-command.module.ts index 5ba1f7af2d..13ac5c1320 100644 --- a/packages/twenty-server/src/database/commands/upgrade-version-command/1-17/1-17-upgrade-version-command.module.ts +++ b/packages/twenty-server/src/database/commands/upgrade-version-command/1-17/1-17-upgrade-version-command.module.ts @@ -1,12 +1,14 @@ import { Module } from '@nestjs/common'; import { TypeOrmModule } from '@nestjs/typeorm'; +import { DeleteFileRecordsCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command'; import { IdentifyWebhookMetadataCommand } from 'src/database/commands/upgrade-version-command/1-17/1-17-identify-webhook-metadata.command'; import { MakeWebhookUniversalIdentifierAndApplicationIdNotNullableMigrationCommand } from 'src/database/commands/upgrade-version-command/1-17/1-17-make-webhook-universal-identifier-and-application-id-not-nullable-migration.command'; import { MigrateAttachmentToMorphRelationsCommand } from 'src/database/commands/upgrade-version-command/1-17/1-17-migrate-attachment-to-morph-relations.command'; import { ApplicationModule } from 'src/engine/core-modules/application/application.module'; import { FeatureFlagEntity } from 'src/engine/core-modules/feature-flag/feature-flag.entity'; import { FeatureFlagModule } from 'src/engine/core-modules/feature-flag/feature-flag.module'; +import { FileEntity } from 'src/engine/core-modules/file/entities/file.entity'; import { WorkspaceEntity } from 'src/engine/core-modules/workspace/workspace.entity'; import { DataSourceModule } from 'src/engine/metadata-modules/data-source/data-source.module'; import { FieldMetadataEntity } from 'src/engine/metadata-modules/field-metadata/field-metadata.entity'; @@ -28,6 +30,7 @@ import { AttachmentWorkspaceEntity } from 'src/modules/attachment/standard-objec FeatureFlagEntity, AttachmentWorkspaceEntity, WebhookEntity, + FileEntity, ]), DataSourceModule, WorkspaceCacheStorageModule, @@ -42,11 +45,13 @@ import { AttachmentWorkspaceEntity } from 'src/modules/attachment/standard-objec MigrateAttachmentToMorphRelationsCommand, IdentifyWebhookMetadataCommand, MakeWebhookUniversalIdentifierAndApplicationIdNotNullableMigrationCommand, + DeleteFileRecordsCommand, ], exports: [ MigrateAttachmentToMorphRelationsCommand, IdentifyWebhookMetadataCommand, MakeWebhookUniversalIdentifierAndApplicationIdNotNullableMigrationCommand, + DeleteFileRecordsCommand, ], }) export class V1_17_UpgradeVersionCommandModule {} diff --git a/packages/twenty-server/src/database/commands/upgrade-version-command/upgrade.command.ts b/packages/twenty-server/src/database/commands/upgrade-version-command/upgrade.command.ts index aad1167912..7e09940a96 100644 --- a/packages/twenty-server/src/database/commands/upgrade-version-command/upgrade.command.ts +++ b/packages/twenty-server/src/database/commands/upgrade-version-command/upgrade.command.ts @@ -24,6 +24,7 @@ import { FixNanPositionValuesInNotesCommand } from 'src/database/commands/upgrad import { MigratePageLayoutWidgetConfigurationCommand } from 'src/database/commands/upgrade-version-command/1-15/1-15-migrate-page-layout-widget-configuration.command'; import { BackfillOpportunityOwnerFieldCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-backfill-opportunity-owner-field.command'; import { BackfillStandardPageLayoutsCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-backfill-standard-page-layouts.command'; +import { DeleteFileRecordsCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-delete-all-files.command'; import { FlushV2CacheAndIncrementMetadataVersionCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-flush-v2-cache-and-increment-metadata-version.command'; import { IdentifyAgentMetadataCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-identify-agent-metadata.command'; import { IdentifyFieldMetadataCommand } from 'src/database/commands/upgrade-version-command/1-16/1-16-identify-field-metadata.command'; @@ -112,6 +113,7 @@ export class UpgradeCommand extends UpgradeCommandRunner { protected readonly identifyRemainingEntitiesMetadataCommand: IdentifyRemainingEntitiesMetadataCommand, protected readonly makeRemainingEntitiesUniversalIdentifierAndApplicationIdNotNullableMigrationCommand: MakeRemainingEntitiesUniversalIdentifierAndApplicationIdNotNullableMigrationCommand, protected readonly flushV2CacheAndIncrementMetadataVersionCommand: FlushV2CacheAndIncrementMetadataVersionCommand, + protected readonly deleteFileRecordsCommand: DeleteFileRecordsCommand, // 1.17 Commands protected readonly migrateAttachmentToMorphRelationsCommand: MigrateAttachmentToMorphRelationsCommand, @@ -185,6 +187,7 @@ export class UpgradeCommand extends UpgradeCommandRunner { .makeRemainingEntitiesUniversalIdentifierAndApplicationIdNotNullableMigrationCommand, this.flushV2CacheAndIncrementMetadataVersionCommand, this.updateTaskOnDeleteActionCommand, + this.deleteFileRecordsCommand, ]; const commands_1170: VersionCommands = [ @@ -192,6 +195,7 @@ export class UpgradeCommand extends UpgradeCommandRunner { this.identifyWebhookMetadataCommand, this .makeWebhookUniversalIdentifierAndApplicationIdNotNullableMigrationCommand, + this.deleteFileRecordsCommand, ]; this.allCommands = {