Chat
El endpoint Chat permite que los usuarios envíen mensajes al coach financiero de IA de Ozzie. El coach mantiene plena consciencia del contexto financiero del usuario — incluyendo su intake, historial de transacciones, plan actual, metas y money moves — y responde con orientación personalizada y accionable.
Cada respuesta incluye metadatos estructurados junto al texto de la respuesta, facilitando la construcción de experiencias de UI ricas sobre la conversación.
Cómo funciona el coach
El coach de IA no es un chatbot genérico. Para cada mensaje que recibe:
- Carga el perfil financiero completo del usuario (intake, transacciones, plan, metas)
- Identifica la intención y el tema del mensaje
- Responde en el idioma configurado del usuario
- Devuelve metadatos (
emotion,topic,intent) que tu UI puede usar para adaptar la experiencia
El coach adapta su tono basándose en el personality_type del usuario si se ha establecido uno via POST /plan/personalize.
Referencia del objeto
Solicitud
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
message | string | Sí | El mensaje del usuario al coach. Máx 2000 caracteres. |
Respuesta
| Campo | Tipo | Descripción |
|---|---|---|
reply | string | La respuesta del coach en el idioma configurado del usuario |
emotion | string | El tono emocional de la respuesta (ej.: "encouraging", "neutral", "cautious", "celebratory") |
topic | string | El tema financiero relacionado con el mensaje (ej.: "savings", "spending", "goals", "debt", "general") |
intent | string | Intención clasificada del mensaje del usuario (ej.: "progress_check", "advice_request", "transaction_log", "goal_update", "emotional_support") |
POST /v1/users/{user_id}/chat/messages
Envía un mensaje al coach financiero de IA en nombre de un usuario y devuelve la respuesta del coach.
Parámetros de ruta
| Parámetro | Tipo | Requerido | Descripción |
|---|---|---|---|
user_id | string | Sí | El ID de usuario de Ozzie |
Cuerpo de la solicitud
| Campo | Tipo | Requerido | Descripción |
|---|---|---|---|
message | string | Sí | El mensaje de texto del usuario |
Solicitud
- curl
- Node.js
- Python
curl -X POST https://api.ozzieapp.com/v1/users/usr_4f8a1b2c3d/chat/messages \
-H "Authorization: Bearer ozp_Y2xpZW50X2ExYjJjM2Q0OnNrX2xpdmVfeEs5bVAycVI3dEwu" \
-H "Content-Type: application/json" \
-d '{
"message": "¿Cómo voy con mi meta de ahorro?"
}'
const token = Buffer.from(
`${process.env.OZZIE_CLIENT_ID}:${process.env.OZZIE_CLIENT_SECRET}`
).toString('base64');
const response = await fetch(
'https://api.ozzieapp.com/v1/users/usr_4f8a1b2c3d/chat/messages',
{
method: 'POST',
headers: {
'Authorization': `Bearer ${token}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
message: '¿Cómo voy con mi meta de ahorro?',
}),
}
);
const { data } = await response.json();
console.log(data.reply);
import base64, os, httpx
token = base64.b64encode(
f"{os.environ['OZZIE_CLIENT_ID']}:{os.environ['OZZIE_CLIENT_SECRET']}".encode()
).decode()
response = httpx.post(
"https://api.ozzieapp.com/v1/users/usr_4f8a1b2c3d/chat/messages",
headers={
"Authorization": f"Bearer {token}",
"Content-Type": "application/json",
},
json={"message": "¿Cómo voy con mi meta de ahorro?"},
)
print(response.json()["data"]["reply"])
Respuesta
{
"object": "chat_message",
"data": {
"reply": "¡Estás haciendo un progreso real! Has ahorrado $1,200 hacia tu Fondo de Emergencia de $10,000 — eso es el 12% de tu meta. Con tu contribución quincenal actual de $150, vas camino a alcanzar $3,000 en unos 9 meses. Tu próxima transferencia programada es el 19 de mayo. ¿Quieres que te muestre algunas formas de acelerar esto?",
"emotion": "encouraging",
"topic": "savings",
"intent": "progress_check"
}
}
Ejemplos de conversaciones
Pidiendo consejos sobre gastos
Solicitud:
{
"message": "Siento que estoy gastando demasiado en comida. ¿Qué debería hacer?"
}
Respuesta:
{
"object": "chat_message",
"data": {
"reply": "Tienes razón en notarlo — la comida es tu mayor categoría discrecional este mes con $680, que es aproximadamente el 18% de tus ingresos netos. Una meta razonable para alguien con tus ingresos y objetivos es alrededor de $400–450/mes. La mayor brecha parece ser comer fuera ($310) versus supermercado ($370). Preparar dos o tres cenas por semana podría ahorrarte $80–100/mes de forma realista sin sentirse como un gran sacrificio. ¿Quieres que añada una meta específica de gasto en comida a tu plan?",
"emotion": "neutral",
"topic": "spending",
"intent": "advice_request"
}
}
Registrando una transacción via chat
Solicitud:
{
"message": "Acabo de gastar $45 en el supermercado"
}
Respuesta:
{
"object": "chat_message",
"data": {
"reply": "Anotado — registré $45 en el Supermercado bajo Alimentación. Tu total en alimentación para mayo ahora es $215. Vas camino a mantenerte dentro de tu presupuesto de comida este mes, lo que es genial. ¡Sigue así!",
"emotion": "encouraging",
"topic": "spending",
"intent": "transaction_log"
}
}
Pidiendo apoyo emocional
Solicitud:
{
"message": "Siento que nunca voy a salir de las deudas. Es abrumador."
}
Respuesta:
{
"object": "chat_message",
"data": {
"reply": "Ese sentimiento es completamente válido — cargar deudas es genuinamente estresante. Pero esto es lo que tus números realmente dicen: con tu tasa de pago actual de $200/mes, estarás libre de deudas en aproximadamente 26 meses. Eso no es para siempre — es una línea de llegada. Y cada pago que haces acorta ese plazo. Ya has pagado $850 desde que empezaste. ¿Quieres ver una pequeña cosa que podrías ajustar para reducir algunos meses?",
"emotion": "cautious",
"topic": "debt",
"intent": "emotional_support"
}
}
Actualización de meta via chat
Solicitud:
{
"message": "Quiero cambiar mi meta. Prefiero ahorrar para un viaje que pagar mi tarjeta de crédito."
}
Respuesta:
{
"object": "chat_message",
"data": {
"reply": "Totalmente razonable — tú decides qué importa. Solo para que tengas el panorama completo: tu saldo de tarjeta de crédito es $2,100 y estás pagando 19.9% de TAE, lo que significa que te está costando unos $35/mes en intereses. Un fondo de viaje crecería más rápido si liquidaras la tarjeta primero. Dicho esto, si el viaje es una prioridad próxima que te mantiene motivado, absolutamente podemos construir un plan alrededor de eso. ¿Quieres que ejecute ambos escenarios para que puedas comparar?",
"emotion": "neutral",
"topic": "goals",
"intent": "goal_update"
}
}
Errores
| Código | Estado HTTP | Cuándo ocurre |
|---|---|---|
UNAUTHORIZED | 401 | Credenciales ausentes o inválidas |
NOT_FOUND | 404 | El usuario no existe |
VALIDATION_ERROR | 422 | Campo message ausente o supera 2000 caracteres |
INVALID_JSON | 400 | El cuerpo de la solicitud no es JSON válido |
INTAKE_REQUIRED | 422 | El usuario no tiene intake financiero — el coach necesita contexto para responder con sentido |
RATE_LIMIT_EXCEEDED | 429 | Demasiadas solicitudes de chat en la ventana actual |
INTERNAL_ERROR | 500 | La generación de IA falló — seguro para reintentar |
Usa los campos topic e intent para enriquecer tu UI. Por ejemplo: muestra un widget de gráfico de ahorro cuando topic sea "savings", reproduce una animación sutil cuando emotion sea "celebratory", o solicita al usuario que actualice su meta cuando intent sea "goal_update".
El coach no almacena historial de conversación entre llamadas en la versión actual de la API. Cada mensaje se procesa con el contexto financiero completo del usuario pero sin memoria de turnos anteriores del chat. Si tu aplicación necesita una UI de conversación persistente, mantén el historial de mensajes en tu lado e incluye opcionalmente contexto previo relevante en el texto del mensaje.