Configuración del Agente de IA

Este documento describe la estructura y configuración del archivo agent.config.json, utilizado para definir completamente un Agente de IA en Plazbot. Un agente puede estar vinculado a un portal web, widget o canal de mensajería como WhatsApp o cualquier software que tenga.

Github

Puedes descargar nuestro repositorio de ejemplo para crear tus agentes.

Inicialización

import { Agent } from 'plazbot';

const bot = new Agent({
  workspaceId: "[YOUR_WORKSPACE_ID]",
  apiKey: "[YOUR_API_KEY]",
  zone: "LA" // Use "EU" for Europe
});

Creación del Agente

El agente es la parte más importante del SDK. Aquí podrás crear agentes de IA con características específicas e implementarlos en diferentes canales, como el Portal de IA, un widget o WhatsApp. También puedes usar nuestro agente en cualquiera de tus herramientas empresariales internas, si lo deseas.

    const agent = await bot.addAgent(config);
    const agentId = agent.agentId;
    const agentUpdated = await bot.updateAgent(`agentId`, config);

Para trabajar con los agentes, existe un archivo JSON que funciona como el configurador inicial del agente y tiene la siguiente estructura. No es necesario completar todo el archivo, pero puedes configurar tu agente como prefieras.

Puedes entrenar al agente como necesites, ya sea a través de nuestro configurador o si quieres configurarlo todo en una sola línea de comandos; no es necesario usar todos los campos del archivo de configuración.

✅ También proporcionamos un archivo básico para que lo uses en el Repositorio de Github.

Estructura del Archivo agent.config.json

