expressed-example-app 1.0.0 → 2.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md ADDED
@@ -0,0 +1,136 @@
1
+ # Express-Router-BDS Example Application
2
+
3
+ This is a sample Express.js application demonstrating the usage of the `express-router-bds` routing system with custom hooks, advanced features, and integrated queue system.
4
+
5
+ ## Overview
6
+
7
+ This example application showcases:
8
+
9
+ - High-performance routing with `express-router-bds`
10
+ - JSON-based route configuration
11
+ - Custom hook system implementation
12
+ - Parameterized route handling
13
+ - Directory-based route loading
14
+ - Integrated queue system with `express-queued`
15
+ - Declarative route definitions in separate JSON files
16
+
17
+ ## Features
18
+
19
+ - **Modular Route Configuration**: Routes defined in JSON files for easy maintenance
20
+ - **Custom Hooks**: Comprehensive hook system with `pre_route_load`, `post_route_load`, `before_route_handler`, `after_route_handler`, `route_handler_error`, and more
21
+ - **Parameterized Routes**: Support for dynamic routes like `/users/:id` and `/products/:category/:id`
22
+ - **Integrated Queue System**: Background task processing with `express-queued`
23
+ - **Declarative Routes**: Separate route files for different functionalities
24
+ - **Extensible Architecture**: Easy to extend with custom middleware and hooks
25
+
26
+ ## Project Structure
27
+
28
+ ```
29
+ express-app/
30
+ ├── app.js # Main application entry point
31
+ ├── queue-system.js # Queue system integration
32
+ ├── hooks-config.js # Base hook configurations
33
+ ├── hooks-personalizados.js # Custom hook implementations
34
+ ├── controllers/
35
+ │ ├── mainController.js # Home, init and queue route handlers
36
+ │ ├── productController.js # Product route handlers
37
+ │ └── userController.js # User route handlers
38
+ ├── routes/
39
+ │ ├── main-routes.json # Main route definitions in JSON format
40
+ │ └── queue-routes.json # Queue-related route definitions
41
+ └── node_modules/
42
+ ├── express-router-bds/ # Custom routing system
43
+ └── express-queued/ # Queue system
44
+ ```
45
+
46
+ ## Available Endpoints
47
+
48
+ ### Main Endpoints
49
+ - `GET /` - Home page with welcome message
50
+ - `GET /init` - Initialization endpoint
51
+ - `GET /users/:id` - Get user by ID
52
+ - `GET /products/:category/:id` - Get product by category and ID
53
+ - `GET /test-hook` - Test endpoint for hook demonstration
54
+
55
+ ### Queue System Endpoints
56
+ - `GET /queue-status` - Get the status of the queue system
57
+ - `GET /start-queues` - Start the queue system
58
+ - `GET /stop-queues` - Stop the queue system
59
+ - `POST /process-user` - Add a user processing task to the queue
60
+ - `POST /process-product` - Add a product processing task to the queue
61
+ - `POST /send-email` - Add an email sending task to the queue
62
+
63
+ ## Queue System
64
+
65
+ The application integrates `express-queued` for background task processing:
66
+
67
+ - **Multiple Queues**: Dedicated queues for different types of tasks
68
+ - **Configurable Concurrency**: Control how many tasks execute simultaneously per queue
69
+ - **Retry System**: Automatic failure handling with configurable retries
70
+ - **Priority Management**: Assign priorities to tasks
71
+ - **Hooks Integration**: Customize processing with hooks
72
+
73
+ ### Queue Types
74
+ - `procesamiento-general` - General processing tasks
75
+ - `envio-correos` - Email sending tasks
76
+ - `procesamiento-usuarios` - User processing tasks
77
+ - `procesamiento-productos` - Product processing tasks
78
+
79
+ ## Hook System
80
+
81
+ The application demonstrates several types of hooks:
82
+
83
+ - `pre_route_load` - Executes before loading routes from a file
84
+ - `post_route_load` - Executes after loading routes from a file
85
+ - `before_route_processing` - Executes before processing any route
86
+ - `route_matched` - Executes when a matching route is found
87
+ - `before_route_handler` - Executes before executing a route handler
88
+ - `after_route_handler` - Executes after executing a route handler
89
+ - `route_handler_error` - Executes when a route handler error occurs
90
+
91
+ ## Installation
92
+
93
+ ```bash
94
+ npm install
95
+ ```
96
+
97
+ ## Usage
98
+
99
+ Start the server:
100
+
101
+ ```bash
102
+ npm start
103
+ ```
104
+
105
+ The application will be available at `http://localhost:3000`
106
+
107
+ ## Testing
108
+
109
+ Test the main endpoints:
110
+
111
+ ```bash
112
+ curl http://localhost:3000
113
+ curl http://localhost:3000/users/123
114
+ curl http://localhost:3000/products/electronics/456
115
+ ```
116
+
117
+ Test the queue system:
118
+
119
+ ```bash
120
+ # Check queue status
121
+ curl http://localhost:3000/queue-status
122
+
123
+ # Add a user processing task
124
+ curl -X POST http://localhost:3000/process-user \
125
+ -H "Content-Type: application/json" \
126
+ -d '{"userId": "123", "name": "John Doe", "email": "john@example.com"}'
127
+
128
+ # Add an email sending task
129
+ curl -X POST http://localhost:3000/send-email \
130
+ -H "Content-Type: application/json" \
131
+ -d '{"to": "test@example.com", "subject": "Test", "content": "Test content"}'
132
+ ```
133
+
134
+ ## License
135
+
136
+ This project is part of the `express-router-bds` ecosystem and follows the same licensing terms.
package/app.js CHANGED
@@ -1,115 +1,167 @@
1
- /**
2
- * Aplicación principal
3
- * Integración de @hooked, @router y @queued con una arquitectura limpia
4
- */
5
-
6
1
  const express = require('express');
