feat: inicializacion de Help Desk segun estandar Telcotronics con bitacora de errores e integracion MCP
This commit is contained in:
@@ -0,0 +1,44 @@
|
||||
const db = require('../config/db');
|
||||
|
||||
const Company = {
|
||||
findAll: async () => {
|
||||
const [rows] = await db.query('SELECT * FROM companies ORDER BY created_at DESC');
|
||||
return rows;
|
||||
},
|
||||
findById: async (id) => {
|
||||
const [rows] = await db.query('SELECT * FROM companies WHERE id = ?', [id]);
|
||||
return rows[0];
|
||||
},
|
||||
findBySlug: async (slug) => {
|
||||
const [rows] = await db.query('SELECT * FROM companies WHERE slug = ?', [slug]);
|
||||
return rows[0];
|
||||
},
|
||||
create: async (name, slug, plan = 'free') => {
|
||||
const [result] = await db.query(
|
||||
'INSERT INTO companies (name, slug, plan) VALUES (?, ?, ?)',
|
||||
[name, slug, plan]
|
||||
);
|
||||
return result.insertId;
|
||||
},
|
||||
update: async (id, data) => {
|
||||
const fields = [];
|
||||
const values = [];
|
||||
for (const [key, value] of Object.entries(data)) {
|
||||
fields.push(`${key} = ?`);
|
||||
values.push(value);
|
||||
}
|
||||
if (fields.length === 0) return;
|
||||
values.push(id);
|
||||
await db.query(`UPDATE companies SET ${fields.join(', ')} WHERE id = ?`, values);
|
||||
},
|
||||
countUsers: async (companyId) => {
|
||||
const [rows] = await db.query('SELECT COUNT(*) as total FROM users WHERE company_id = ? AND is_active = 1', [companyId]);
|
||||
return rows[0].total;
|
||||
},
|
||||
countTickets: async (companyId) => {
|
||||
const [rows] = await db.query('SELECT COUNT(*) as total FROM tickets WHERE company_id = ?', [companyId]);
|
||||
return rows[0].total;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = Company;
|
||||
@@ -0,0 +1,27 @@
|
||||
const db = require('../config/db');
|
||||
|
||||
const Department = {
|
||||
findAll: async (companyId) => {
|
||||
const [rows] = await db.query('SELECT * FROM departments WHERE company_id = ? ORDER BY nombre', [companyId]);
|
||||
return rows;
|
||||
},
|
||||
findById: async (id) => {
|
||||
const [rows] = await db.query('SELECT * FROM departments WHERE id = ?', [id]);
|
||||
return rows[0];
|
||||
},
|
||||
create: async (companyId, nombre, descripcion) => {
|
||||
const [result] = await db.query(
|
||||
'INSERT INTO departments (company_id, nombre, descripcion) VALUES (?, ?, ?)',
|
||||
[companyId, nombre, descripcion]
|
||||
);
|
||||
return result.insertId;
|
||||
},
|
||||
update: async (id, nombre, descripcion) => {
|
||||
await db.query('UPDATE departments SET nombre = ?, descripcion = ? WHERE id = ?', [nombre, descripcion, id]);
|
||||
},
|
||||
delete: async (id) => {
|
||||
await db.query('DELETE FROM departments WHERE id = ?', [id]);
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = Department;
|
||||
@@ -0,0 +1,95 @@
|
||||
const db = require('../config/db');
|
||||
|
||||
const Ticket = {
|
||||
findAll: async (companyId) => {
|
||||
const [rows] = await db.query(`
|
||||
SELECT t.*, u.nombre as usuario_nombre, d.nombre as departamento_nombre,
|
||||
a.nombre as asignado_nombre
|
||||
FROM tickets t
|
||||
LEFT JOIN users u ON t.user_id = u.id
|
||||
LEFT JOIN departments d ON t.department_id = d.id
|
||||
LEFT JOIN users a ON t.assigned_to = a.id
|
||||
WHERE t.company_id = ?
|
||||
ORDER BY t.created_at DESC
|
||||
`, [companyId]);
|
||||
return rows;
|
||||
},
|
||||
findByUser: async (companyId, userId) => {
|
||||
const [rows] = await db.query(`
|
||||
SELECT t.*, d.nombre as departamento_nombre, a.nombre as asignado_nombre
|
||||
FROM tickets t
|
||||
LEFT JOIN departments d ON t.department_id = d.id
|
||||
LEFT JOIN users a ON t.assigned_to = a.id
|
||||
WHERE t.company_id = ? AND t.user_id = ?
|
||||
ORDER BY t.created_at DESC
|
||||
`, [companyId, userId]);
|
||||
return rows;
|
||||
},
|
||||
findByAgent: async (companyId, agentId) => {
|
||||
const [rows] = await db.query(`
|
||||
SELECT t.*, u.nombre as usuario_nombre, d.nombre as departamento_nombre
|
||||
FROM tickets t
|
||||
LEFT JOIN users u ON t.user_id = u.id
|
||||
LEFT JOIN departments d ON t.department_id = d.id
|
||||
WHERE t.company_id = ? AND t.assigned_to = ?
|
||||
ORDER BY t.created_at DESC
|
||||
`, [companyId, agentId]);
|
||||
return rows;
|
||||
},
|
||||
findById: async (id) => {
|
||||
const [rows] = await db.query(`
|
||||
SELECT t.*, u.nombre as usuario_nombre, u.email as usuario_email,
|
||||
d.nombre as departamento_nombre, a.nombre as asignado_nombre
|
||||
FROM tickets t
|
||||
LEFT JOIN users u ON t.user_id = u.id
|
||||
LEFT JOIN departments d ON t.department_id = d.id
|
||||
LEFT JOIN users a ON t.assigned_to = a.id
|
||||
WHERE t.id = ?
|
||||
`, [id]);
|
||||
return rows[0];
|
||||
},
|
||||
create: async (companyId, userId, departmentId, asunto, mensaje, prioridad = 'media') => {
|
||||
const [result] = await db.query(
|
||||
'INSERT INTO tickets (company_id, user_id, department_id, asunto, mensaje, prioridad) VALUES (?, ?, ?, ?, ?, ?)',
|
||||
[companyId, userId, departmentId, asunto, mensaje, prioridad]
|
||||
);
|
||||
return result.insertId;
|
||||
},
|
||||
update: async (id, data) => {
|
||||
const fields = [];
|
||||
const values = [];
|
||||
for (const [key, value] of Object.entries(data)) {
|
||||
fields.push(`${key} = ?`);
|
||||
values.push(value);
|
||||
}
|
||||
if (fields.length === 0) return;
|
||||
values.push(id);
|
||||
await db.query(`UPDATE tickets SET ${fields.join(', ')} WHERE id = ?`, values);
|
||||
},
|
||||
getResponses: async (ticketId) => {
|
||||
const [rows] = await db.query(`
|
||||
SELECT r.*, u.nombre as usuario_nombre, u.rol as usuario_rol
|
||||
FROM ticket_respuestas r
|
||||
LEFT JOIN users u ON r.user_id = u.id
|
||||
WHERE r.ticket_id = ?
|
||||
ORDER BY r.created_at ASC
|
||||
`, [ticketId]);
|
||||
return rows;
|
||||
},
|
||||
addResponse: async (ticketId, userId, mensaje) => {
|
||||
const [result] = await db.query(
|
||||
'INSERT INTO ticket_respuestas (ticket_id, user_id, mensaje) VALUES (?, ?, ?)',
|
||||
[ticketId, userId, mensaje]
|
||||
);
|
||||
return result.insertId;
|
||||
},
|
||||
countByStatus: async (companyId) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT status, COUNT(*) as total FROM tickets WHERE company_id = ? GROUP BY status',
|
||||
[companyId]
|
||||
);
|
||||
return rows;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = Ticket;
|
||||
@@ -0,0 +1,72 @@
|
||||
const db = require('../config/db');
|
||||
const crypto = require('crypto');
|
||||
|
||||
const User = {
|
||||
findAll: async (companyId) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT id, company_id, nombre, email, rol, is_active, created_at FROM users WHERE company_id = ? ORDER BY created_at DESC',
|
||||
[companyId]
|
||||
);
|
||||
return rows;
|
||||
},
|
||||
findById: async (id) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT u.*, c.name as company_name, c.plan as company_plan, c.max_users, c.max_tickets FROM users u LEFT JOIN companies c ON u.company_id = c.id WHERE u.id = ?',
|
||||
[id]
|
||||
);
|
||||
return rows[0];
|
||||
},
|
||||
findByEmail: async (email) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT u.*, c.name as company_name, c.plan as company_plan, c.max_users, c.max_tickets FROM users u LEFT JOIN companies c ON u.company_id = c.id WHERE u.email = ?',
|
||||
[email]
|
||||
);
|
||||
return rows[0];
|
||||
},
|
||||
create: async (companyId, nombre, email, password, rol = 'client') => {
|
||||
const [result] = await db.query(
|
||||
'INSERT INTO users (company_id, nombre, email, password, rol) VALUES (?, ?, ?, ?, ?)',
|
||||
[companyId, nombre, email, password, rol]
|
||||
);
|
||||
return result.insertId;
|
||||
},
|
||||
update: async (id, data) => {
|
||||
const fields = [];
|
||||
const values = [];
|
||||
for (const [key, value] of Object.entries(data)) {
|
||||
fields.push(`${key} = ?`);
|
||||
values.push(value);
|
||||
}
|
||||
if (fields.length === 0) return;
|
||||
values.push(id);
|
||||
await db.query(`UPDATE users SET ${fields.join(', ')} WHERE id = ?`, values);
|
||||
},
|
||||
delete: async (id) => {
|
||||
await db.query('DELETE FROM users WHERE id = ?', [id]);
|
||||
},
|
||||
findByInviteToken: async (token) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT * FROM users WHERE invite_token = ? AND invite_token_expires > NOW()',
|
||||
[token]
|
||||
);
|
||||
return rows[0];
|
||||
},
|
||||
generateInviteToken: async (userId) => {
|
||||
const token = crypto.randomBytes(32).toString('hex');
|
||||
const expires = new Date(Date.now() + 7 * 24 * 60 * 60 * 1000);
|
||||
await db.query(
|
||||
'UPDATE users SET invite_token = ?, invite_token_expires = ? WHERE id = ?',
|
||||
[token, expires, userId]
|
||||
);
|
||||
return token;
|
||||
},
|
||||
countByCompany: async (companyId) => {
|
||||
const [rows] = await db.query(
|
||||
'SELECT COUNT(*) as total FROM users WHERE company_id = ? AND is_active = 1',
|
||||
[companyId]
|
||||
);
|
||||
return rows[0].total;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = User;
|
||||
Reference in New Issue
Block a user