{
  "name": "Sales Clinic",
  "description": "Virtual Agent IA assistant of the Dental Clinic Smiles",
  "prompt": "You are Máximo, a professional virtual assistant for Smiles Dental Clinic. Help patients with appointments, general information, and guide them through our services. Always maintain a professional yet friendly tone.",
  "zone": "LA",
  "buffer": 15,
  "color": "blue",
  "question": "How can I help you today?",
  "timezone": "America/Lima",
  "enable": true,
  "tags": [
    "health",
    "dentistry",
    "ia",
    "plazbot"
  ],
  "showInChat": false,
  "enableWidget": true,
  "darkWidget": true,
  "nameWidget": "Dental Assistant",
  "initialShowWidget": true,
  "examples": [
    { "value": "How to schedule an appointment?", "color": "green" },
    { "value": "What are your office hours?", "color": "blue" },
    { "value": "Do you accept insurance?", "color": "orange" },
    { "value": "Emergency contact information", "color": "gray" },
    { "value": "Location and directions", "color": "white" }
  ],
  "instructions": {
    "tone": "professional",
    "style": "short answers",
    "personality": "friendly",
    "objective": "help with clarity",
    "language": "es-419",
    "emojis": false,
    "preferredFormat": "plain text",
    "maxWords": 80,
    "avoidTopics": [
      "laboratory costs",
      "external claims",
      "specific medical diagnoses"
    ],
    "respondOnlyIfKnows": true,
    "maintainToneBetweenMessages": true,
    "greeting": "Hello, I am Máximo, your virtual assistant from Smiles Dental Clinic. How can I help you today?"
  },
  "person": {
    "name": "Máximo",
    "role": "Virtual customer service assistant",
    "speaksInFirstPerson": true,
    "isHuman": false
  },
  "fallbacks": {
    "noAnswer": "Sorry, I don't have information on that topic. Let me connect you with one of our specialists.",
    "serviceError": "There was a problem processing your request. Please try again later or contact us directly.",
    "doNotUnderstand": "Could you please repeat it in another way? I want to make sure I help you correctly."
  },
  "rules": {
    "doNotMentionPrices": false,
    "doNotDiagnose": true,
    "doNotRespondOutsideHours": "Our office hours are Monday to Saturday, from 8am to 6pm. For emergencies, please call our emergency line."
  },
  "channels": [
    {
      "channel": "whatsapp",
      "key": "+51987654321",
      "multianswer": false
    },
    {
      "channel": "telegram",
      "key": "smiles_clinic_bot",
      "multianswer": true
    }
  ],
  "services": [
    {
      "intent": "schedule_appointment",
      "reference": "Service for scheduling patient appointments at the dental clinic",
      "enabled": true,
      "method": "POST",
      "tags": ["appointment", "scheduling"],
      "endpoint": "https://api.smilesclinic.com/v1/appointments/schedule",
      "requiredFields": [
        {
          "name": "patient_name",
          "description": "Full name of the patient who wants to schedule the appointment",
          "promptHint": "Could you please provide your full name?",
          "type": "string"
        },
        {
          "name": "email",
          "description": "Patient's email address for appointment confirmation",
          "promptHint": "What's your email address for the appointment confirmation?",
          "type": "email"
        },
        {
          "name": "phone",
          "description": "Patient's phone number for contact",
          "promptHint": "Could you provide your phone number?",
          "type": "phone"
        },
        {
          "name": "preferred_date",
          "description": "Preferred date and time for the appointment",
          "promptHint": "What date and time would work best for your appointment?",
          "type": "datetime"
        },
        {
          "name": "service_type",
          "description": "Type of dental service needed",
          "promptHint": "What type of dental service do you need? (cleaning, consultation, etc.)",
          "type": "string"
        }
      ],
      "headers": {
        "Authorization": "Bearer {{clinic_api_key}}",
        "Content-Type": "application/json",
        "X-Clinic-ID": "smiles_001"
      },
      "bodyTemplate": {
        "patient": {
          "name": "{{patient_name}}",
          "email": "{{email}}",
          "phone": "{{phone}}"
        },
        "appointment": {
          "datetime": "{{preferred_date|format('yyyy-MM-dd HH:mm')}}",
          "service": "{{service_type}}",
          "timezone": "America/Lima"
        }
      },
      "bodySchema": {
        "patient_name": "string",
        "email": "string",
        "preferred_date": "date",
        "service_type": "string"
      },
      "responseMapping": {
        "confirmation_id": "$.data.appointment.id",
        "scheduled_date": "$.data.appointment.datetime",
        "status": "$.status",
        "doctor_name": "$.data.appointment.doctor.name",
        "conflict_reason": "$.error.reason"
      },
      "responseMessage": "Your appointment has been successfully scheduled for {{scheduled_date}} with Dr. {{doctor_name}}",
      "responseConditions": [
        {
          "condition": "$.status == 'confirmed'",
          "message": "¡Perfect! Your appointment has been confirmed for {{scheduled_date}} with Dr. {{doctor_name}}. We'll send you a reminder 24 hours before. Confirmation ID: {{confirmation_id}}",
          "nextService": "send_appointment_reminder"
        },
        {
          "condition": "$.status == 'conflict'",
          "message": "Sorry, that time slot is not available. {{conflict_reason}}. Would you like me to suggest other available times?",
          "nextService": "suggest_alternative_times"
        },
        {
          "condition": "$.status == 'error' && $.error.code == 'invalid_email'",
          "message": "The email address provided seems invalid. Could you please verify your email address?",
          "nextService": "verify_contact_info"
        },
        {
          "condition": "$.status == 'error' && $.error.code == 'past_date'",
          "message": "I cannot schedule appointments for past dates. Could you please choose a future date?"
        },
        {
          "condition": "$.status == 'pending'",
          "message": "Your appointment request is being reviewed. We'll contact you within 24 hours to confirm availability and finalize the details."
        }
      ],
      "action": "conversar_humano"
    },
    {
      "intent": "check_insurance",
      "reference": "Service to verify patient insurance coverage and benefits",
      "enabled": true,
      "method": "GET",
      "tags": ["insurance", "verification"],
      "endpoint": "https://api.smilesclinic.com/v1/insurance/verify",
      "requiredFields": [
        {
          "name": "insurance_provider",
          "description": "Name of the insurance company",
          "promptHint": "What's your insurance provider name?",
          "type": "string"
        },
        {
          "name": "policy_number",
          "description": "Insurance policy or member ID number",
          "promptHint": "Could you provide your policy or member ID number?",
          "type": "string"
        }
      ],
      "headers": {
        "Authorization": "Bearer {{insurance_api_key}}",
        "Content-Type": "application/json"
      },
      "responseMapping": {
        "coverage_status": "$.data.coverage.status",
        "deductible": "$.data.coverage.deductible",
        "copay": "$.data.coverage.copay",
        "covered_services": "$.data.coverage.services"
      },
      "responseMessage": "Your insurance verification is complete. Coverage status: {{coverage_status}}",
      "responseConditions": [
        {
          "condition": "$.data.coverage.status == 'active'",
          "message": "Great news! Your insurance is active. Your copay is ${{copay}} and your remaining deductible is ${{deductible}}. Covered services include: {{covered_services}}."
        },
        {
          "condition": "$.data.coverage.status == 'inactive'",
          "message": "It appears your insurance policy is not currently active. Please contact your insurance provider or we can discuss our self-pay options."
        },
        {
          "condition": "$.data.coverage.status == 'not_found'",
          "message": "I couldn't find your policy in our system. Please verify your insurance information or contact us directly for assistance."
        }
      ]
    }
  ],
  "actions": [
    {
      "intent": "assign_urgent_tag",
      "reference": "Tags patients as urgent when they mention emergency dental situations",
      "tags": ["emergency", "urgent"],
      "enabled": true,
      "responseMessage": "I've marked your case as urgent and notified our emergency team.",
      "responseJson": false,
      "action": [
        {
          "type": "action.tag",
          "value": "urgent_case"
        },
        {
          "type": "action.asign",
          "value": "emergency@smilesclinic.com"
        }
      ]
    },
    {
      "intent": "schedule_follow_up",
      "reference": "Automatically schedules follow-up appointments and assigns appropriate case management",
      "tags": ["follow-up", "scheduling"],
      "enabled": true,
      "responseMessage": "Your follow-up has been scheduled and assigned to our treatment coordinator.",
      "responseJson": false,
      "action": [
        {
          "type": "action.stage",
          "value": "follow_up_scheduled"
        },
        {
          "type": "action.segmentation",
          "value": "post_treatment_care"
        }
      ]
    },
    {
      "intent": "end_consultation",
      "reference": "Ends the AI consultation when the patient no longer needs assistance",
      "tags": ["consultation", "end"],
      "enabled": true,
      "responseMessage": "Thank you for contacting Smiles Dental Clinic. Have a great day!",
      "responseJson": false,
      "action": [
        {
          "type": "action.agentShutDown",
          "value": "true"
        }
      ]
    }
  ]
}

