feat: implement private messaging and user notification system

main
brobert (aider) 3 months ago
parent 2c8ae1f687
commit 5a44e73106

@ -1,6 +1,7 @@
import { sendMessage } from '../utils/messaging';
import { createTask, assignTask, completeTask, getPendingTasks } from '../../services/taskService';
import { setRemindersEnabled } from '../../services/userService';
import { normalizeUserIdentifier, extractUserFromJid } from '../../utils/userUtils';
function formatTaskList(tasks: any[]) {
if (tasks.length === 0) {

@ -0,0 +1,54 @@
import { sendMessage } from '../utils/messaging';
import { formatUserMention } from '../utils/userUtils';
import { Task } from '../models/task';
export function notifyTaskCreation(task: Task) {
const creatorMention = formatUserMention(task.createdBy);
const assigneeMention = task.assignedTo ? formatUserMention(task.assignedTo) : 'ninguno';
// Notify creator
let message = `✅ Tarea creada:\nID: ${task.id}\nDescripción: ${task.description}`;
if (task.assignedTo) {
message += `\nAsignada a: ${assigneeMention}`;
}
if (task.dueDate) {
message += `\nFecha límite: ${task.dueDate}`;
}
sendMessage(task.createdBy, message);
// Notify assignee if different from creator
if (task.assignedTo && task.assignedTo !== task.createdBy) {
const assigneeMessage = `📝 ${creatorMention} te ha asignado una nueva tarea:\n` +
`ID: ${task.id}\nDescripción: ${task.description}` +
(task.dueDate ? `\nFecha límite: ${task.dueDate}` : '');
sendMessage(task.assignedTo, assigneeMessage);
}
}
export function notifyTaskAssignment(task: Task, assignedBy: string) {
const assignerMention = formatUserMention(assignedBy);
const assigneeMention = formatUserMention(task.assignedTo);
// Notify assigner
sendMessage(assignedBy, `✅ Tarea ${task.id} asignada a ${assigneeMention}`);
// Notify assignee
const assigneeMessage = `📝 ${assignerMention} te ha asignado la tarea:\n` +
`ID: ${task.id}\nDescripción: ${task.description}` +
(task.dueDate ? `\nFecha límite: ${task.dueDate}` : '');
sendMessage(task.assignedTo, assigneeMessage);
}
export function notifyTaskCompletion(task: Task, completedBy: string) {
const completerMention = formatUserMention(completedBy);
// Notify completer
sendMessage(completedBy, `✅ Tarea completada:\nID: ${task.id}\nDescripción: ${task.description}`);
// Notify creator if different from completer
if (task.createdBy && task.createdBy !== completedBy) {
const creatorMessage = `${completerMention} ha completado la tarea:\n` +
`ID: ${task.id}\nDescripción: ${task.description}`;
sendMessage(task.createdBy, creatorMessage);
}
}

@ -1,7 +1,11 @@
import { query, execute } from '../database/db';
import { normalizeUserIdentifier } from '../utils/userUtils';
import { notifyTaskCreation, notifyTaskAssignment, notifyTaskCompletion } from './notificationService';
// Create a new task
export function createTask(sender: string, params: CreateTaskParams) {
const createdBy = normalizeUserIdentifier(sender);
const assignedTo = params.assignedTo ? normalizeUserIdentifier(params.assignedTo) : null;
if (!params.description || params.description.trim().length < 3) {
throw new Error('La descripción de la tarea debe tener al menos 3 caracteres');
}
@ -12,13 +16,16 @@ export function createTask(sender: string, params: CreateTaskParams) {
const result = execute(
'INSERT INTO tasks (description, created_by, assigned_to, due_date, completed) VALUES (?, ?, ?, ?, ?)',
[params.description.trim(), sender, params.assignedTo || null, params.dueDate || null, false]
[params.description.trim(), createdBy, assignedTo, params.dueDate || null, false]
);
const task = getTaskById(result.lastInsertRowid);
if (!task) {
throw new Error('Error al crear la tarea');
}
// Notify relevant users
notifyTaskCreation(task);
return task;
}

@ -0,0 +1,24 @@
export function normalizeUserIdentifier(input: string): string {
// Remove @ prefix if present
const cleanInput = input.startsWith('@') ? input.slice(1) : input;
// Remove any non-numeric characters
const phoneNumber = cleanInput.replace(/\D/g, '');
// Validate phone number length
if (phoneNumber.length < 8 || phoneNumber.length > 15) {
throw new Error('Número de teléfono inválido');
}
return `@${phoneNumber}`;
}
export function extractUserFromJid(jid: string): string {
// Extract phone number from JID (format: 12345678@s.whatsapp.net)
const phoneNumber = jid.split('@')[0];
return normalizeUserIdentifier(phoneNumber);
}
export function formatUserMention(phoneNumber: string): string {
return `@${phoneNumber.replace('@', '')}`;
}
Loading…
Cancel
Save