'use strict' const GroupChat = require('../models/GroupChat') const { sseSend } = require('../services/sse') function extractAuth(req) { const accountId = req.teamAccount?.accountId || req.admin?.id || null const tenantId = req.tenantId || req.teamAccount?.tenantId || req.admin?.tenant_id || null return { accountId, tenantId } } class GroupChatController { /** * GET /api/admin/inbox/groups * Lista grupos do colaborador (via team_members) ou todos (owner/manager) */ async list(req, res) { try { const { accountId, tenantId } = extractAuth(req) if (!tenantId) return res.status(401).json({ error: 'Não autenticado' }) const role = req.admin?.role || req.teamAccount?.role const isManager = role === 'owner' || role === 'manager' const groups = isManager ? await GroupChat.listAll(tenantId, accountId) : await GroupChat.listForAccount(tenantId, accountId) res.json(groups) } catch (err) { console.error('[groupChat.list]', err.message) res.status(500).json({ error: 'Erro ao listar grupos' }) } } /** * GET /api/admin/inbox/groups/:id/messages * Histórico de mensagens de um grupo */ async getMessages(req, res) { try { const { tenantId } = extractAuth(req) if (!tenantId) return res.status(401).json({ error: 'Não autenticado' }) const groupChatId = Number(req.params.id) const limit = Math.min(Number(req.query.limit) || 50, 200) const before = req.query.before || null const group = await GroupChat.findById(tenantId, groupChatId) if (!group) return res.status(404).json({ error: 'Grupo não encontrado' }) const msgs = await GroupChat.getMessages(tenantId, groupChatId, limit, before) res.json(msgs) } catch (err) { console.error('[groupChat.getMessages]', err.message) res.status(500).json({ error: 'Erro ao buscar mensagens' }) } } /** * POST /api/admin/inbox/groups/:id/message * Enviar mensagem em um grupo */ async sendMessage(req, res) { try { const { accountId, tenantId } = extractAuth(req) if (!accountId || !tenantId) return res.status(401).json({ error: 'Não autenticado' }) const groupChatId = Number(req.params.id) const { content } = req.body if (!content?.trim()) return res.status(400).json({ error: 'content obrigatório' }) const group = await GroupChat.findById(tenantId, groupChatId) if (!group) return res.status(404).json({ error: 'Grupo não encontrado' }) const msg = await GroupChat.sendMessage(tenantId, groupChatId, accountId, content.trim()) res.json(msg) // Notificar membros do grupo via SSE (exceto o remetente) const memberIds = await GroupChat.getMemberIds(groupChatId) const payload = { id: msg.id, group_chat_id: groupChatId, group_name: group.name, from: accountId, content: content.trim(), created_at: msg.created_at, } for (const memberId of memberIds) { if (memberId !== accountId) { sseSend(memberId, 'group_message.new', payload) } } } catch (err) { console.error('[groupChat.sendMessage]', err.message) res.status(500).json({ error: 'Erro ao enviar mensagem' }) } } /** * GET /api/admin/inbox/groups/:id/members * Listar membros de um grupo */ async getMembers(req, res) { try { const { tenantId } = extractAuth(req) if (!tenantId) return res.status(401).json({ error: 'Não autenticado' }) const groupChatId = Number(req.params.id) const group = await GroupChat.findById(tenantId, groupChatId) if (!group) return res.status(404).json({ error: 'Grupo não encontrado' }) const members = await GroupChat.getMembers(tenantId, groupChatId) res.json(members) } catch (err) { console.error('[groupChat.getMembers]', err.message) res.status(500).json({ error: 'Erro ao buscar membros' }) } } /** * POST /api/admin/inbox/groups/:id/read * Marcar grupo como lido */ async markRead(req, res) { try { const { accountId } = extractAuth(req) if (!accountId) return res.status(401).json({ error: 'Não autenticado' }) await GroupChat.markRead(accountId, Number(req.params.id)) res.json({ ok: true }) } catch (err) { console.error('[groupChat.markRead]', err.message) res.status(500).json({ error: 'Erro ao marcar como lido' }) } } } module.exports = new GroupChatController()