Servicios (services)

Los servicios permiten que el agente recolecte información del usuario paso a paso y luego llame a APIs externas. Son ideales para procesos como reservas, registros, consultas que requieren datos específicos.

Estructura de un Servicio

CampoTipoRequeridoDescripción
intentstring✅ SíIdentificador único del servicio.
referencestring✅ SíDescripción para que la IA entienda cuándo usar este servicio.
enabledboolean✅ SíSi el servicio está activo.
methodstring✅ SíMétodo HTTP (GET, POST, PUT, DELETE).
requiredFieldsarray✅ SíCampos que el agente debe recolectar del usuario.
endpointstring✅ SíURL de la API externa a llamar.
headersobject❌ NoHeaders HTTP (Authorization, Content-Type, etc.).
bodyTemplateobject❌ NoEstructura del body usando las variables recolectadas.
responseMappingobject❌ NoMapeo de la respuesta usando JSONPath.
responseMessagestring❌ NoMensaje base de respuesta exitosa.
responseConditionsarray❌ NoRespuestas condicionales según el resultado de la API.
actionstring❌ NoAcción a ejecutar después del servicio.

Para más información detallada sobre servicios, consulta la documentación completa de Services.

Acciones (actions)

Las acciones permiten que el agente ejecute tareas específicas en respuesta a intenciones del usuario. Son especialmente útiles para automatizar procesos como asignar etiquetas, cambiar estados de contactos o integrar con sistemas externos.