7
- const fs = require('fs');
8
- const path = require('path');
9
- const ExpressHooked = require('express-hooked');
10
2
  const ExpressRouterIntegration = require('express-router-bds');
11
- const ExpressQueueIntegration = require('express-queued');
12
- const AppHooks = require('./hooks/AppHooks');
13
- const { captureBodyMiddleware } = require('./middleware/bodyCapture');
3
+ const RouteDirectoryLoader = require('express-router-bds/RouteDirectoryLoader');
4
+ const AppHooks = require('./hooks-config');
5
+ const HooksPersonalizados = require('./hooks-personalizados');
6
+ const QueueSystem = require('./queue-system');
14
7
 
15
- // Crear la aplicación Express
16
8
  const app = express();
17
- const port = 3001;
9
+ const PORT = process.env.PORT || 3000;
18
10
 
19
- // Leer la configuración de rutas desde el archivo JSON
20
- const routesConfig = JSON.parse(fs.readFileSync(path.join(__dirname, 'config/routes.json'), 'utf8'));
11
+ // Crear instancia del router
12
+ const routerIntegration = new ExpressRouterIntegration();
21
13
 
22
- // Inicializar el sistema de hooks
23
- const hooked = new ExpressHooked(app);
14
+ // Crear instancia del sistema de colas
15
+ const queueSystem = new QueueSystem();
24
16
 
25
- // Inicializar el sistema de enrutamiento
26
- const router = new ExpressRouterIntegration();
17
+ // Inicializar hooks y filtros
18
+ const appHooks = new AppHooks(app, routerIntegration.getHooks());
27
19
 
28
- // Inicializar el sistema de colas
29
- const queueSystem = new ExpressQueueIntegration();
20
+ // Inicializar hooks personalizados
21
+ const hooksPersonalizados = new HooksPersonalizados(routerIntegration);
30
22
 
31
- // Registrar los hooks de la aplicación
32
- AppHooks.registerHooks(hooked);
23
+ // Cargar rutas desde directorio
24
+ const routeDirectoryLoader = new RouteDirectoryLoader();
33
25
 
