Pipeline detallado
Pre-LLM (síncrono, costo LLM cero)
-
StudentModelService.getSnapshot(userId, courseId)
- Carga ConceptMastery (distribución Beta por concepto)
- Carga misconceptions activas/resolving (con evidence trail)
- Carga EpisodicMemory (lo que funcionó antes)
- Carga quizContext (avgScore, passRate, totalAttempts, weakAreas)
- Carga historial de ChatSession (sliding window de 10 msgs)
-
RetrievalAgent.retrieve(query, studentModel)
- Reformula la query usando contexto (sustituye "esto", "aquello" por conceptos actuales)
- Búsqueda en pgvector con filtros (tenantId, courseId)
- Boost por áreas débiles en quizzes (
quizWeakAreasdel studentModel) - Top-K con reranking semántico
-
PedagogicalAgent.select(studentModel, query)
- Evalúa el mastery promedio + dominio específico de la query
- Aplica ajustes (chat-quiz divergence, edad, estilo de aprendizaje)
- Devuelve estrategia + adición al system prompt
-
buildEnrichedPrompt(query, studentModel, ragChunks, strategy, misconceptions)
- Construye el system prompt con:
- Estrategia pedagógica seleccionada
- Contexto RAG (top-5 chunks con atribución de fuente)
- Misconceptions activas (con instrucciones para abordarlas)
- Intentos de quiz recientes (memoria inter-turno)
- Contexto de inline quiz trigger (si hubo un quiz reciente)
- Construye el system prompt con:
LLM principal (streaming, SSE)
router.stream(taskType: "chat_tutor", messages, options) resuelve el provider vía TenantTaskModelConfig:
- Claude (primary) → OpenAI → xAI Grok → Google Gemini (cadena de fallback)
- Circuit breaker por provider (estado en Redis)
- Middleware de metering: rate limit + comprobación de créditos + calculadora de costos
- Streaming vía Server-Sent Events al cliente
El LLM puede emitir tool calls especiales:
[INLINE_QUIZ]{...}[/INLINE_QUIZ]— quiz interactivo renderizado en el chatpresent_quiztool call — formato Vercel AI SDK
Post-LLM (background vía after(), fire-and-forget)
-
EvaluationAgent.evaluate(turn, studentModel) — Haiku, ~$0.001
- Clasifica el entendimiento: correct | partial | incorrect | unclear
- Detecta StudentMisconception con:
- source: "chat"
- sourceSessionId
- contextSnippet (max 500 chars)
- concepts[] (mapeados a ConceptMastery)
- Actualiza ConceptMastery (actualización bayesiana vía beta(alpha+success, beta+failure))
- Llama a MisconceptionResolutionService.checkAndTransition (máquina de estados)
-
ContentAgent.preGenerate(studentModel, conceptId) — Haiku, ~$0.001
- Genera un ejercicio de seguimiento basado en conceptos débiles
- Almacena en Redis (TTL 30min) para servir en el siguiente turno
- Reduce la latencia percibida por el alumno
-
SessionSummarizer (cada 10 turnos) — Haiku, ~$0.001
- Resume el historial largo
- Reemplaza mensajes antiguos en el sliding window
- Preserva los insights pedagógicos relevantes
-
SupervisorAgent.run(turn, courseContext) — Haiku, ~$0.001
- Clasifica severity (5 niveles) + category (8 tipos)
- Crea AiSupervisorIncident si severity != "none"
- Aplica strikes / quarantine / safety cooldown según las reglas
Configuración por admin
TenantTaskModelConfig
El admin elige provider+modelo por tipo de tarea:
chat_tutor → Claude Sonnet 4.6 (o GPT-4o, o Grok-3, etc)
chat_evaluation → Claude Haiku
chat_summarization → Claude Haiku
chat_supervisor → Claude Haiku
content_generation → Claude Haiku
course_review → Claude Sonnet
gamification_agent → Claude Sonnet
course_agent → Claude Sonnet
PedagogicalConfig
Configurabilidad pedagógica por tenant:
- masteryThresholds: umbrales para cambiar de estrategia (default 0.3, 0.5, 0.7, 0.9)
- domainOverrides: ajuste por dominio (ej: matemáticas usa scaffolding más agresivo)
- ageOverrides: ajuste por franja etaria (niño = direct_instruction más frecuente)
- learningStyleOverrides: visual, auditivo, kinestésico
Personalización del prompt template
El admin institucional puede editar el system prompt del tutor vía PromptTemplate (en la base de datos):
- Por taskType (chat_tutor)
- Por provider (Anthropic, OpenAI, Google, xAI — variantes optimizadas)
- Por locale (pt-BR, en-US, es-ES, fr-FR)
- Por tenant (o null = global)
- Por curso (override per-course)
Limitaciones técnicas
- Latencia first-token: 800-1500ms (incluyendo el pipeline pre-LLM)
- Latencia total del turno: 2-8s para una respuesta promedio (~300 palabras)
- Ventana de contexto: limitada por el provider (Claude Sonnet 4.6 = 200K, GPT-4o = 128K)
- Idiomas: el tutor responde en el idioma del alumno, pero internamente el pipeline es bilingüe (en/pt)
- Imágenes: el tutor acepta imágenes en el input (multimodal Claude/GPT/Gemini) pero el RAG es text-only
- Avatar parlante + voz (salida): disponible como opt-in por curso — avatar parlante en tiempo real con voz TTS vía HeyGen LiveAvatar o D-ID (BYO key). Ver Avatar & TTS.
- Voz de entrada (STT): hablar con el tutor (voz del alumno → speech-to-text → chat) aún no está implementado (roadmap).