Estructura de una Acción

CampoTipoRequeridoDescripción
intentstring✅ SíIdentificador único de la acción.
referencestring✅ SíDescripción detallada para que la IA entienda cuándo usar esta acción.
tagsarray❌ NoEtiquetas para clasificar la acción.
enabledboolean✅ SíSi la acción está activa.
responseMessagestring❌ NoMensaje de respuesta fijo (solo si responseIA = false).
responseIAboolean❌ NoSi debe continuar con IA después de ejecutar (true) o usar solo responseMessage (false).
responseJsonboolean❌ NoSi responder en formato JSON estructurado (true) o texto plano (false).
actionarray✅ SíLista de acciones a ejecutar.

Tipos de Acciones Disponibles

TipoDescripciónValor Esperado
action.tagAsigna una etiqueta al contactoNombre de la etiqueta
action.stageCambia la fase del contactoNombre de la fase
action.asignAsigna un agente humanoEmail del agente
action.segmentationAsigna una segmentaciónNombre de la segmentación
action.agentShutDownApaga el agente de IA"true"

Comportamiento de Respuesta

responseIA = true (Recomendado para la mayoría de casos):

{
  "responseIA": true,
  "responseJson": false
}
  • Ejecuta las acciones ✅
  • La IA responde naturalmente según el contexto ✅
  • Más inteligente y conversacional ✅

responseIA = false + responseJson = false:

{
  "responseIA": false,
  "responseJson": false,
  "responseMessage": "Solicitud procesada correctamente."
}
  • Ejecuta las acciones ✅
  • Responde con mensaje fijo ✅
  • Útil para confirmaciones simples ✅

responseIA = false + responseJson = true:

{
  "responseIA": false,
  "responseJson": true,
  "responseMessage": "Proceso completado"
}
  • Ejecuta las acciones ✅
  • Responde con JSON estructurado ✅
  • Ideal para integraciones con APIs/webhooks ✅

Para más información detallada sobre acciones, consulta la documentación completa de Actions.

Canales (channels)

Los canales definen dónde y cómo tu agente puede comunicarse con los usuarios.

CampoTipoRequeridoDescripción
channelstring✅ SíTipo de canal: whatsapp, telegram, messenger, etc.
keystring✅ SíIdentificador del canal (número de teléfono para WhatsApp).

Ejemplo de Canales

"channels": [
  { "channel": "whatsapp", "key": "123456789" },
  { "channel": "telegram", "key": "@mi_bot" },
  { "channel": "messenger", "key": "page_id_123" }
]

Campos principales del agente

CampoDescripción
nameNombre del agente. Visible en el panel. Requerido
promptInstrucciones base para el comportamiento del agente. Requerido
bufferCantidad de mensajes que se mantienen como contexto. Rango: 3 a 10. Requerido
colorColor de presentación. Valores: blue, orange, gray, green, white.
questionPregunta principal que se muestra en el portal.
descriptionDescripción general del agente.
zoneZona donde opera el agente: LA (Latinoamérica) o EU (Europa). Requerido
timezoneZona horaria. Ejemplo: America/Lima. TimeZone Formats
tagsEtiquetas internas para clasificar agentes.
examplesPreguntas sugeridas. Hasta 5.
showInChatSi el agente se muestra en el widget/chat. (boolean)

Instrucciones (instructions)

CampoTipoDescripción
tonestringTono de comunicación: professional, friendly, etc.
stylestringEstilo de respuestas: short answers, detailed.
personalitystringPersonalidad del agente.
objectivestringObjetivo principal del agente.
languagestringIdioma en que debe responder. Ver tabla de idiomas.
emojisbooleanSi puede usar emojis.
preferredFormatstringplain text o markdown.
maxWordsnumberMáximo de palabras por respuesta.
avoidTopicsarrayLista de temas prohibidos.
respondOnlyIfKnowsbooleanSi debe evitar responder sin información confiable.
maintainToneBetweenMessagesbooleanMantiene el mismo tono entre mensajes.
greetingstringMensaje de bienvenida.

