import { ForbiddenException } from "@nestjs/common"; import { Test, TestingModule } from "@nestjs/testing"; import { EventsGateway } from "../realtime/events.gateway"; import { MessagesService } from "./messages.service"; import { MessagesRepository } from "./repositories/messages.repository"; describe("MessagesService", () => { let service: MessagesService; let repository: MessagesRepository; let eventsGateway: EventsGateway; const mockMessagesRepository = { findConversationBetweenUsers: jest.fn(), createConversation: jest.fn(), addParticipant: jest.fn(), createMessage: jest.fn(), findAllConversations: jest.fn(), isParticipant: jest.fn(), findMessagesByConversationId: jest.fn(), }; const mockEventsGateway = { sendToUser: jest.fn(), }; beforeEach(async () => { const module: TestingModule = await Test.createTestingModule({ providers: [ MessagesService, { provide: MessagesRepository, useValue: mockMessagesRepository }, { provide: EventsGateway, useValue: mockEventsGateway }, ], }).compile(); service = module.get(MessagesService); repository = module.get(MessagesRepository); eventsGateway = module.get(EventsGateway); }); describe("sendMessage", () => { it("should send message to existing conversation", async () => { const senderId = "s1"; const dto = { recipientId: "r1", text: "hello" }; mockMessagesRepository.findConversationBetweenUsers.mockResolvedValue({ id: "conv1" }); mockMessagesRepository.createMessage.mockResolvedValue({ id: "m1", text: "hello" }); const result = await service.sendMessage(senderId, dto); expect(result.id).toBe("m1"); expect(mockEventsGateway.sendToUser).toHaveBeenCalledWith("r1", "new_message", expect.anything()); }); it("should create new conversation if not exists", async () => { const senderId = "s1"; const dto = { recipientId: "r1", text: "hello" }; mockMessagesRepository.findConversationBetweenUsers.mockResolvedValue(null); mockMessagesRepository.createConversation.mockResolvedValue({ id: "new_conv" }); mockMessagesRepository.createMessage.mockResolvedValue({ id: "m1" }); await service.sendMessage(senderId, dto); expect(mockMessagesRepository.createConversation).toHaveBeenCalled(); expect(mockMessagesRepository.addParticipant).toHaveBeenCalledTimes(2); }); }); describe("getMessages", () => { it("should return messages if user is participant", async () => { mockMessagesRepository.isParticipant.mockResolvedValue(true); mockMessagesRepository.findMessagesByConversationId.mockResolvedValue([{ id: "m1" }]); const result = await service.getMessages("u1", "conv1"); expect(result).toHaveLength(1); }); it("should throw ForbiddenException if user is not participant", async () => { mockMessagesRepository.isParticipant.mockResolvedValue(false); await expect(service.getMessages("u1", "conv1")).rejects.toThrow(ForbiddenException); }); }); });