fix: resolve file conflicts

This commit is contained in:
yassinedorbozgithub 2025-01-15 10:39:59 +01:00
commit e42d8aad39
16 changed files with 200 additions and 192 deletions

View File

@ -61,11 +61,11 @@ describe('BlockController', () => {
let blockController: BlockController;
let blockService: BlockService;
let categoryService: CategoryService;
let category: Category | null;
let block: Block | null;
let blockToDelete: Block | null;
let hasNextBlocks: Block | null;
let hasPreviousBlocks: Block | null;
let category: Category;
let block: Block;
let blockToDelete: Block;
let hasNextBlocks: Block;
let hasPreviousBlocks: Block;
const FIELDS_TO_POPULATE = [
'trigger_labels',
'assign_labels',
@ -142,18 +142,19 @@ describe('BlockController', () => {
blockController = module.get<BlockController>(BlockController);
blockService = module.get<BlockService>(BlockService);
categoryService = module.get<CategoryService>(CategoryService);
category = await categoryService.findOne({ label: 'default' });
block = await blockService.findOne({ name: 'first' });
blockToDelete = await blockService.findOne({ name: 'buttons' });
hasNextBlocks = await blockService.findOne({
category = (await categoryService.findOne({ label: 'default' }))!;
block = (await blockService.findOne({ name: 'first' }))!;
blockToDelete = (await blockService.findOne({ name: 'buttons' }))!;
hasNextBlocks = (await blockService.findOne({
name: 'hasNextBlocks',
});
hasPreviousBlocks = await blockService.findOne({
}))!;
hasPreviousBlocks = (await blockService.findOne({
name: 'hasPreviousBlocks',
});
}))!;
});
afterEach(jest.clearAllMocks);
afterAll(closeInMongodConnection);
describe('find', () => {
@ -162,9 +163,9 @@ describe('BlockController', () => {
const result = await blockController.find([], {});
const blocksWithCategory = blockFixtures.map((blockFixture) => ({
...blockFixture,
category: category!.id,
category: category.id,
nextBlocks:
blockFixture.name === 'hasNextBlocks' ? [hasPreviousBlocks!.id] : [],
blockFixture.name === 'hasNextBlocks' ? [hasPreviousBlocks.id] : [],
}));
expect(blockService.find).toHaveBeenCalledWith({}, undefined);
@ -196,13 +197,13 @@ describe('BlockController', () => {
describe('findOne', () => {
it('should find one block by id', async () => {
jest.spyOn(blockService, 'findOne');
const result = await blockController.findOne(hasNextBlocks!.id, []);
expect(blockService.findOne).toHaveBeenCalledWith(hasNextBlocks!.id);
const result = await blockController.findOne(hasNextBlocks.id, []);
expect(blockService.findOne).toHaveBeenCalledWith(hasNextBlocks.id);
expect(result).toEqualPayload(
{
...blockFixtures.find(({ name }) => name === hasNextBlocks!.name),
category: category!.id,
nextBlocks: [hasPreviousBlocks!.id],
...blockFixtures.find(({ name }) => name === hasNextBlocks.name),
category: category.id,
nextBlocks: [hasPreviousBlocks.id],
},
[...IGNORED_TEST_FIELDS, 'attachedToBlock'],
);
@ -211,11 +212,11 @@ describe('BlockController', () => {
it('should find one block by id, and populate its category and previousBlocks', async () => {
jest.spyOn(blockService, 'findOneAndPopulate');
const result = await blockController.findOne(
hasPreviousBlocks!.id,
hasPreviousBlocks.id,
FIELDS_TO_POPULATE,
);
expect(blockService.findOneAndPopulate).toHaveBeenCalledWith(
hasPreviousBlocks!.id,
hasPreviousBlocks.id,
);
expect(result).toEqualPayload({
...blockFixtures.find(({ name }) => name === 'hasPreviousBlocks'),
@ -227,12 +228,12 @@ describe('BlockController', () => {
it('should find one block by id, and populate its category and an empty previousBlocks', async () => {
jest.spyOn(blockService, 'findOneAndPopulate');
block = await blockService.findOne({ name: 'attachment' });
block = (await blockService.findOne({ name: 'attachment' }))!;
const result = await blockController.findOne(
block!.id,
block.id,
FIELDS_TO_POPULATE,
);
expect(blockService.findOneAndPopulate).toHaveBeenCalledWith(block!.id);
expect(blockService.findOneAndPopulate).toHaveBeenCalledWith(block.id);
expect(result).toEqualPayload({
...blockFixtures.find(({ name }) => name === 'attachment'),
category,
@ -247,12 +248,12 @@ describe('BlockController', () => {
jest.spyOn(blockService, 'create');
const mockedBlockCreateDto: BlockCreateDto = {
name: 'block with nextBlocks',
nextBlocks: [hasNextBlocks!.id],
nextBlocks: [hasNextBlocks.id],
patterns: ['Hi'],
trigger_labels: [],
assign_labels: [],
trigger_channels: [],
category: category!.id,
category: category.id,
options: {
typing: 0,
fallback: {
@ -284,17 +285,15 @@ describe('BlockController', () => {
describe('deleteOne', () => {
it('should delete block', async () => {
jest.spyOn(blockService, 'deleteOne');
const result = await blockController.deleteOne(blockToDelete!.id);
const result = await blockController.deleteOne(blockToDelete.id);
expect(blockService.deleteOne).toHaveBeenCalledWith(blockToDelete!.id);
expect(blockService.deleteOne).toHaveBeenCalledWith(blockToDelete.id);
expect(result).toEqual({ acknowledged: true, deletedCount: 1 });
});
it('should throw NotFoundException when attempting to delete a block by id', async () => {
await expect(
blockController.deleteOne(blockToDelete!.id),
).rejects.toThrow(
new NotFoundException(`Block with ID ${blockToDelete!.id} not found`),
await expect(blockController.deleteOne(blockToDelete.id)).rejects.toThrow(
new NotFoundException(`Block with ID ${blockToDelete.id} not found`),
);
});
});
@ -305,16 +304,16 @@ describe('BlockController', () => {
const updateBlock: BlockUpdateDto = {
name: 'modified block name',
};
const result = await blockController.updateOne(block!.id, updateBlock);
const result = await blockController.updateOne(block.id, updateBlock);
expect(blockService.updateOne).toHaveBeenCalledWith(
block!.id,
block.id,
updateBlock,
);
expect(result).toEqualPayload(
{
...blockFixtures.find(({ name }) => name === block!.name),
category: category!.id,
...blockFixtures.find(({ name }) => name === block.name),
category: category.id,
...updateBlock,
},
[...IGNORED_TEST_FIELDS, 'attachedToBlock'],
@ -327,9 +326,9 @@ describe('BlockController', () => {
};
await expect(
blockController.updateOne(blockToDelete!.id, updateBlock),
blockController.updateOne(blockToDelete.id, updateBlock),
).rejects.toThrow(
new NotFoundException(`Block with ID ${blockToDelete!.id} not found`),
new NotFoundException(`Block with ID ${blockToDelete.id} not found`),
);
});
});

View File

@ -36,8 +36,8 @@ import { ContextVarController } from './context-var.controller';
describe('ContextVarController', () => {
let contextVarController: ContextVarController;
let contextVarService: ContextVarService;
let contextVar: ContextVar | null;
let contextVarToDelete: ContextVar | null;
let contextVar: ContextVar;
let contextVarToDelete: ContextVar;
beforeAll(async () => {
const module = await Test.createTestingModule({
@ -56,15 +56,16 @@ describe('ContextVarController', () => {
contextVarController =
module.get<ContextVarController>(ContextVarController);
contextVarService = module.get<ContextVarService>(ContextVarService);
contextVar = await contextVarService.findOne({
contextVar = (await contextVarService.findOne({
label: 'test context var 1',
});
contextVarToDelete = await contextVarService.findOne({
}))!;
contextVarToDelete = (await contextVarService.findOne({
label: 'test context var 2',
});
}))!;
});
afterEach(jest.clearAllMocks);
afterAll(closeInMongodConnection);
describe('count', () => {
@ -91,11 +92,11 @@ describe('ContextVarController', () => {
describe('findOne', () => {
it('should return the existing contextVar', async () => {
jest.spyOn(contextVarService, 'findOne');
const result = await contextVarController.findOne(contextVar!.id);
const result = await contextVarController.findOne(contextVar.id);
expect(contextVarService.findOne).toHaveBeenCalledWith(contextVar!.id);
expect(contextVarService.findOne).toHaveBeenCalledWith(contextVar.id);
expect(result).toEqualPayload(
contextVarFixtures.find(({ label }) => label === contextVar!.label)!,
contextVarFixtures.find(({ label }) => label === contextVar.label)!,
);
});
});
@ -121,11 +122,11 @@ describe('ContextVarController', () => {
it('should delete a contextVar by id', async () => {
jest.spyOn(contextVarService, 'deleteOne');
const result = await contextVarController.deleteOne(
contextVarToDelete!.id,
contextVarToDelete.id,
);
expect(contextVarService.deleteOne).toHaveBeenCalledWith(
contextVarToDelete!.id,
contextVarToDelete.id,
);
expect(result).toEqual({
acknowledged: true,
@ -135,10 +136,10 @@ describe('ContextVarController', () => {
it('should throw a NotFoundException when attempting to delete a contextVar by id', async () => {
await expect(
contextVarController.deleteOne(contextVarToDelete!.id),
contextVarController.deleteOne(contextVarToDelete.id),
).rejects.toThrow(
new NotFoundException(
`Context var with ID ${contextVarToDelete!.id} not found.`,
`Context var with ID ${contextVarToDelete.id} not found.`,
),
);
});
@ -152,12 +153,12 @@ describe('ContextVarController', () => {
.spyOn(contextVarService, 'deleteMany')
.mockResolvedValue(deleteResult);
const result = await contextVarController.deleteMany([
contextVarToDelete!.id,
contextVar!.id,
contextVarToDelete.id,
contextVar.id,
]);
expect(contextVarService.deleteMany).toHaveBeenCalledWith({
_id: { $in: [contextVarToDelete!.id, contextVar!.id] },
_id: { $in: [contextVarToDelete.id, contextVar.id] },
});
expect(result).toEqual(deleteResult);
});
@ -175,10 +176,7 @@ describe('ContextVarController', () => {
});
await expect(
contextVarController.deleteMany([
contextVarToDelete!.id,
contextVar!.id,
]),
contextVarController.deleteMany([contextVarToDelete.id, contextVar.id]),
).rejects.toThrow(
new NotFoundException('Context vars with provided IDs not found'),
);
@ -192,16 +190,16 @@ describe('ContextVarController', () => {
it('should return updated contextVar', async () => {
jest.spyOn(contextVarService, 'updateOne');
const result = await contextVarController.updateOne(
contextVar!.id,
contextVar.id,
contextVarUpdatedDto,
);
expect(contextVarService.updateOne).toHaveBeenCalledWith(
contextVar!.id,
contextVar.id,
contextVarUpdatedDto,
);
expect(result).toEqualPayload({
...contextVarFixtures.find(({ label }) => label === contextVar!.label),
...contextVarFixtures.find(({ label }) => label === contextVar.label),
...contextVarUpdatedDto,
});
});
@ -209,12 +207,12 @@ describe('ContextVarController', () => {
it('should throw a NotFoundException when attempting to update an non existing contextVar by id', async () => {
await expect(
contextVarController.updateOne(
contextVarToDelete!.id,
contextVarToDelete.id,
contextVarUpdatedDto,
),
).rejects.toThrow(
new NotFoundException(
`ContextVar with ID ${contextVarToDelete!.id} not found`,
`ContextVar with ID ${contextVarToDelete.id} not found`,
),
);
});

View File

@ -53,10 +53,10 @@ describe('MessageController', () => {
let messageService: MessageService;
let subscriberService: SubscriberService;
let userService: UserService;
let sender: Subscriber | null;
let recipient: Subscriber | null;
let user: User | null;
let message: Message | null;
let sender: Subscriber;
let recipient: Subscriber;
let user: User;
let message: Message;
let allMessages: Message[];
let allUsers: User[];
let allSubscribers: Subscriber[];
@ -128,16 +128,17 @@ describe('MessageController', () => {
userService = module.get<UserService>(UserService);
subscriberService = module.get<SubscriberService>(SubscriberService);
messageController = module.get<MessageController>(MessageController);
message = await messageService.findOne({ mid: 'mid-1' });
sender = await subscriberService.findOne(message!.sender!);
recipient = await subscriberService.findOne(message!.recipient!);
user = await userService.findOne(message!.sentBy!);
message = (await messageService.findOne({ mid: 'mid-1' }))!;
sender = (await subscriberService.findOne(message.sender!))!;
recipient = (await subscriberService.findOne(message.recipient!))!;
user = (await userService.findOne(message.sentBy!))!;
allSubscribers = await subscriberService.findAll();
allUsers = await userService.findAll();
allMessages = await messageService.findAll();
});
afterEach(jest.clearAllMocks);
afterAll(closeInMongodConnection);
describe('count', () => {
@ -153,31 +154,31 @@ describe('MessageController', () => {
describe('findOne', () => {
it('should find message by id, and populate its corresponding sender and recipient', async () => {
jest.spyOn(messageService, 'findOneAndPopulate');
const result = await messageController.findOne(message!.id, [
const result = await messageController.findOne(message.id, [
'sender',
'recipient',
]);
expect(messageService.findOneAndPopulate).toHaveBeenCalledWith(
message!.id,
message.id,
);
expect(result).toEqualPayload({
...messageFixtures.find(({ mid }) => mid === message!.mid),
...messageFixtures.find(({ mid }) => mid === message.mid),
sender,
recipient,
sentBy: user!.id,
sentBy: user.id,
});
});
it('should find message by id', async () => {
jest.spyOn(messageService, 'findOne');
const result = await messageController.findOne(message!.id, []);
const result = await messageController.findOne(message.id, []);
expect(messageService.findOne).toHaveBeenCalledWith(message!.id);
expect(messageService.findOne).toHaveBeenCalledWith(message.id);
expect(result).toEqualPayload({
...messageFixtures.find(({ mid }) => mid === message!.mid),
sender: sender!.id,
recipient: recipient!.id,
sentBy: user!.id,
...messageFixtures.find(({ mid }) => mid === message.mid),
sender: sender.id,
recipient: recipient.id,
sentBy: user.id,
});
});
});

View File

@ -48,7 +48,7 @@ describe('SubscriberController', () => {
let subscriberService: SubscriberService;
let labelService: LabelService;
let userService: UserService;
let subscriber: Subscriber | null;
let subscriber: Subscriber;
let allLabels: Label[];
let allSubscribers: Subscriber[];
let allUsers: User[];
@ -90,15 +90,16 @@ describe('SubscriberController', () => {
subscriberController =
module.get<SubscriberController>(SubscriberController);
subscriber = await subscriberService.findOne({
subscriber = (await subscriberService.findOne({
first_name: 'Jhon',
});
}))!;
allLabels = await labelService.findAll();
allSubscribers = await subscriberService.findAll();
allUsers = await userService.findAll();
});
afterEach(jest.clearAllMocks);
afterAll(closeInMongodConnection);
describe('count', () => {
@ -114,39 +115,38 @@ describe('SubscriberController', () => {
describe('findOne', () => {
it('should find one subscriber by id', async () => {
jest.spyOn(subscriberService, 'findOne');
const result = await subscriberService.findOne(subscriber!.id);
const result = await subscriberService.findOne(subscriber.id);
const labelIDs = allLabels
.filter((label) => subscriber!.labels.includes(label.id))
.filter((label) => subscriber.labels.includes(label.id))
.map(({ id }) => id);
expect(subscriberService.findOne).toHaveBeenCalledWith(subscriber!.id);
expect(subscriberService.findOne).toHaveBeenCalledWith(subscriber.id);
expect(result).toEqualPayload({
...subscriberFixtures.find(
({ first_name }) => first_name === subscriber!.first_name,
({ first_name }) => first_name === subscriber.first_name,
),
labels: labelIDs,
assignedTo: allUsers.find(({ id }) => subscriber!.assignedTo === id)
?.id,
assignedTo: allUsers.find(({ id }) => subscriber.assignedTo === id)?.id,
});
});
it('should find one subscriber by id, and populate its corresponding labels', async () => {
jest.spyOn(subscriberService, 'findOneAndPopulate');
const result = await subscriberController.findOne(subscriber!.id, [
const result = await subscriberController.findOne(subscriber.id, [
'labels',
]);
expect(subscriberService.findOneAndPopulate).toHaveBeenCalledWith(
subscriber!.id,
subscriber.id,
);
expect(result).toEqualPayload({
...subscriberFixtures.find(
({ first_name }) => first_name === subscriber!.first_name,
({ first_name }) => first_name === subscriber.first_name,
),
labels: allLabels.filter((label) =>
subscriber!.labels.includes(label.id),
subscriber.labels.includes(label.id),
),
assignedTo: allUsers.find(({ id }) => subscriber!.assignedTo === id),
assignedTo: allUsers.find(({ id }) => subscriber.assignedTo === id),
});
});
});
@ -178,7 +178,7 @@ describe('SubscriberController', () => {
({ labels, ...rest }) => ({
...rest,
labels: allLabels.filter((label) => labels.includes(label.id)),
assignedTo: allUsers.find(({ id }) => subscriber!.assignedTo === id),
assignedTo: allUsers.find(({ id }) => subscriber.assignedTo === id),
}),
);

View File

@ -31,9 +31,9 @@ describe('BlockRepository', () => {
let blockRepository: BlockRepository;
let categoryRepository: CategoryRepository;
let blockModel: Model<Block>;
let category: Category | null;
let hasPreviousBlocks: Block | null;
let hasNextBlocks: Block | null;
let category: Category;
let hasPreviousBlocks: Block;
let hasNextBlocks: Block;
let validIds: string[];
let validCategory: string;
@ -51,13 +51,13 @@ describe('BlockRepository', () => {
validIds = ['64abc1234def567890fedcba', '64abc1234def567890fedcbc'];
validCategory = '64def5678abc123490fedcba';
category = await categoryRepository.findOne({ label: 'default' });
hasPreviousBlocks = await blockRepository.findOne({
category = (await categoryRepository.findOne({ label: 'default' }))!;
hasPreviousBlocks = (await blockRepository.findOne({
name: 'hasPreviousBlocks',
});
hasNextBlocks = await blockRepository.findOne({
}))!;
hasNextBlocks = (await blockRepository.findOne({
name: 'hasNextBlocks',
});
}))!;
});
afterEach(jest.clearAllMocks);
@ -67,15 +67,13 @@ describe('BlockRepository', () => {
it('should find one block by id, and populate its trigger_labels, assign_labels, nextBlocks, attachedBlock, category,previousBlocks', async () => {
jest.spyOn(blockModel, 'findById');
const result = await blockRepository.findOneAndPopulate(
hasNextBlocks!.id,
);
const result = await blockRepository.findOneAndPopulate(hasNextBlocks.id);
expect(blockModel.findById).toHaveBeenCalledWith(
hasNextBlocks!.id,
hasNextBlocks.id,
undefined,
);
expect(result).toEqualPayload({
...blockFixtures.find(({ name }) => name === hasNextBlocks!.name),
...blockFixtures.find(({ name }) => name === hasNextBlocks.name),
category,
nextBlocks: [hasPreviousBlocks],
previousBlocks: [],

View File

@ -62,23 +62,20 @@ describe('MessageRepository', () => {
describe('findOneAndPopulate', () => {
it('should find one message by id, and populate its sender and recipient', async () => {
jest.spyOn(messageModel, 'findById');
const message = await messageRepository.findOne({ mid: 'mid-1' });
const message = (await messageRepository.findOne({ mid: 'mid-1' }))!;
const sender = await subscriberRepository.findOne(message!['sender']);
const recipient = await subscriberRepository.findOne(
message!['recipient'],
);
const user = await userRepository.findOne(message!['sentBy']);
const result = await messageRepository.findOneAndPopulate(message!.id);
const user = (await userRepository.findOne(message!['sentBy']))!;
const result = await messageRepository.findOneAndPopulate(message.id);
expect(messageModel.findById).toHaveBeenCalledWith(
message!.id,
undefined,
);
expect(messageModel.findById).toHaveBeenCalledWith(message.id, undefined);
expect(result).toEqualPayload({
...messageFixtures.find(({ mid }) => mid === message!.mid),
...messageFixtures.find(({ mid }) => mid === message.mid),
sender,
recipient,
sentBy: user!.id,
sentBy: user.id,
});
});
});

View File

@ -97,30 +97,31 @@ describe('SubscriberRepository', () => {
});
afterEach(jest.clearAllMocks);
afterAll(closeInMongodConnection);
describe('findOneAndPopulate', () => {
it('should find one subscriber by id,and populate its labels', async () => {
jest.spyOn(subscriberModel, 'findById');
const subscriber = await subscriberRepository.findOne({
const subscriber = (await subscriberRepository.findOne({
first_name: 'Jhon',
});
}))!;
const allLabels = await labelRepository.findAll();
const result = await subscriberRepository.findOneAndPopulate(
subscriber!.id,
subscriber.id,
);
const subscriberWithLabels = {
...subscriberFixtures.find(
({ first_name }) => first_name === subscriber!.first_name,
({ first_name }) => first_name === subscriber.first_name,
),
labels: allLabels.filter((label) =>
subscriber!.labels.includes(label.id),
subscriber.labels.includes(label.id),
),
assignedTo: allUsers.find(({ id }) => subscriber!.assignedTo === id),
assignedTo: allUsers.find(({ id }) => subscriber.assignedTo === id),
};
expect(subscriberModel.findById).toHaveBeenCalledWith(
subscriber!.id,
subscriber.id,
undefined,
);
expect(result).toEqualPayload(subscriberWithLabels);

View File

@ -74,10 +74,10 @@ import { CategoryService } from './category.service';
describe('BlockService', () => {
let blockRepository: BlockRepository;
let categoryRepository: CategoryRepository;
let category: Category | null;
let block: Block | null;
let category: Category;
let block: Block;
let blockService: BlockService;
let hasPreviousBlocks: Block | null;
let hasPreviousBlocks: Block;
let contentService: ContentService;
let contentTypeService: ContentTypeService;
let settingService: SettingService;
@ -154,11 +154,11 @@ describe('BlockService', () => {
contentTypeService = module.get<ContentTypeService>(ContentTypeService);
categoryRepository = module.get<CategoryRepository>(CategoryRepository);
blockRepository = module.get<BlockRepository>(BlockRepository);
category = await categoryRepository.findOne({ label: 'default' });
hasPreviousBlocks = await blockRepository.findOne({
category = (await categoryRepository.findOne({ label: 'default' }))!;
hasPreviousBlocks = (await blockRepository.findOne({
name: 'hasPreviousBlocks',
});
block = await blockRepository.findOne({ name: 'hasNextBlocks' });
}))!;
block = (await blockRepository.findOne({ name: 'hasNextBlocks' }))!;
settings = await settingService.getSettings();
});
@ -168,10 +168,10 @@ describe('BlockService', () => {
describe('findOneAndPopulate', () => {
it('should find one block by id, and populate its trigger_labels, assign_labels,attachedBlock,category,nextBlocks', async () => {
jest.spyOn(blockRepository, 'findOneAndPopulate');
const result = await blockService.findOneAndPopulate(block!.id);
const result = await blockService.findOneAndPopulate(block.id);
expect(blockRepository.findOneAndPopulate).toHaveBeenCalledWith(
block!.id,
block.id,
undefined,
);
expect(result).toEqualPayload({
@ -441,8 +441,10 @@ describe('BlockService', () => {
describe('processMessage', () => {
it('should process list message (with limit = 2 and skip = 0)', async () => {
const contentType = await contentTypeService.findOne({ name: 'Product' });
blockProductListMock.options!.content!.entity = contentType!.id;
const contentType = (await contentTypeService.findOne({
name: 'Product',
}))!;
blockProductListMock.options.content!.entity = contentType.id;
const result = await blockService.processMessage(
blockProductListMock,
{
@ -454,27 +456,29 @@ describe('BlockService', () => {
'conv_id',
);
const elements = await contentService.findPage(
{ status: true, entity: contentType!.id },
{ status: true, entity: contentType.id },
{ skip: 0, limit: 2, sort: ['createdAt', 'desc'] },
);
const flattenedElements = elements.map(Content.toElement);
expect(result!.format).toEqualPayload(
blockProductListMock.options!.content!.display,
expect(result.format).toEqualPayload(
blockProductListMock.options.content!.display,
);
expect(
(result!.message as StdOutgoingListMessage).elements,
(result.message as StdOutgoingListMessage).elements,
).toEqualPayload(flattenedElements);
expect((result.message as StdOutgoingListMessage).options).toEqualPayload(
blockProductListMock.options.content!,
);
expect(
(result!.message as StdOutgoingListMessage).options,
).toEqualPayload(blockProductListMock.options!.content!);
expect(
(result!.message as StdOutgoingListMessage).pagination,
(result.message as StdOutgoingListMessage).pagination,
).toEqualPayload({ total: 4, skip: 0, limit: 2 });
});
it('should process list message (with limit = 2 and skip = 2)', async () => {
const contentType = await contentTypeService.findOne({ name: 'Product' });
blockProductListMock.options!.content!.entity = contentType!.id;
const contentType = (await contentTypeService.findOne({
name: 'Product',
}))!;
blockProductListMock.options.content!.entity = contentType.id;
const result = await blockService.processMessage(
blockProductListMock,
{
@ -486,20 +490,20 @@ describe('BlockService', () => {
'conv_id',
);
const elements = await contentService.findPage(
{ status: true, entity: contentType!.id },
{ status: true, entity: contentType.id },
{ skip: 2, limit: 2, sort: ['createdAt', 'desc'] },
);
const flattenedElements = elements.map(Content.toElement);
expect(result!.format).toEqual(
blockProductListMock.options!.content?.display,
expect(result.format).toEqual(
blockProductListMock.options.content?.display,
);
expect((result!.message as StdOutgoingListMessage).elements).toEqual(
expect((result.message as StdOutgoingListMessage).elements).toEqual(
flattenedElements,
);
expect((result!.message as StdOutgoingListMessage).options).toEqual(
blockProductListMock.options!.content,
expect((result.message as StdOutgoingListMessage).options).toEqual(
blockProductListMock.options.content,
);
expect((result!.message as StdOutgoingListMessage).pagination).toEqual({
expect((result.message as StdOutgoingListMessage).pagination).toEqual({
total: 4,
skip: 2,
limit: 2,

View File

@ -440,7 +440,7 @@ export class BlockService extends BaseService<
subscriberContext: SubscriberContext,
fallback = false,
conversationId?: string,
) {
): Promise<StdOutgoingEnvelope> {
const settings = await this.settingService.getSettings();
const blockMessage: BlockMessage =
fallback && block.options?.fallback
@ -592,13 +592,18 @@ export class BlockService extends BaseService<
);
// Process custom plugin block
try {
return await plugin?.process(block, context, conversationId);
const envelope = await plugin?.process(block, context, conversationId);
if (!envelope) {
throw new Error('Unable to find envelope');
}
return envelope;
} catch (e) {
this.logger.error('Plugin was unable to load/process ', e);
throw new Error(`Unknown plugin - ${JSON.stringify(blockMessage)}`);
}
} else {
throw new Error('Invalid message format.');
}
throw new Error('Invalid message format.');
}
}

View File

@ -21,10 +21,7 @@ import {
getDefaultConversationContext,
} from '../schemas/conversation.schema';
import { Context } from '../schemas/types/context';
import {
IncomingMessageType,
StdOutgoingEnvelope,
} from '../schemas/types/message';
import { IncomingMessageType } from '../schemas/types/message';
import { SubscriberContext } from '../schemas/types/subscriberContext';
import { BlockService } from './block.service';
@ -71,13 +68,13 @@ export class BotService {
);
// Process message : Replace tokens with context data and then send the message
const recipient = event.getSender();
const envelope = (await this.blockService.processMessage(
const envelope = await this.blockService.processMessage(
block,
context,
recipient?.context as SubscriberContext,
fallback,
conservationId,
)) as StdOutgoingEnvelope;
);
// Send message through the right channel
const response = await event
@ -258,7 +255,7 @@ export class BotService {
convo.context.attempt++;
fallback = true;
} else {
if (convo.context) convo.context.attempt = 0;
convo.context.attempt = 0;
fallbackBlock = undefined;
}

View File

@ -296,7 +296,9 @@ export class ChatService {
@OnEvent('hook:subscriber:postCreate')
async onSubscriberCreate({ _id }: SubscriberDocument) {
const subscriber = await this.subscriberService.findOne(_id);
if (subscriber) this.websocketGateway.broadcastSubscriberNew(subscriber);
if (subscriber) {
this.websocketGateway.broadcastSubscriberNew(subscriber);
}
}
/**
@ -307,6 +309,8 @@ export class ChatService {
@OnEvent('hook:subscriber:postUpdate')
async onSubscriberUpdate({ _id }: SubscriberDocument) {
const subscriber = await this.subscriberService.findOne(_id);
if (subscriber) this.websocketGateway.broadcastSubscriberUpdate(subscriber);
if (subscriber) {
this.websocketGateway.broadcastSubscriberUpdate(subscriber);
}
}
}

View File

@ -36,7 +36,7 @@ export class ContextVarService extends BaseService<
block: Block | BlockFull,
): Promise<Record<string, ContextVar>> {
const vars = await this.find({
name: { $in: block.capture_vars?.map(({ context_var }) => context_var) },
name: { $in: block.capture_vars.map(({ context_var }) => context_var) },
});
return vars.reduce((acc, cv) => {
acc[cv.name] = cv;

View File

@ -71,8 +71,6 @@ export class ConversationService extends BaseService<
const msgType = event.getMessageType();
const profile = event.getSender();
if (!convo.context) throw new Error('Missing conversation context');
// Capture channel specific context data
convo.context.channel = event.getHandler().getName();
convo.context.text = event.getText();

View File

@ -48,11 +48,11 @@ describe('MessageService', () => {
let allMessages: Message[];
let allSubscribers: Subscriber[];
let allUsers: User[];
let message: Message | null;
let sender: Subscriber | null;
let recipient: Subscriber | null;
let message: Message;
let sender: Subscriber;
let recipient: Subscriber;
let messagesWithSenderAndRecipient: Message[];
let user: User | null;
let user: User;
beforeAll(async () => {
const module = await Test.createTestingModule({
@ -90,10 +90,10 @@ describe('MessageService', () => {
allSubscribers = await subscriberRepository.findAll();
allUsers = await userRepository.findAll();
allMessages = await messageRepository.findAll();
message = await messageRepository.findOne({ mid: 'mid-1' });
sender = await subscriberRepository.findOne(message!.sender!);
recipient = await subscriberRepository.findOne(message!.recipient!);
user = await userRepository.findOne(message!.sentBy!);
message = (await messageRepository.findOne({ mid: 'mid-1' }))!;
sender = (await subscriberRepository.findOne(message.sender!))!;
recipient = (await subscriberRepository.findOne(message.recipient!))!;
user = (await userRepository.findOne(message.sentBy!))!;
messagesWithSenderAndRecipient = allMessages.map((message) => ({
...message,
sender: allSubscribers.find(({ id }) => id === message.sender)?.id,
@ -108,17 +108,17 @@ describe('MessageService', () => {
describe('findOneAndPopulate', () => {
it('should find message by id, and populate its corresponding sender and recipient', async () => {
jest.spyOn(messageRepository, 'findOneAndPopulate');
const result = await messageService.findOneAndPopulate(message!.id);
const result = await messageService.findOneAndPopulate(message.id);
expect(messageRepository.findOneAndPopulate).toHaveBeenCalledWith(
message!.id,
message.id,
undefined,
);
expect(result).toEqualPayload({
...messageFixtures.find(({ mid }) => mid === message!.mid),
...messageFixtures.find(({ mid }) => mid === message.mid),
sender,
recipient,
sentBy: user!.id,
sentBy: user.id,
});
});
});

View File

@ -90,20 +90,20 @@ describe('SubscriberService', () => {
describe('findOneAndPopulate', () => {
it('should find subscribers, and foreach subscriber populate its corresponding labels', async () => {
jest.spyOn(subscriberService, 'findOneAndPopulate');
const subscriber = await subscriberRepository.findOne({
const subscriber = (await subscriberRepository.findOne({
first_name: 'Jhon',
});
const result = await subscriberService.findOneAndPopulate(subscriber!.id);
}))!;
const result = await subscriberService.findOneAndPopulate(subscriber.id);
expect(subscriberService.findOneAndPopulate).toHaveBeenCalledWith(
subscriber!.id,
subscriber.id,
);
expect(result).toEqualPayload({
...subscriber,
labels: allLabels.filter((label) =>
subscriber!.labels.includes(label.id),
subscriber.labels.includes(label.id),
),
assignedTo: allUsers.find(({ id }) => subscriber!.assignedTo === id),
assignedTo: allUsers.find(({ id }) => subscriber.assignedTo === id),
});
});
});
@ -133,13 +133,13 @@ describe('SubscriberService', () => {
await subscriberService.findOneByForeignId('foreign-id-dimelo');
const subscriber = allSubscribers.find(
({ foreign_id }) => foreign_id === 'foreign-id-dimelo',
);
)!;
expect(subscriberRepository.findOneByForeignId).toHaveBeenCalled();
expect(result).toEqualPayload({
...subscriber,
labels: allLabels
.filter((label) => subscriber!.labels.includes(label.id))
.filter((label) => subscriber.labels.includes(label.id))
.map((label) => label.id),
});
});

View File

@ -58,6 +58,9 @@ const conversations: ConversationCreateDto[] = [
labels: [],
assignedTo: null,
channel: { name: 'messenger-channel' },
avatar: null,
context: {},
assignedAt: new Date(),
},
skip: {},
attempt: 0,
@ -104,6 +107,9 @@ const conversations: ConversationCreateDto[] = [
labels: [],
assignedTo: null,
channel: { name: 'web-channel' },
avatar: null,
context: {},
assignedAt: new Date(),
},
skip: {},
attempt: 0,
@ -136,9 +142,9 @@ export const installConversationTypeFixtures = async () => {
conversationFixtures.map((conversationFixture) => ({
...conversationFixture,
sender: subscribers[parseInt(conversationFixture.sender)].id,
current: conversationFixture?.current
? blocks[parseInt(conversationFixture.current)].id
: null,
current: conversationFixture.current
? blocks[parseInt(conversationFixture.current)]?.id
: undefined,
next: conversationFixture.next?.map((n) => blocks[parseInt(n)].id),
})),
);