Opciones Objetive “help with clarity” Enfocado en brindar respuestas claras “sell more” Promociona productos o servicios “support users” Ayuda a resolver problemas “guide actions” Brinda pasos concretos o instrucciones

Opciones Personalidad “friendly” Agradable y empático “serious” Reservado y directo “funny” Con toques de humor sutil “robotic” Más neutral, tipo IA técnica

Opciones preferredFormat “plain text” Texto simple “markdown” Permite negritas, listas, enlaces “html” Usado si se integrará en un entorno web

Opciones Style “short answers” Respuestas breves y directas “detailed” Respuestas explicativas, útiles para asistencia técnica “bullet points” Instrucciones u opciones en lista (ideal para pasos o listas) “conversational” Estilo fluido y natural, más humano

Opciones Tono “professional” Tono formal, educado, propio para empresas “friendly” Tono amigable, cercano, ideal para atención al cliente “casual” Informal, con lenguaje relajado y natural “neutral” Objetivo, sin inclinación emocional

Persona del Agente (person)

CampoTipoDescripción
namestringNombre que usará el agente.
rolestringRol representado.
speaksInFirstPersonbooleanHabla en primera persona.
isHumanbooleanSimula ser una persona real.

Reglas y Fallbacks

Fallbacks

CampoTipoDescripción
noAnswerstringMensaje si no tiene respuesta.
serviceErrorstringMensaje de error de servicio.
doNotUnderstandstringMensaje si no entiende la consulta.

Reglas

CampoTipoDescripción
doNotMentionPricesbooleanNo hablar de precios.
doNotDiagnosebooleanNo hacer diagnósticos médicos.
doNotRespondOutsideHoursstringMensaje fuera del horario definido. Trabaja junto con el campo de Timezone

Códigos de Idioma

ValorDescripción
esEspañol general
es-419Español latinoamericano neutral
es-ESEspañol de España
enInglés general
en-USInglés estadounidense
en-GBInglés británico
frFrancés general
fr-FRFrancés de Francia
pt-BRPortugués brasileño
deAlemán

Enviar mensaje al Agente de IA

const response = await bot.onMessage({
  agentId: "agentId",
  question: "Can you give me a summary of the new Meta WhatsApp prices?",
  sessionId: "2aff0c11-434f-4d7c-a325-697128bb8a20",
  file: "https://.../archivo.pdf", // 
  multipleAnswers: true // Optional
});

console.log("💬 IA Response:", respuesta);
CampoTipoRequeridoDescripción
agentIdstring✅ SíIdentificador único del agente. Se utiliza para recuperar su configuración y conocimiento.
questionstring✅ SíPregunta o mensaje del usuario que la IA debe responder.
sessionIdstring✅ SíIdentificador de sesión único para mantener el contexto y el historial (buffer) de la conversación.
filestring❌ NoURL pública opcional de una imagen o archivo PDF. El contenido será extraído y usado si es relevante para la respuesta.
multipleAnswersboolean❌ NoSi se establece en true, la respuesta será devuelta en múltiples bloques (array) en lugar de un único texto. Ideal para respuestas estructuradas.

Tipos de Archivos Soportados en onMessage (OCR)

Tipo de ArchivoSoportadoNotas
.jpg, .png, .bmp, .gif, .tiff✅ SíFormatos estándar de imagen
.pdf✅ SíSolo si el PDF contiene texto incrustado o es una imagen escaneada
.docx, .xlsx❌ NoNo se admite para procesamiento OCR
.txt, .json, etc.❌ NoNo relevantes para extracción OCR

Respuesta esperada:

{
  "success": true,
  "answers": [
    "Beneficio 1: Acceso exclusivo...",
    "Beneficio 2: Soporte personalizado...",
    "Beneficio 3: Capacitación mensual..."
  ],
  "fileName": ["Contrato_socio_plazbot.pdf"]
}

📌 Nota: Si multipleAnswers = false, la respuesta se devolverá en un único string en la propiedad answer.

Get Agents

Devuelve todos los agentes dentro del espacio de trabajo.

    const agents = await bot.getAgents();
    console.log("🧠 Agents:", agents);

Get Agent By Id

Obtiene detalles de un agente específico por ID.

    const agentById = await bot.getAgentById({ id: agentId });
    console.log("📌 Agent by ID:", agentById);

Delete Agent

Elimina un agente y elimina automáticamente su referencia de cualquier portal asociado.

    // Delete Agent
    await bot.deleteAgent({
      id: agentId
    });

📎 Consideraciones Finales

  • El agente puede ser creado, actualizado o eliminado usando el SDK.
  • Para agregar archivos o servicios, use los métodos addFile() por separado.
  • Toda la lógica de respuesta está diseñada para mantener el contexto, estilo y tono definidos.

📁 Gestión de Archivos

Agregar Archivo al Agente

const fileResult = await bot.addFile({
  agentId: "agent_123",
  file: fileBuffer, // Buffer del archivo
  fileName: "manual_usuario.pdf"
});

console.log("📄 File added:", fileResult);

Obtener Archivos del Agente

const files = await bot.getFiles({
  agentId: "agent_123"
});

console.log("📂 Agent files:", files);

Eliminar Archivo

await bot.deleteFile({
  agentId: "agent_123",
  fileId: "file_456"
});

Tipos de Archivos Soportados

ExtensiónTipoTamaño MáximoOCR/Extracción
.pdfDocumentos10 MB✅ Sí
.docxWord5 MB✅ Sí
.txtTexto plano2 MB✅ Sí
.jpg, .pngImágenes5 MB✅ Sí
.csvDatos estructurados10 MB✅ Sí
.xlsxExcel10 MB✅ Sí

Los archivos se procesan automáticamente para extraer su contenido y hacer que esté disponible para el agente durante las conversaciones.

🔧 Manejo de Errores

El SDK proporciona manejo de errores detallado para todas las operaciones:

try {
  const response = await bot.onMessage({
    agentId: "agent_123",
    question: "¿Cuáles son los horarios?",
    sessionId: "session_456"
  });
  
  console.log("✅ Success:", response);
} catch (error) {
  console.error("❌ Error:", error.message);
  
  // Diferentes tipos de errores
  if (error.status === 401) {
    console.log("🔑 Error de autenticación - Revisa tu API Key");
  } else if (error.status === 404) {
    console.log("🔍 Agente no encontrado");
  } else if (error.status === 429) {
    console.log("⏱️ Límite de rate exceeded - Espera antes de reintentar");
  } else {
    console.log("🚨 Error del servidor:", error);
  }
}

⚡ Mejores Prácticas

1. Gestión de Sesiones

// ✅ Correcto - Mantén sessionId consistente por conversación
const sessionId = uuidv4(); // Genera una vez por conversación
await bot.onMessage({ agentId, question: "Hola", sessionId });
await bot.onMessage({ agentId, question: "¿Precios?", sessionId }); // Mismo sessionId

2. Reutilización de Instancia

// ✅ Correcto - Reutiliza la instancia del bot
const bot = new Agent({ workspaceId, apiKey, zone: "LA" });

// Úsala múltiples veces
await bot.onMessage({ agentId: "agent1", question: "...", sessionId: "..." });
await bot.onMessage({ agentId: "agent2", question: "...", sessionId: "..." });

3. Configuración de Zona

// Para usuarios en América Latina
const botLA = new Agent({
  workspaceId: "[YOUR_WORKSPACE_ID]",
  apiKey: "[YOUR_API_KEY]",
  zone: "LA" // Menor latencia desde América
});