34
- // Middleware para capturar el body
35
- app.use(captureBodyMiddleware);
26
+ // Middleware para parsear JSON
27
+ app.use(express.json());
36
28
 
37
- // Middleware para servir archivos estáticos
38
- app.use(express.static(path.join(__dirname, 'public')));
29
+ // Middleware para inyectar el sistema de colas en las solicitudes
30
+ app.use(queueSystem.getInstance().queueMiddleware());
39
31
 
40
- // Cargar dinámicamente los controladores y registrar las rutas
41
- for (const route of routesConfig.routes) {
42
- // Extraer el nombre del controlador y la acción
43
- const [controllerName, actionName] = route.controller.split('.');
44
-
45
- // Construir la ruta del archivo del controlador
46
- const controllerPath = path.join(__dirname, 'controllers', `${controllerName}.js`);
47
-
48
- // Verificar si el archivo del controlador existe
49
- if (fs.existsSync(controllerPath)) {
50
- // Importar el controlador
51
- const Controller = require(controllerPath);
52
-
53
- // Verificar si la acción existe en el controlador
54
- if (Controller[actionName]) {
55
- // Registrar la ruta con el método HTTP, la ruta y el controlador
56
- router.addRoute(route.method, route.path, (req, res) => {
57
- // Disparar hook antes de ejecutar la acción
58
- hooked.doAction('before_controller_action', req, res, route);
59
-
60
- // Disparar hook para mostrar información detallada de la solicitud
61
- // Usar el body capturado en lugar del body original que puede estar vacío
62
- if (req.capturedBody) {
63
- req.body = req.capturedBody;
64
- }
65
- hooked.doAction('request_details_log', req, res, route);
66
-
67
- // Ejecutar la acción del controlador
68
- Controller[actionName](req, res);
69
-
70
- // Disparar hook después de ejecutar la acción
71
- hooked.doAction('after_controller_action', req, res, route);
72
- });
73
- } else {
74
- console.error(`La acción "${actionName}" no existe en el controlador "${controllerName}"`);
75
- }
76
- } else {
77
- console.error(`El archivo del controlador "${controllerPath}" no existe`);
32
+ // Middleware para inyectar el sistema de rutas en las solicitudes
33
+ app.use((req, res, next) => {
34
+ req.routerIntegration = routerIntegration;
35
+ next();
36
+ });
37
+
38
+ routerIntegration.addHook('route_matched', (matchedRoute, req, res) => {
39
+ console.log(`Ruta encontrada: ${matchedRoute.route.path}`);
40
+ if (matchedRoute.params && Object.keys(matchedRoute.params).length > 0) {
41
+ console.log(`Parámetros:`, matchedRoute.params);
78
42
  }
79
- }
43
+ });
44
+
45
+ // Cargar rutas desde el directorio
46
+ routeDirectoryLoader.loadRoutesFromDirectory(routerIntegration, './routes')
47
+ .then(routes => {
48
+ console.log(`${routes.length} rutas cargadas desde directorio`);
49
+ // Mostrar las rutas que se han cargado
50
+ routes.forEach(route => {
51
+ console.log(`Ruta cargada: ${route.method} ${route.path}`);
52
+ });
53
+ })
54
+ .catch(error => {
55
+ console.error('Error cargando rutas desde directorio:', error.message);
56
+ });
57
+
58
+ // Cargar rutas específicas de colas
59
+ const RouteLoader = require('express-router-bds/RouteLoader');
60
+ const queueRouteLoader = new RouteLoader();
61
+ queueRouteLoader.loadRoutes(routerIntegration, './routes/queue-routes.json')
62
+ .then(queueRoutes => {
63
+ console.log(`${queueRoutes.length} rutas de colas cargadas`);
64
+ queueRoutes.forEach(route => {
65
+ console.log(`Ruta de cola cargada: ${route.method} ${route.path}`);
66
+ });
67
+ })
68
+ .catch(error => {
69
+ console.error('Error cargando rutas de colas:', error.message);
70
+ });
80
71
 
81
- // Aplicar el middleware de colas para inyectar el sistema en las solicitudes
82
- app.use(queueSystem.queueMiddleware());
72
+ // Aplicar el router a la aplicación Express
73
+ routerIntegration.applyToApp(app);
83
74
 
84
- // Aplicar el router a la aplicación
85
- router.applyToApp(app);
75
+ // Middleware para manejar errores 404
76
+ app.use((req, res) => {
77
+ res.status(404).json({ error: 'Ruta no encontrada' });
78
+ });
86
79
 
87
- // Iniciar el sistema de colas
88
- queueSystem.start();
80
+ // Ruta para obtener el estado del sistema de colas
81
+ app.get('/queue-status', (req, res) => {
82
+ const status = req.getQueueStatus();
83
+ res.json(status);
84
+ });
85
+
86
+ // Ruta para iniciar el sistema de colas
87
+ app.get('/start-queues', (req, res) => {
88
+ queueSystem.start();
89
+ res.json({ message: 'Sistema de colas iniciado' });
90
+ });
91
+
92
+ // Ruta para detener el sistema de colas
93
+ app.get('/stop-queues', (req, res) => {
94
+ queueSystem.stop();
95
+ res.json({ message: 'Sistema de colas detenido' });
96
+ });
97
+
98
+ // Ruta para procesar un usuario en cola
99
+ app.post('/process-user', (req, res) => {
100
+ const { userId, name, email } = req.body;
101
+
102
+ if (!userId) {
103
+ return res.status(400).json({ error: 'userId es requerido' });
104
+ }
105
+
106
+ const taskId = queueSystem.addUserProcessingTask({ userId, name, email });
107
+
108
+ res.json({
109
+ message: 'Tarea de procesamiento de usuario agregada a la cola',
110
+ taskId
111
+ });
112
+ });
89
113
 
90
- // Iniciar el sistema de hooks
91
- hooked.init();
114
+ // Ruta para procesar un producto en cola
115
+ app.post('/process-product', (req, res) => {
116
+ const { productId, name, price } = req.body;
117
+
118
+ if (!productId) {
119
+ return res.status(400).json({ error: 'productId es requerido' });
120
+ }
121
+
122
+ const taskId = queueSystem.addProductProcessingTask({ productId, name, price });
123
+
124
+ res.json({
125
+ message: 'Tarea de procesamiento de producto agregada a la cola',
126
+ taskId
127
+ });
128
+ });
92
129
 
93
- // Middleware para manejo de errores
94
- app.use((err, req, res, next) => {
95
- console.error('Error:', err);
96
- res.status(500).json({
97
- error: 'Ocurrió un error en el servidor',
98
- message: err.message
130
+ // Ruta para enviar un correo en cola
131
+ app.post('/send-email', (req, res) => {
132
+ const { to, subject, content } = req.body;
133
+
134
+ if (!to) {
135
+ return res.status(400).json({ error: 'to es requerido' });
136
+ }
137
+
138
+ const taskId = queueSystem.addEmailSendingTask({ to, subject, content });
139
+
140
+ res.json({
141
+ message: 'Tarea de envío de correo agregada a la cola',
142
+ taskId
99
143
  });
100
144
  });
101
145
 
102
146
  // Iniciar el servidor
103
- app.listen(port, () => {
104
- console.log(`Servidor corriendo en http://localhost:${port}`);
105
- console.log('Módulos integrados:');
106
- console.log('- @hooked: Sistema de hooks activo');
107
- console.log('- @router: Sistema de enrutamiento activo');
108
- console.log('- @queued: Sistema de colas activo');
147
+ app.listen(PORT, () => {
148
+ console.log(`Servidor corriendo en el puerto ${PORT}`);
149
+ console.log('Endpoints disponibles:');
150
+ console.log('- GET /');
151
+ console.log('- GET /init');
152
+ console.log('- GET /users/:id');
153
+ console.log('- GET /products/:category/:id');
154
+ console.log('- GET /test-hook');
155
+ console.log('- GET /queue-status');
156
+ console.log('- GET /start-queues');
157
+ console.log('- GET /stop-queues');
158
+ console.log('- POST /process-user');
159
+ console.log('- POST /process-product');
160
+ console.log('- POST /send-email');
109
161
 
110
- // Mostrar rutas registradas
111
- console.log('\nRutas disponibles:');
112
- routesConfig.routes.forEach(route => {
113
- console.log(`${route.method} ${route.path} -> ${route.controller}.${route.action}`);
114
- });
115
- });
162
+ // Iniciar el sistema de colas
163
+ queueSystem.start();
164
+ console.log('Sistema de colas iniciado');
165
+ });
166
+
167
+ module.exports = app;
@@ -0,0 +1,177 @@
1
+ # Changelog Detallado: Modificaciones al Core de Express-Router-BDS
2
+
3
+ ## Archivo: `/node_modules/express-router-bds/ExpressRouter.js`
4
+
5
+ ### Cambio 1: Llamada al hook `before_route_processing`
6
+ - **Fecha**: 15 de febrero de 2026
7
+ - **Línea(s)**: 154
8
+ - **Antes**:
9
+ ```javascript
10
+ this.hooks.doAction('before_route_processing', req, res, next);
11
+ ```
12
+ - **Después**:
13
+ ```javascript
14
+ this.hooks.doAction('before_route_processing', req, res);
15
+ ```
16
+ - **Motivo**: Evitar que el hook reciba el parámetro `next` para prevenir conflictos con el flujo normal de Express
17
+
18
+ ### Cambio 2: Manejo de headers en ejecución del handler
19
+ - **Fecha**: 15 de febrero de 2026
20
+ - **Líneas**: 185-187
21
+ - **Antes**:
22
+ ```javascript
23
+ if (!res.headersSent) {
24
+ matchedRoute.route.handler(req, res, next);
25
+ } else {
26
+ console.warn('Headers ya fueron enviados, no se puede ejecutar el handler');
27
+ }
28
+ ```
29
+ - **Después**:
30
+ ```javascript
31
+ if (!res.headersSent) {
32
+ // Añadir logging para depuración
33
+ console.log(`Ejecutando handler para ruta: ${req.method} ${req.url}`);
34
+ matchedRoute.route.handler(req, res, next);
35
+ } else {
36
+ console.warn('Headers ya fueron enviados, no se puede ejecutar el handler');
37
+ next();
38
+ }
39
+ ```
40
+ - **Motivo**: Añadir logging para depuración y asegurar que se llame a `next()` si los headers ya han sido enviados
41
+
42
+ ### Cambio 3: Llamada a hooks de handler
43
+ - **Fecha**: 15 de febrero de 2026
44
+ - **Línea(s)**: 180
45
+ - **Antes**:
46
+ ```javascript
47
+ this.hooks.doAction('before_route_handler', req, res, next);
48
+ ```
49
+ - **Después**:
50
+ ```javascript
51
+ this.hooks.doAction('before_route_handler', req, res);
52
+ ```
53
+ - **Motivo**: Consistencia con el manejo de hooks para evitar conflictos con `next()`
54
+
55
+ ### Cambio 4: Manejo de errores en handler
56
+ - **Fecha**: 15 de febrero de 2026
57
+ - **Línea(s)**: 193
58
+ - **Antes**:
59
+ ```javascript
60
+ this.hooks.doAction('route_handler_error', error, req, res, next);
61
+ ```
62
+ - **Después**:
63
+ ```javascript
64
+ this.hooks.doAction('route_handler_error', error, req, res);
65
+ ```
66
+ - **Motivo**: Consistencia con el manejo de hooks para evitar conflictos con `next()`
67
+
68
+ ## Archivo: `/node_modules/express-router-bds/RouteLoader.js`
69
+
70
+ ### Cambio 1: Manejo seguro de headers en handlers con contentType
71
+ - **Fecha**: 15 de febrero de 2026
72
+ - **Líneas**: 178-195
73
+ - **Antes**:
74
+ ```javascript
75
+ // Ejecutar el handler original
76
+ try {
77
+ if (handler.constructor.name === 'AsyncFunction') {
78
+ await handler(req, res, next);
79
+ } else {
80
+ handler(req, res, next);
81
+ }
82
+ } catch (error) {
83
+ // Si ocurre un error, asegurarse de no intentar enviar headers otra vez
84
+ if (!res.headersSent) {
85
+ next(error);
86
+ } else {
87
+ console.error('Error en el handler:', error);
88
+ }
89
+ }
90
+ ```
91
+ - **Después**:
92
+ ```javascript
93
+ // Ejecutar el handler original solo si no se han enviado headers aún
94
+ if (!res.headersSent) {
95
+ try {
96
+ if (handler.constructor.name === 'AsyncFunction') {
97
+ await handler(req, res, next);
98
+ } else {
99
+ handler(req, res, next);
100
+ }
101
+ } catch (error) {
102
+ // Si ocurre un error, asegurarse de no intentar enviar headers otra vez
103
+ if (!res.headersSent) {
104
+ next(error);
105
+ } else {
106
+ console.error('Error en el handler:', error);
107
+ }
108
+ }
109
+ }
110
+ ```
111
+ - **Motivo**: Asegurar que los handlers no se ejecuten si los headers ya han sido enviados
112
+
113
+ ### Cambio 2: Eliminación de wrapper adicional
114
+ - **Fecha**: 15 de febrero de 2026
115
+ - **Líneas**: 197-217
116
+ - **Antes**:
117
+ ```javascript
118
+ // Crear un handler que envuelva completamente la lógica para prevenir doble ejecución
119
+ const wrappedHandler = async (req, res, next) => {
120
+ // Verificar que no se hayan enviado headers aún
121
+ if (res.headersSent) {
122
+ return;
123
+ }
124
+
125
+ // Ejecutar el handler final
126
+ try {
127
+ await finalHandler(req, res, next);
128
+ } catch (error) {
129
+ if (!res.headersSent) {
130
+ next(error);
131
+ } else {
132
+ console.error('Error en el handler:', error);
133
+ }
134
+ }
135
+ };
136
+
137
+ // Agregar la ruta con el handler envuelto
138
+ routerIntegration.addRoute(route.method, route.path, wrappedHandler);
139
+ ```
140
+ - **Después**:
141
+ ```javascript
142
+ // Agregar la ruta con el handler final (sin doble wrapper)
143
+ // Asegurarse de que el handler es correcto
144
+ routerIntegration.addRoute(route.method, route.path, finalHandler);
145
+ ```
146
+ - **Motivo**: Eliminar wrapper redundante que podría causar problemas de ejecución doble
147
+
148
+ ## Archivo: `/node_modules/express-router-bds/RouteMatcher.js`
149
+
150
+ ### Cambio 1: Mejora en la conversión de rutas a expresiones regulares
151
+ - **Fecha**: 15 de febrero de 2026
152
+ - **Líneas**: 213-225
153
+ - **Antes**:
154
+ ```javascript
155
+ // Lógica de escape de caracteres especiales
156
+ let escapedPath = '';
157
+ for (let i = 0; i < path.length; i++) {
158
+ const char = path[i];
159
+ if (char.match(/[.+?^${}()|[\]\\-]/) && !(i > 0 && path[i-1] === ':')) {
160
+ escapedPath += '\\' + char;
161
+ } else {
162
+ escapedPath += char;
163
+ }
164
+ }
165
+ ```
166
+ - **Después**: (Sin cambios, ya que no se modificó este archivo directamente)
167
+
168
+ ## Resumen de Impacto
169
+
170
+ Los cambios realizados al core de `express-router-bds` se enfocaron principalmente en:
171
+
172
+ 1. **Evitar conflictos con el parámetro `next`** en las llamadas a hooks
173
+ 2. **Mejorar la seguridad en el manejo de headers** para prevenir el error `ERR_HTTP_HEADERS_SENT`
174
+ 3. **Eliminar wrappers redundantes** que podían causar ejecuciones dobles de handlers
175
+ 4. **Agregar verificaciones adicionales** para asegurar que los handlers solo se ejecuten cuando sea seguro hacerlo
176
+
177
+ Estos cambios resolvieron el problema fundamental donde las rutas se identificaban pero los handlers no se ejecutaban, permitiendo que la aplicación funcione correctamente.
@@ -0,0 +1,96 @@
1
+ // controllers/mainController.js
2
+ // Controlador principal de la aplicación
3
+
4
+ class MainController {
5
+ /**
6
+ * Maneja la ruta raíz
7
+ * @param {Object} req - Objeto de solicitud
8
+ * @param {Object} res - Objeto de respuesta
9
+ */
10
+ home(req, res) {
11
+ if (!res.headersSent) {
12
+ res.json({
13
+ message: '¡Bienvenido a la aplicación Express con Router-BDS!',
14
+ timestamp: new Date().toISOString()
15
+ });
16
+ } else {
17
+ console.log('Headers ya fueron enviados en home handler');
18
+ }
19
+ }
20
+
21
+ /**
22
+ * Maneja la ruta de inicialización
23
+ * @param {Object} req - Objeto de solicitud
24
+ * @param {Object} res - Objeto de respuesta
25
+ */
26
+ init(req, res) {
27
+ res.json({
28
+ message: 'Aplicación inicializada correctamente con Router-BDS',
29
+ status: 'success'
30
+ });
31
+ }
32
+
33
+ /**
34
+ * Obtiene el estado del sistema de colas
35
+ * @param {Object} req - Objeto de solicitud
36
+ * @param {Object} res - Objeto de respuesta
37
+ */
38
+ getQueueStatus(req, res) {
39
+ const status = req.getQueueStatus();
40
+ res.json(status);
41
+ }
42
+
43
+ /**
44
+ * Inicia el sistema de colas
45
+ * @param {Object} req - Objeto de solicitud
46
+ * @param {Object} res - Objeto de respuesta
47
+ */
48
+ startQueues(req, res) {
49
+ req.queueSystem.start();
50
+ res.json({ message: 'Sistema de colas iniciado' });
51
+ }
52
+
53
+ /**
54
+ * Detiene el sistema de colas
55
+ * @param {Object} req - Objeto de solicitud
56
+ * @param {Object} res - Objeto de respuesta
57
+ */
58
+ stopQueues(req, res) {
59
+ req.queueSystem.stop();
60
+ res.json({ message: 'Sistema de colas detenido' });
61
+ }
62
+
63
+ /**
64
+ * Agrega una tarea de envío de correo a la cola
65
+ * @param {Object} req - Objeto de solicitud
66
+ * @param {Object} res - Objeto de respuesta
67
+ */
68
+ sendEmailInQueue(req, res) {
69
+ const { to, subject, content } = req.body;
70
+
71
+ if (!to) {
72
+ return res.status(400).json({ error: 'to es requerido' });
73
+ }
74
+
75
+ const taskId = req.addTask('envio-correos', async (data, taskObj) => {
76
+ console.log(`[ENVIO-CORREO] Enviando correo a: ${data.to}`);
77
+
78
+ // Simular envío de correo (con 10% de probabilidad de fallo)
79
+ await new Promise(resolve => setTimeout(resolve, 1000));
80
+
81
+ if (Math.random() < 0.1) {
82
+ throw new Error(`Fallo al enviar correo a: ${data.to}`);
83
+ }
84
+
85
+ console.log(`[ENVIO-CORREO] Correo enviado exitosamente a: ${data.to}`);
86
+ return `Correo enviado a ${data.to} exitosamente`;
87
+ }, { to, subject, content });
88
+
89
+ res.json({
90
+ message: 'Tarea de envío de correo agregada a la cola',
91
+ taskId
92
+ });
93
+ }
94
+ }
95
+
96
+ module.exports = new MainController();