Refactor printer function and implement Redis state management - #1244
Open
Juank2001 wants to merge 7 commits into
Open
Refactor printer function and implement Redis state management#1244Juank2001 wants to merge 7 commits into
Juank2001 wants to merge 7 commits into
Conversation
…rsistence feat(bot): add RedisState handler and unit tests for scalable state management
…gration feat(types): update BotState methods to support Promise return types chore(database-redis): add development dependencies for testing and build
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Que tipo de Pull Request es?
Descripción
Este PR introduce el manejo de estado basado en Redis y un Adaptador de Historial en Redis. Estos componentes permiten que el bot escale horizontalmente al compartir el estado de los usuarios y el historial de mensajes entre múltiples instancias, superando las limitaciones del almacenamiento en memoria.
📋 Cambios principales
RedisState Handler: Una nueva clase para gestionar el estado de los usuarios.
Soporta notación de puntos (dot-notation) para acceder a propiedades anidadas (ej. state.get('user.profile.name')).
Implementa fusión de estados (merge) para evitar la pérdida de datos durante actualizaciones concurrentes.
Incluye TTL automático (24h) para optimizar el uso de memoria en Redis.
RedisAdapter (Historial): Un proveedor de base de datos para almacenar el historial de chats en listas de Redis.
Soporta límite de mensajes mediante store_messages (usando LTRIM).
Permite prefijos personalizados para entornos con múltiples bots.
Integración en el Core: Se añadió RedisOptions a la CoreClass para permitir el intercambio opcional entre MemoryState y RedisState.
🧪 Pruebas (Testing)
Validados con UVU e ioredis-mock.
Se verificó que el estado esté aislado por usuario (basado en su número).
Se comprobó que la recuperación de propiedades anidadas maneje correctamente los valores undefined.
Se confirmó que clearAll afecte únicamente a las llaves con el prefijo del bot.
⚙️ Modo de uso
Para habilitar el estado en Redis, pasa los detalles de la conexión en la configuración de createBot:
TypeScript
const redis = new Redis({ host: 'localhost', port: 6379 })
const bot = await createBot({
database: RedisAdapter(redis, {)),
flow: adapterFlow,
provider: adapterProvider,
args: {
RedisOptions: {
connection: redis,
options: { prefix: 'mi-bot' }
}
}
})
Para mejorar el contexto entre multiples instancias se podria reemplazar el state por el stateRedis en los casos que no se implemente la configuracion necesaria de redis, para esto es necesario actualizar las propiedades de state para que se resuelvan como promesas y facilite la transición
Este PR agrega soporte para el evento CONTACTS de WhatsApp/Meta y corrige la lógica de resolución de eventos para garantizar que el flujo WELCOME actúe correctamente como fallback cuando no existe un flujo específico para el evento recibido.
📋 Cambios principales
Soporte para CONTACTS
Se agregó el reconocimiento de mensajes de tipo Contacts provenientes de WhatsApp/Meta mediante un nuevo patrón de evento:
LIST_REGEX.REGEX_EVENT_CONTACTS
y su correspondiente resolución de flujo:
this.generalArgs.listEvents.CONTACTS
Esto permite crear flujos específicos para mensajes que contienen contactos compartidos.
Corrección del fallback de eventos
Se movió la resolución del flujo WELCOME al final del proceso de evaluación de eventos.
Anteriormente, si un mensaje coincidía con un evento (por ejemplo MEDIA, LOCATION, DOCUMENT, etc.) pero no existía un flujo registrado para ese evento, msgToSend era reemplazado por un arreglo vacío, impidiendo que el bot respondiera.
Ahora, una vez evaluados todos los eventos, se verifica si se encontró algún flujo:
if (!msgToSend.length) {
msgToSend = this.flowClass.find(this.generalArgs.listEvents.WELCOME) || []
}
De esta forma, cuando un evento no tiene un flujo asociado, el bot utiliza automáticamente el flujo WELCOME como comportamiento por defecto.
🧪 Pruebas (Testing)
Se verificó que los mensajes de tipo CONTACTS ejecuten correctamente el flujo configurado.
Se comprobó que los eventos existentes (MEDIA, LOCATION, DOCUMENT, VOICE_NOTE, ORDER, TEMPLATE, CALL) mantienen su comportamiento.
Se validó que, cuando un evento no tiene un flujo registrado, el bot responde utilizando el flujo WELCOME en lugar de quedarse sin respuesta.
⚙️ Compatibilidad
Este cambio es completamente retrocompatible.
No modifica el comportamiento de los flujos existentes.
El evento CONTACTS es opcional y solo se utiliza cuando el desarrollador define un flujo para él.
La corrección del fallback evita casos donde el bot permanecía sin responder debido a que un evento reconocido no tenía un flujo asociado.