// Para usuarios en Europa
const botEU = new Agent({
  workspaceId: "[YOUR_WORKSPACE_ID]",
  apiKey: "[YOUR_API_KEY]",
  zone: "EU" // Menor latencia desde Europa
});

4. Rate Limiting

async function sendMultipleMessages(messages) {
  for (const message of messages) {
    try {
      const response = await bot.onMessage(message);
      console.log(response);
      
      // Pausa entre mensajes para evitar rate limiting
      await new Promise(resolve => setTimeout(resolve, 100));
    } catch (error) {
      if (error.status === 429) {
        console.log("Rate limit detectado, esperando...");
        await new Promise(resolve => setTimeout(resolve, 5000));
        // Opcionalmente reintentar
      }
      console.error("Error:", error.message);
    }
  }
}

📊 Ejemplos Avanzados

Chat Bot Completo

import { Agent } from 'plazbot';
import { v4 as uuidv4 } from 'uuid';

class PlazbotChatBot {
  private bot: Agent;
  private sessionId: string;
  
  constructor(workspaceId: string, apiKey: string, zone: "LA" | "EU" = "LA") {
    this.bot = new Agent({ workspaceId, apiKey, zone });
    this.sessionId = uuidv4();
  }
  
  async chat(agentId: string, message: string, file?: string) {
    try {
      const response = await this.bot.onMessage({
        agentId,
        question: message,
        sessionId: this.sessionId,
        file,
        multipleAnswers: false
      });
      
      return {
        success: true,
        message: response.answer,
        sessionId: this.sessionId
      };
    } catch (error) {
      return {
        success: false,
        error: error.message,
        sessionId: this.sessionId
      };
    }
  }
  
  async resetSession() {
    this.sessionId = uuidv4();
  }
}

// Uso
const chatBot = new PlazbotChatBot("workspace_123", "api_key_456", "LA");

const response1 = await chatBot.chat("agent_123", "Hola, ¿cómo estás?");
console.log(response1.message);

const response2 = await chatBot.chat("agent_123", "¿Cuáles son sus servicios?");
console.log(response2.message);

Integración con Webhook

import express from 'express';
import { Agent } from 'plazbot';

const app = express();
const bot = new Agent({
  workspaceId: process.env.PLAZBOT_WORKSPACE_ID!,
  apiKey: process.env.PLAZBOT_API_KEY!,
  zone: "LA"
});

app.post('/webhook/whatsapp', async (req, res) => {
  const { message, from, sessionId } = req.body;
  
  try {
    const response = await bot.onMessage({
      agentId: "whatsapp_agent_123",
      question: message,
      sessionId: sessionId || from, // Usa el número como sessionId
    });
    
    // Envía respuesta de vuelta a WhatsApp
    res.json({
      success: true,
      reply: response.answer
    });
  } catch (error) {
    res.status(500).json({
      success: false,
      error: error.message
    });
  }
});

💡 Tip Pro: Usa el campo multipleAnswers: true cuando necesites respuestas estructuradas para integraciones complejas o cuando quieras procesar cada parte de la respuesta por separado.

Configuración Avanzada del Agent Config

Ejemplo Completo de Actions

{
  "actions": [
    {
      "intent": "conversar_humano",
      "reference": "Información cuando un usuario quiere hablar con un Agente humano.",
      "tags": ["conversacion", "humano", "agente"],
      "enabled": true,
      "responseMessage": "Por favor, espera un momento mientras te conectamos con un agente humano.",
      "responseIA": false,
      "responseJson": false,
      "action": [
        {
          "type": "action.asign",
          "value": "soporte@empresa.com"
        },
        {
          "type": "action.stage",
          "value": "agendado"
        },
        {
          "type": "action.agentShutDown",
          "value": "true"
        },
        {
          "type": "action.segmentation",
          "value": "clientes_vip"
        },
        {
          "type": "action.tag",
          "value": "requiere_atencion_humana"
        }
      ]
    },
    {
      "intent": "marcar_como_lead",
      "reference": "Cuando un usuario muestra interés comercial o solicita información de ventas.",
      "tags": ["ventas", "lead", "comercial"],
      "enabled": true,
      "responseIA": true,
      "responseJson": false,
      "action": [
        {
          "type": "action.tag",
          "value": "lead_calificado"
        },
        {
          "type": "action.stage",
          "value": "prospecto"
        },
        {
          "type": "action.segmentation",
          "value": "interesados_ventas"
        }
      ]
    }
  ]
}

