Closes https://github.com/twentyhq/core-team-issues/issues/747
This commit is contained in:
@ -0,0 +1,425 @@
|
||||
import { ObjectRecordsPermissions } from 'twenty-shared/types';
|
||||
import {
|
||||
DeepPartial,
|
||||
FindManyOptions,
|
||||
FindOneOptions,
|
||||
FindOptionsWhere,
|
||||
ObjectLiteral,
|
||||
QueryRunner,
|
||||
} from 'typeorm';
|
||||
|
||||
import { FeatureFlagMap } from 'src/engine/core-modules/feature-flag/interfaces/feature-flag-map.interface';
|
||||
import { WorkspaceInternalContext } from 'src/engine/twenty-orm/interfaces/workspace-internal-context.interface';
|
||||
|
||||
import { FeatureFlagKey } from 'src/engine/core-modules/feature-flag/enums/feature-flag-key.enum';
|
||||
import { WorkspaceEntityManager } from 'src/engine/twenty-orm/entity-manager/workspace-entity-manager';
|
||||
import { WorkspaceRepository } from 'src/engine/twenty-orm/repository/workspace.repository';
|
||||
|
||||
describe('WorkspaceRepository', () => {
|
||||
let repository: WorkspaceRepository<ObjectLiteral>;
|
||||
let mockEntityManager: jest.Mocked<WorkspaceEntityManager>;
|
||||
let mockInternalContext: WorkspaceInternalContext;
|
||||
let mockFeatureFlagMap: FeatureFlagMap;
|
||||
let mockObjectRecordsPermissions: ObjectRecordsPermissions;
|
||||
let mockQueryRunner: QueryRunner;
|
||||
|
||||
beforeEach(() => {
|
||||
mockEntityManager = {
|
||||
find: jest.fn(),
|
||||
findBy: jest.fn(),
|
||||
findAndCount: jest.fn(),
|
||||
findAndCountBy: jest.fn(),
|
||||
findOne: jest.fn(),
|
||||
findOneBy: jest.fn(),
|
||||
findOneOrFail: jest.fn(),
|
||||
findOneByOrFail: jest.fn(),
|
||||
save: jest.fn(),
|
||||
remove: jest.fn(),
|
||||
delete: jest.fn(),
|
||||
softRemove: jest.fn(),
|
||||
softDelete: jest.fn(),
|
||||
recover: jest.fn(),
|
||||
restore: jest.fn(),
|
||||
insert: jest.fn(),
|
||||
update: jest.fn(),
|
||||
upsert: jest.fn(),
|
||||
exists: jest.fn(),
|
||||
existsBy: jest.fn(),
|
||||
count: jest.fn(),
|
||||
countBy: jest.fn(),
|
||||
sum: jest.fn(),
|
||||
average: jest.fn(),
|
||||
minimum: jest.fn(),
|
||||
maximum: jest.fn(),
|
||||
increment: jest.fn(),
|
||||
decrement: jest.fn(),
|
||||
preload: jest.fn(),
|
||||
clear: jest.fn(),
|
||||
} as unknown as jest.Mocked<WorkspaceEntityManager>;
|
||||
|
||||
mockInternalContext = {
|
||||
workspaceId: 'test-workspace-id',
|
||||
objectMetadataMaps: {
|
||||
idByNameSingular: {},
|
||||
},
|
||||
featureFlagsMap: {},
|
||||
} as WorkspaceInternalContext;
|
||||
|
||||
mockFeatureFlagMap = Object.values(FeatureFlagKey).reduce(
|
||||
(acc, key) => ({ ...acc, [key]: false }),
|
||||
{} as FeatureFlagMap,
|
||||
);
|
||||
mockObjectRecordsPermissions = {
|
||||
'test-entity': {
|
||||
canRead: true,
|
||||
canUpdate: false,
|
||||
canSoftDelete: false,
|
||||
canDestroy: false,
|
||||
},
|
||||
};
|
||||
mockQueryRunner = {} as QueryRunner;
|
||||
|
||||
repository = new WorkspaceRepository(
|
||||
mockInternalContext,
|
||||
'test-entity',
|
||||
mockEntityManager,
|
||||
mockFeatureFlagMap,
|
||||
mockQueryRunner,
|
||||
mockObjectRecordsPermissions,
|
||||
false,
|
||||
);
|
||||
|
||||
// Mock the private methods
|
||||
jest
|
||||
.spyOn(repository as any, 'getObjectMetadataFromTarget')
|
||||
.mockResolvedValue({
|
||||
id: 'test-metadata-id',
|
||||
nameSingular: 'test-entity',
|
||||
namePlural: 'test-entities',
|
||||
fields: [],
|
||||
});
|
||||
|
||||
jest.spyOn(repository as any, 'formatData').mockImplementation((data) => {
|
||||
if (Array.isArray(data)) {
|
||||
return data.map((item) => Object.assign({}, item));
|
||||
}
|
||||
|
||||
return Object.assign({}, data);
|
||||
});
|
||||
|
||||
jest.spyOn(repository as any, 'formatResult').mockImplementation((data) => {
|
||||
if (Array.isArray(data)) {
|
||||
return data.map((item) => Object.assign({}, item));
|
||||
}
|
||||
|
||||
return Object.assign({}, data);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Find Methods', () => {
|
||||
it('should delegate to workspaceEntityManager find', async () => {
|
||||
const options: FindManyOptions<ObjectLiteral> = {
|
||||
where: { id: 'test-id' },
|
||||
};
|
||||
|
||||
mockEntityManager.find.mockResolvedValue([{ id: 'test-id' }]);
|
||||
|
||||
await repository.find(options);
|
||||
|
||||
expect(mockEntityManager.find).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ where: { id: 'test-id' } },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager findBy', async () => {
|
||||
const where: FindOptionsWhere<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.findBy.mockResolvedValue([{ id: 'test-id' }]);
|
||||
|
||||
await repository.findBy(where);
|
||||
|
||||
expect(mockEntityManager.findBy).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager findAndCount', async () => {
|
||||
const options: FindManyOptions<ObjectLiteral> = {
|
||||
where: { id: 'test-id' },
|
||||
};
|
||||
|
||||
mockEntityManager.findAndCount.mockResolvedValue([
|
||||
[{ id: 'test-id' }],
|
||||
1,
|
||||
]);
|
||||
|
||||
await repository.findAndCount(options);
|
||||
|
||||
expect(mockEntityManager.findAndCount).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ where: { id: 'test-id' } },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager findOne', async () => {
|
||||
const options: FindOneOptions<ObjectLiteral> = {
|
||||
where: { id: 'test-id' },
|
||||
};
|
||||
|
||||
mockEntityManager.findOne.mockResolvedValue({ id: 'test-id' });
|
||||
|
||||
await repository.findOne(options);
|
||||
|
||||
expect(mockEntityManager.findOne).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ where: { id: 'test-id' } },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Save Methods', () => {
|
||||
it('should delegate to workspaceEntityManager save', async () => {
|
||||
const entity: DeepPartial<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.save.mockResolvedValue({ id: 'test-id' });
|
||||
|
||||
await repository.save(entity);
|
||||
|
||||
expect(mockEntityManager.save).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
undefined,
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Remove Methods', () => {
|
||||
it('should delegate to workspaceEntityManager remove', async () => {
|
||||
const entity: ObjectLiteral = { id: 'test-id' };
|
||||
const expectedResult = [{ id: 'test-id' }];
|
||||
|
||||
mockEntityManager.remove.mockResolvedValue(expectedResult);
|
||||
|
||||
const result = await repository.remove(entity);
|
||||
|
||||
expect(mockEntityManager.remove).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
undefined,
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual(expectedResult);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager delete', async () => {
|
||||
const criteria: FindOptionsWhere<ObjectLiteral> = { id: 'test-id' };
|
||||
const expectedResult = { affected: 1, raw: [] };
|
||||
|
||||
mockEntityManager.delete.mockResolvedValue(expectedResult);
|
||||
|
||||
const result = await repository.delete(criteria);
|
||||
|
||||
expect(mockEntityManager.delete).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
expect(result).toEqual(expectedResult);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Insert Methods', () => {
|
||||
it('should delegate to workspaceEntityManager insert', async () => {
|
||||
const entity: DeepPartial<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.insert.mockResolvedValue({
|
||||
identifiers: [{ id: 'test-id' }],
|
||||
generatedMaps: [{ id: 'test-id' }],
|
||||
raw: [],
|
||||
});
|
||||
|
||||
await repository.insert(entity);
|
||||
|
||||
expect(mockEntityManager.insert).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager upsert', async () => {
|
||||
const entity: DeepPartial<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.upsert.mockResolvedValue({
|
||||
identifiers: [{ id: 'test-id' }],
|
||||
generatedMaps: [{ id: 'test-id' }],
|
||||
raw: [],
|
||||
});
|
||||
|
||||
await repository.upsert(entity, ['id']);
|
||||
|
||||
expect(mockEntityManager.upsert).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
['id'],
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Update Methods', () => {
|
||||
it('should delegate to workspaceEntityManager update', async () => {
|
||||
const criteria: FindOptionsWhere<ObjectLiteral> = { id: 'test-id' };
|
||||
const partialEntity: DeepPartial<ObjectLiteral> = { name: 'test' };
|
||||
|
||||
mockEntityManager.update.mockResolvedValue({
|
||||
affected: 1,
|
||||
raw: [],
|
||||
generatedMaps: [],
|
||||
});
|
||||
|
||||
await repository.update(criteria, partialEntity);
|
||||
|
||||
expect(mockEntityManager.update).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
{ name: 'test' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Math Methods', () => {
|
||||
it('should delegate to workspaceEntityManager sum', async () => {
|
||||
const where: FindOptionsWhere<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.sum.mockResolvedValue(100);
|
||||
|
||||
await repository.sum('testColumn', where);
|
||||
|
||||
expect(mockEntityManager.sum).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
'testColumn',
|
||||
{ id: 'test-id' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager increment', async () => {
|
||||
const conditions: FindOptionsWhere<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.increment.mockResolvedValue({
|
||||
affected: 1,
|
||||
raw: [],
|
||||
generatedMaps: [],
|
||||
});
|
||||
|
||||
await repository.increment(conditions, 'testColumn', 1);
|
||||
|
||||
expect(mockEntityManager.increment).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
'testColumn',
|
||||
1,
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
describe('Preload and Clear Methods', () => {
|
||||
it('should delegate to workspaceEntityManager preload', async () => {
|
||||
const entityLike: DeepPartial<ObjectLiteral> = { id: 'test-id' };
|
||||
|
||||
mockEntityManager.preload.mockResolvedValue({ id: 'test-id' });
|
||||
|
||||
await repository.preload(entityLike);
|
||||
|
||||
expect(mockEntityManager.preload).toHaveBeenCalledWith(
|
||||
'test-entity',
|
||||
{ id: 'test-id' },
|
||||
{
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it('should delegate to workspaceEntityManager clear', async () => {
|
||||
mockEntityManager.clear.mockResolvedValue(undefined);
|
||||
|
||||
await repository.clear();
|
||||
|
||||
expect(mockEntityManager.clear).toHaveBeenCalledWith('test-entity', {
|
||||
shouldBypassPermissionChecks: false,
|
||||
objectRecordsPermissions: mockObjectRecordsPermissions,
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe('Restricted Methods', () => {
|
||||
it('should throw error for query', async () => {
|
||||
await expect(repository.query()).rejects.toThrow('Method not allowed.');
|
||||
});
|
||||
|
||||
it('should throw error for findByIds', async () => {
|
||||
await expect(repository.findByIds()).rejects.toThrow(
|
||||
'findByIds is deprecated. Please use findBy with In operator instead.',
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw error for findOneById', async () => {
|
||||
await expect(repository.findOneById()).rejects.toThrow(
|
||||
'findOneById is deprecated. Please use findOneBy with id condition instead.',
|
||||
);
|
||||
});
|
||||
|
||||
it('should throw error for exist', async () => {
|
||||
await expect(repository.exist()).rejects.toThrow(
|
||||
'exist is deprecated. Please use exists method instead.',
|
||||
);
|
||||
});
|
||||
});
|
||||
});
|
||||
@ -94,7 +94,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
const result = await manager.find(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.find(
|
||||
this.target,
|
||||
computedOptions,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -106,7 +114,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
const result = await manager.findBy(this.target, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findBy(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -118,7 +134,15 @@ export class WorkspaceRepository<
|
||||
): Promise<[T[], number]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
const result = await manager.findAndCount(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findAndCount(
|
||||
this.target,
|
||||
computedOptions,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -130,9 +154,14 @@ export class WorkspaceRepository<
|
||||
): Promise<[T[], number]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findAndCountBy(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
@ -145,7 +174,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T | null> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
const result = await manager.findOne(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findOne(
|
||||
this.target,
|
||||
computedOptions,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -157,7 +194,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T | null> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
const result = await manager.findOneBy(this.target, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findOneBy(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -169,7 +214,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
const result = await manager.findOneOrFail(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findOneOrFail(
|
||||
this.target,
|
||||
computedOptions,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
return formattedResult;
|
||||
@ -181,9 +234,14 @@ export class WorkspaceRepository<
|
||||
): Promise<T> {
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.findOneByOrFail(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result);
|
||||
|
||||
@ -219,25 +277,32 @@ export class WorkspaceRepository<
|
||||
|
||||
override async save<U extends DeepPartial<T>>(
|
||||
entityOrEntities: U | U[],
|
||||
options?: SaveOptions,
|
||||
options?: SaveOptions | (SaveOptions & { reload: false }),
|
||||
entityManager?: WorkspaceEntityManager,
|
||||
): Promise<U | U[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const formattedEntityOrEntities = await this.formatData(entityOrEntities);
|
||||
let result: U | U[];
|
||||
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
// Needed because save method has multiple signature, otherwise we will need to do a type assertion
|
||||
if (Array.isArray(formattedEntityOrEntities)) {
|
||||
result = await manager.save(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
} else {
|
||||
result = await manager.save(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
@ -268,10 +333,15 @@ export class WorkspaceRepository<
|
||||
): Promise<T | T[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const formattedEntityOrEntities = await this.formatData(entityOrEntities);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
const result = await manager.remove(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
|
||||
const formattedResult = await this.formatResult(result);
|
||||
@ -298,7 +368,12 @@ export class WorkspaceRepository<
|
||||
criteria = await this.transformOptions(criteria);
|
||||
}
|
||||
|
||||
return manager.delete(this.target, criteria);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.delete(this.target, criteria, permissionOptions);
|
||||
}
|
||||
|
||||
override softRemove<U extends DeepPartial<T>>(
|
||||
@ -332,20 +407,26 @@ export class WorkspaceRepository<
|
||||
): Promise<U | U[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const formattedEntityOrEntities = await this.formatData(entityOrEntities);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
let result: U | U[];
|
||||
|
||||
// Needed becasuse save method has multiple signature, otherwise we will need to do a type assertion
|
||||
// Needed because save method has multiple signature, otherwise we will need to do a type assertion
|
||||
if (Array.isArray(formattedEntityOrEntities)) {
|
||||
result = await manager.softRemove(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
} else {
|
||||
result = await manager.softRemove(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
@ -373,7 +454,12 @@ export class WorkspaceRepository<
|
||||
criteria = await this.transformOptions(criteria);
|
||||
}
|
||||
|
||||
return manager.softDelete(this.target, criteria);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.softDelete(this.target, criteria, permissionOptions);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -410,20 +496,26 @@ export class WorkspaceRepository<
|
||||
): Promise<U | U[]> {
|
||||
const manager = entityManager || this.manager;
|
||||
const formattedEntityOrEntities = await this.formatData(entityOrEntities);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
let result: U | U[];
|
||||
|
||||
// Needed becasuse save method has multiple signature, otherwise we will need to do a type assertion
|
||||
// Needed because save method has multiple signature, otherwise we will need to do a type assertion
|
||||
if (Array.isArray(formattedEntityOrEntities)) {
|
||||
result = await manager.recover(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
} else {
|
||||
result = await manager.recover(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
options,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
@ -451,7 +543,12 @@ export class WorkspaceRepository<
|
||||
criteria = await this.transformOptions(criteria);
|
||||
}
|
||||
|
||||
return manager.restore(this.target, criteria);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.restore(this.target, criteria, permissionOptions);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -464,10 +561,15 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
|
||||
const formattedEntity = await this.formatData(entity);
|
||||
const result = await manager.insert(this.target, formattedEntity, {
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
});
|
||||
};
|
||||
const result = await manager.insert(
|
||||
this.target,
|
||||
formattedEntity,
|
||||
permissionOptions,
|
||||
);
|
||||
const formattedResult = await this.formatResult(result.generatedMaps);
|
||||
|
||||
return {
|
||||
@ -500,7 +602,17 @@ export class WorkspaceRepository<
|
||||
criteria = await this.transformOptions(criteria);
|
||||
}
|
||||
|
||||
return manager.update(this.target, criteria, partialEntity);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.update(
|
||||
this.target,
|
||||
criteria,
|
||||
partialEntity,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
override async upsert(
|
||||
@ -512,14 +624,16 @@ export class WorkspaceRepository<
|
||||
|
||||
const formattedEntityOrEntities = await this.formatData(entityOrEntities);
|
||||
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
const result = await manager.upsert(
|
||||
this.target,
|
||||
formattedEntityOrEntities,
|
||||
conflictPathsOrOptions,
|
||||
{
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
},
|
||||
permissionOptions,
|
||||
);
|
||||
|
||||
const formattedResult = await this.formatResult(result.generatedMaps);
|
||||
@ -541,7 +655,12 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
|
||||
return manager.exists(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.exists(this.target, computedOptions, permissionOptions);
|
||||
}
|
||||
|
||||
override async existsBy(
|
||||
@ -551,7 +670,16 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.existsBy(this.target, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.existsBy(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -564,7 +692,12 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions(options);
|
||||
|
||||
return manager.count(this.target, computedOptions);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.count(this.target, computedOptions, permissionOptions);
|
||||
}
|
||||
|
||||
override async countBy(
|
||||
@ -574,7 +707,16 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.countBy(this.target, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.countBy(
|
||||
this.target,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -588,7 +730,17 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.sum(this.target, columnName, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.sum(
|
||||
this.target,
|
||||
columnName,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
override async average(
|
||||
@ -599,7 +751,17 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.average(this.target, columnName, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.average(
|
||||
this.target,
|
||||
columnName,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
override async minimum(
|
||||
@ -610,7 +772,17 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.minimum(this.target, columnName, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.minimum(
|
||||
this.target,
|
||||
columnName,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
override async maximum(
|
||||
@ -621,7 +793,17 @@ export class WorkspaceRepository<
|
||||
const manager = entityManager || this.manager;
|
||||
const computedOptions = await this.transformOptions({ where });
|
||||
|
||||
return manager.maximum(this.target, columnName, computedOptions.where);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.maximum(
|
||||
this.target,
|
||||
columnName,
|
||||
computedOptions.where,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
override async increment(
|
||||
@ -635,11 +817,17 @@ export class WorkspaceRepository<
|
||||
where: conditions,
|
||||
});
|
||||
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.increment(
|
||||
this.target,
|
||||
computedConditions.where,
|
||||
propertyPath,
|
||||
value,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
@ -654,14 +842,73 @@ export class WorkspaceRepository<
|
||||
where: conditions,
|
||||
});
|
||||
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.decrement(
|
||||
this.target,
|
||||
computedConditions.where,
|
||||
propertyPath,
|
||||
value,
|
||||
permissionOptions,
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* PRELOAD METHOD
|
||||
*/
|
||||
override async preload<U extends DeepPartial<T>>(
|
||||
entityLike: U,
|
||||
entityManager?: WorkspaceEntityManager,
|
||||
): Promise<T | undefined> {
|
||||
const manager = entityManager || this.manager;
|
||||
const formattedEntityLike = await this.formatData(entityLike);
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.preload(this.target, formattedEntityLike, permissionOptions);
|
||||
}
|
||||
|
||||
/**
|
||||
* CLEAR METHOD
|
||||
*/
|
||||
override async clear(entityManager?: WorkspaceEntityManager): Promise<void> {
|
||||
const manager = entityManager || this.manager;
|
||||
const permissionOptions = {
|
||||
shouldBypassPermissionChecks: this.shouldBypassPermissionChecks,
|
||||
objectRecordsPermissions: this.objectRecordsPermissions,
|
||||
};
|
||||
|
||||
return manager.clear(this.target, permissionOptions);
|
||||
}
|
||||
|
||||
/**
|
||||
* DEPRECATED AND RESTRICTED METHODS
|
||||
*/
|
||||
override async query(): Promise<unknown> {
|
||||
throw new Error('Method not allowed.');
|
||||
}
|
||||
|
||||
override async findByIds(): Promise<T[]> {
|
||||
throw new Error(
|
||||
'findByIds is deprecated. Please use findBy with In operator instead.',
|
||||
);
|
||||
}
|
||||
|
||||
override async findOneById(): Promise<T | null> {
|
||||
throw new Error(
|
||||
'findOneById is deprecated. Please use findOneBy with id condition instead.',
|
||||
);
|
||||
}
|
||||
|
||||
override async exist(): Promise<boolean> {
|
||||
throw new Error('exist is deprecated. Please use exists method instead.');
|
||||
}
|
||||
|
||||
/**
|
||||
* PRIVATE METHODS
|
||||
*/
|
||||
|
||||
Reference in New Issue
Block a user