Bot de turnos con estados
Construye un bot que agenda turnos con una máquina de estados y pruébalo conversando.
Vamos a construir un bot que agenda turnos para una clínica. El flujo es corto pero tiene todo lo esencial: estados, validación de entrada, confirmación e intenciones globales.
Los estados
inicio ──"turno"──▶ pedir_dia ──día válido──▶ pedir_hora
│
confirmado ◀──"sí"── confirmar ◀──hora válidaConversa con tu bot
El script registra un manejador con mx.bot.onMessage. Escribe en el campo del teléfono para hablar con él. Modifica las respuestas o agrega un estado nuevo; el bot se reinicia al editar.
// Bot de turnos: máquina de estados mínima
let step = "inicio";
const turno = {};
const DIAS = ["lunes", "martes", "miércoles", "jueves", "viernes"];
mx.bot.onMessage(({ text }) => {
const t = text.trim().toLowerCase();
if (t === "cancelar") {
step = "inicio";
return mx.bot.reply("Listo, cancelé el proceso. Escribe 'turno' para empezar de nuevo.");
}
if (step === "inicio") {
if (t.includes("turno")) {
step = "pedir_dia";
return mx.bot.reply("¿Qué día prefieres? (lunes a viernes)");
}
return mx.bot.reply("Hola 👋 Escribe 'turno' para agendar.");
}
if (step === "pedir_dia") {
if (!DIAS.includes(t)) return mx.bot.reply("No reconocí el día. Prueba con 'martes'.");
turno.dia = t;
step = "pedir_hora";
return mx.bot.reply("Perfecto. ¿A qué hora? (9 a 17)");
}
if (step === "pedir_hora") {
const h = parseInt(t, 10);
if (!(h >= 9 && h <= 17)) return mx.bot.reply("Atendemos de 9 a 17. ¿Qué hora te acomoda?");
turno.hora = h;
step = "confirmar";
return mx.bot.reply("¿Confirmas el " + turno.dia + " a las " + h + ":00? (sí/no)");
}
if (step === "confirmar") {
step = "inicio";
return mx.bot.reply(t.startsWith("s") ? "✅ Turno confirmado. Te enviaremos un recordatorio." : "Sin problema, no agendé nada.");
}
});
mx.bot.reply("Hola 👋 Soy el asistente de la clínica. Escribe 'turno' para agendar.");Persistir el estado
En el playground, step vive en memoria del worker. En producción vive en una base de datos o en un almacén clave-valor con TTL, indexado por usuario y canal, porque cada mensaje puede llegar a una instancia distinta de tu servicio.
Fíjate en que cada rama del bot valida la entrada antes de avanzar. Un bot que acepta cualquier cosa para no frustrar al usuario termina frustrándolo más tarde, cuando el turno queda registrado para un día que no existe.