diff --git a/src/support-chat/support-chat.service.ts b/src/support-chat/support-chat.service.ts index e4beff0..ce6df65 100644 --- a/src/support-chat/support-chat.service.ts +++ b/src/support-chat/support-chat.service.ts @@ -10,50 +10,40 @@ import { SupportChatStatus } from '@prisma/client'; export class SupportChatService { constructor(private readonly prisma: PrismaService) {} - /** - * Get or create an OPEN support chat for a user - */ - async getOrCreateChat(userId: string) { - // Find existing OPEN chat - let chat = await this.prisma.supportChat.findFirst({ - where: { userId, status: SupportChatStatus.OPEN }, - include: { - user: { - select: { - id: true, - email: true, - userProfile: { - select: { firstName: true, lastName: true, avatar: true }, - }, - agentProfile: { - select: { firstName: true, lastName: true, avatar: true }, - }, - }, + private readonly chatInclude = { + user: { + select: { + id: true, + email: true, + userProfile: { + select: { firstName: true, lastName: true, avatar: true }, + }, + agentProfile: { + select: { firstName: true, lastName: true, avatar: true }, }, }, - }); + }, + }; - if (!chat) { - chat = await this.prisma.supportChat.create({ - data: { userId }, - include: { - user: { - select: { - id: true, - email: true, - userProfile: { - select: { firstName: true, lastName: true, avatar: true }, - }, - agentProfile: { - select: { firstName: true, lastName: true, avatar: true }, - }, - }, - }, - }, + /** + * Get or create an OPEN support chat for a user. + * Uses a transaction to prevent race conditions creating duplicates. + */ + async getOrCreateChat(userId: string) { + return this.prisma.$transaction(async (tx) => { + // Find existing OPEN chat + const existing = await tx.supportChat.findFirst({ + where: { userId, status: SupportChatStatus.OPEN }, + include: this.chatInclude, }); - } - return chat; + if (existing) return existing; + + return tx.supportChat.create({ + data: { userId }, + include: this.chatInclude, + }); + }); } /**