Variables de Entorno Recomendadas

# .env
PLAZBOT_WORKSPACE_ID=your_workspace_id_here
PLAZBOT_API_KEY=your_api_key_here
PLAZBOT_ZONE=LA # o EU

# Para diferentes entornos
NODE_ENV=development # o production

Configuración por Entorno

interface BotConfig {
  workspaceId: string;
  apiKey: string;
  zone: "LA" | "EU";
}

const configs: Record<string, BotConfig> = {
  development: {
    workspaceId: process.env.DEV_WORKSPACE_ID!,
    apiKey: process.env.DEV_API_KEY!,
    zone: "LA"
  },
  production: {
    workspaceId: process.env.PROD_WORKSPACE_ID!,
    apiKey: process.env.PROD_API_KEY!,
    zone: "LA"
  }
};

const bot = new Agent(configs[process.env.NODE_ENV || 'development']);

🚀 Migración y Versionado

Desde SDK v1 a v2

// ❌ SDK v1 (Obsoleto)
const plazbot = require('plazbot-v1');
const response = await plazbot.send(agentId, message);

// ✅ SDK v2 (Actual)
import { Agent } from 'plazbot';
const bot = new Agent({ workspaceId, apiKey, zone: "LA" });
const response = await bot.onMessage({ agentId, question: message, sessionId });

Cambios Importantes v2

  • Soporte para TypeScript nativo
  • Gestión de sesiones mejorada
  • Manejo de errores más robusto
  • Soporte para archivos y OCR
  • Respuestas múltiples y JSON
  • Mejor configuración de zonas geográficas

📋 Checklist de Implementación

✅ Configuración Inicial

  • Obtener credenciales de API desde el panel de Plazbot
  • Instalar SDK: npm install plazbot
  • Configurar variables de entorno
  • Crear instancia del Agent con zona correcta

✅ Desarrollo del Agente

  • Definir estructura del agent.config.json
  • Configurar instructions, person, rules y fallbacks
  • Implementar services para APIs externas (opcional)
  • Configurar actions para automatizaciones (opcional)
  • Agregar archivos de conocimiento (opcional)

✅ Testing y Producción

  • Probar conversaciones básicas con onMessage
  • Validar manejo de errores y rate limiting
  • Implementar logging y monitoreo
  • Configurar webhook para canal (WhatsApp, etc.)
  • Deploy a producción con variables correctas

🔍 Estado de Funcionalidades

✅ Estables y Productivas

  • Core SDK: Creación, edición, eliminación de agentes
  • Messaging: onMessage con sessionId y multipleAnswers
  • Files: Upload, gestión y eliminación de archivos
  • Services: POST/GET básicos con responseMapping y responseConditions
  • Actions: Básicas (tag, stage, assign) con responseJson
  • Variables: Interpolación en headers y body templates
  • Zonas: LA y EU con balanceeo automático

⚠️ Experimentales

  • responseIA en Actions: Funcionalidad parcial, puede requerir ajustes
  • Variables dinámicas en endpoints: Funciona pero documentación limitada

🚧 En Desarrollo Futuro

  • Timeout y reintentos configurables
  • Mock responses para testing
  • Métricas avanzadas de performance
  • Caché de respuestas
  • Validación regex personalizada

¿Necesitas Ayuda?

Si tienes preguntas sobre el SDK o necesitas asistencia con la implementación, contacta a nuestro equipo de soporte o revisa los ejemplos en el repositorio de GitHub.