Deprecate nullable syncableEntity (#17279)

# Introduction
As we've been identifying both standard and custom entities for all the
metadata that had standard
We now still need to identify all custom entities enforcing them to have
an `applicationId` and `universalIdentifier`

In this PR we've removed the `SyncableEntityRequired` in favor requiring
props directly in the `SyncableEntity`
Which means that all metadata in db will now expect non nullable
applicationId and universalIdentifier across the whole application

Will add some type cleanup later in
https://github.com/twentyhq/twenty/pull/17277
This commit is contained in:
Paul Rastoin
2026-01-21 11:23:55 +01:00
committed by GitHub
parent b56f45e871
commit 596b7cc62d
28 changed files with 934 additions and 63 deletions
@@ -3,6 +3,7 @@
import { Module } from '@nestjs/common';
import { TypeOrmModule } from '@nestjs/typeorm';
import { ApplicationModule } from 'src/engine/core-modules/application/application.module';
import { BillingModule } from 'src/engine/core-modules/billing/billing.module';
import { WorkspaceManyOrAllFlatEntityMapsCacheModule } from 'src/engine/metadata-modules/flat-entity/services/workspace-many-or-all-flat-entity-maps-cache.module';
import { RowLevelPermissionPredicateGroupEntity } from 'src/engine/metadata-modules/row-level-permission-predicate/entities/row-level-permission-predicate-group.entity';
@@ -24,6 +25,7 @@ import { WorkspaceMigrationModule } from 'src/engine/workspace-manager/workspace
WorkspaceManyOrAllFlatEntityMapsCacheModule,
WorkspaceMigrationModule,
BillingModule,
ApplicationModule,
],
providers: [
RowLevelPermissionPredicateService,
@@ -7,6 +7,7 @@ import { InjectRepository } from '@nestjs/typeorm';
import { isDefined } from 'twenty-shared/utils';
import { Repository } from 'typeorm';
import { ApplicationService } from 'src/engine/core-modules/application/application.service';
import { BillingEntitlementKey } from 'src/engine/core-modules/billing/enums/billing-entitlement-key.enum';
import { BillingService } from 'src/engine/core-modules/billing/services/billing.service';
import { WorkspaceManyOrAllFlatEntityMapsCacheService } from 'src/engine/metadata-modules/flat-entity/services/workspace-many-or-all-flat-entity-maps-cache.service';
@@ -42,6 +43,7 @@ export class RowLevelPermissionPredicateGroupService {
@InjectRepository(RowLevelPermissionPredicateGroupEntity)
private readonly rowLevelPermissionPredicateGroupRepository: Repository<RowLevelPermissionPredicateGroupEntity>,
private readonly configService: ConfigService,
private readonly applicationService: ApplicationService,
) {}
async createOne({
@@ -52,12 +54,19 @@ export class RowLevelPermissionPredicateGroupService {
workspaceId: string;
}): Promise<RowLevelPermissionPredicateGroupDTO> {
await this.hasRowLevelPermissionFeatureOrThrow(workspaceId);
const { workspaceCustomFlatApplication } =
await this.applicationService.findWorkspaceTwentyStandardAndCustomApplicationOrThrow(
{
workspaceId,
},
);
const flatGroupToCreate =
fromCreateRowLevelPermissionPredicateGroupInputToFlatRowLevelPermissionPredicateGroupToCreate(
{
createRowLevelPermissionPredicateGroupInput,
workspaceId,
workspaceCustomApplicationId: workspaceCustomFlatApplication.id,
},
);
@@ -6,6 +6,7 @@ import { ConfigService } from '@nestjs/config';
import { isDefined } from 'twenty-shared/utils';
import { v4 } from 'uuid';
import { ApplicationService } from 'src/engine/core-modules/application/application.service';
import { BillingEntitlementKey } from 'src/engine/core-modules/billing/enums/billing-entitlement-key.enum';
import { BillingService } from 'src/engine/core-modules/billing/services/billing.service';
import { WorkspaceManyOrAllFlatEntityMapsCacheService } from 'src/engine/metadata-modules/flat-entity/services/workspace-many-or-all-flat-entity-maps-cache.service';
@@ -47,6 +48,7 @@ export class RowLevelPermissionPredicateService {
private readonly workspaceCacheService: WorkspaceCacheService,
private readonly billingService: BillingService,
private readonly configService: ConfigService,
private readonly applicationService: ApplicationService,
) {}
async createOne({
@@ -58,11 +60,18 @@ export class RowLevelPermissionPredicateService {
}): Promise<RowLevelPermissionPredicateDTO> {
await this.hasRowLevelPermissionFeatureOrThrow(workspaceId);
const { workspaceCustomFlatApplication } =
await this.applicationService.findWorkspaceTwentyStandardAndCustomApplicationOrThrow(
{
workspaceId,
},
);
const flatPredicateToCreate =
fromCreateRowLevelPermissionPredicateInputToFlatRowLevelPermissionPredicateToCreate(
{
createRowLevelPermissionPredicateInput,
workspaceId,
workspaceCustomApplicationId: workspaceCustomFlatApplication.id,
},
);
@@ -322,6 +331,12 @@ export class RowLevelPermissionPredicateService {
const { roleId, objectMetadataId, predicates, predicateGroups } = input;
const { workspaceCustomFlatApplication } =
await this.applicationService.findWorkspaceTwentyStandardAndCustomApplicationOrThrow(
{
workspaceId,
},
);
const {
flatRowLevelPermissionPredicateMaps,
flatRowLevelPermissionPredicateGroupMaps,
@@ -366,6 +381,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId,
workspaceId,
flatRowLevelPermissionPredicateGroupMaps,
workspaceCustomApplicationId: workspaceCustomFlatApplication.id,
});
const { predicatesToCreate, predicatesToUpdate, predicatesToDelete } =
@@ -376,6 +392,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId,
workspaceId,
flatRowLevelPermissionPredicateMaps,
workspaceCustomApplicationId: workspaceCustomFlatApplication.id,
});
await this.runUpsertMigration({
@@ -435,6 +452,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId,
workspaceId,
flatRowLevelPermissionPredicateGroupMaps,
workspaceCustomApplicationId,
}: {
existingGroups: FlatRowLevelPermissionPredicateGroup[];
inputGroups: RowLevelPermissionPredicateGroupInput[];
@@ -442,6 +460,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId: string;
workspaceId: string;
flatRowLevelPermissionPredicateGroupMaps: FlatEntityMaps<FlatRowLevelPermissionPredicateGroup>;
workspaceCustomApplicationId: string;
}): {
groupsToCreate: FlatRowLevelPermissionPredicateGroup[];
groupsToUpdate: FlatRowLevelPermissionPredicateGroup[];
@@ -488,7 +507,7 @@ export class RowLevelPermissionPredicateService {
updatedAt: createdAt,
deletedAt: null,
universalIdentifier: groupId,
applicationId: null,
applicationId: workspaceCustomApplicationId,
});
}
}
@@ -515,6 +534,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId,
workspaceId,
flatRowLevelPermissionPredicateMaps,
workspaceCustomApplicationId,
}: {
existingPredicates: FlatRowLevelPermissionPredicate[];
inputPredicates: RowLevelPermissionPredicateInput[];
@@ -522,6 +542,7 @@ export class RowLevelPermissionPredicateService {
objectMetadataId: string;
workspaceId: string;
flatRowLevelPermissionPredicateMaps: FlatEntityMaps<FlatRowLevelPermissionPredicate>;
workspaceCustomApplicationId: string;
}): {
predicatesToCreate: FlatRowLevelPermissionPredicate[];
predicatesToUpdate: FlatRowLevelPermissionPredicate[];
@@ -583,7 +604,7 @@ export class RowLevelPermissionPredicateService {
updatedAt: createdAt,
deletedAt: null,
universalIdentifier: predicateId,
applicationId: null,
applicationId: workspaceCustomApplicationId,
});
}
}