Empezar en 15 minutos
Del primer request al primer webhook. Todo contra sandbox, sin tocar nada real.
0. Lo que necesitas
Una credencial hp_test_… que te da la agencia que administra tu cuenta. Apunta a una subcuenta de prueba con datos ficticios.
export HAPEE_KEY="hp_test_..."
export HAPEE_URL="https://beta.hapee.ai/api/v1"
1. Confirmar que la credencial sirve · 1 min
curl -s "$HAPEE_URL/me" -H "Authorization: Bearer $HAPEE_KEY"
{
"key": { "id": 44, "name": "Mi ERP sandbox", "mode": "test",
"read_only": false, "scoped_to_subaccount": true },
"subaccount": { "id": 91, "name": "Cliente — Sandbox",
"timezone": "America/Santiago", "default_currency": "CLP",
"sandbox": true, "language": "es" },
"limits": { "requests_per_minute": 100, "batch_max_items": 100,
"events_retention_days": 30, "idempotency_window_hours": 24 },
"api_version": "v1"
}
Mira que sandbox diga true. Si dice false, paras acá: esa credencial apunta a datos reales.
2. Crear un contacto · 2 min
curl -s -X POST "$HAPEE_URL/contacts/upsert" \
-H "Authorization: Bearer $HAPEE_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: mi-primera-prueba-001" \
-d '{
"external_id": "ERP-DEMO-1",
"email": "prueba@ejemplo.cl",
"first_name": "Ana", "last_name": "Pérez",
"phone": "+56912345678",
"rut": "12.345.678-5"
}'
{ "data": { "id": 90211, "email": "prueba@ejemplo.cl", "…": "…" },
"created": true }
external_id es el id de tu sistema. Es lo que hace que la carga se pueda repetir sin duplicar: la segunda vez actualiza en lugar de crear.
3. Probar que la idempotencia funciona · 2 min
Corre el mismo comando otra vez, sin cambiar nada. Vas a recibir la misma respuesta y la cabecera Idempotent-Replay: true. No se creó un segundo contacto.
Ahora corre una tercera vez cambiando first_name pero dejando la misma Idempotency-Key:
{ "error": {
"code": "idempotency_key_reusada",
"message": "Esta Idempotency-Key ya se usó con un cuerpo distinto..."
} }
Eso es correcto: misma clave con otro cuerpo significa que la reusaste para otra cosa. Una clave por operación.
4. Registrar un webhook · 5 min
Necesitas una URL pública. Para probar en tu máquina, levanta un túnel:
ngrok http 3000 # te da algo como https://a1b2c3.ngrok-free.app
curl -s -X POST "$HAPEE_URL/webhooks/endpoints" \
-H "Authorization: Bearer $HAPEE_KEY" \
-H "Content-Type: application/json" \
-d '{
"url": "https://a1b2c3.ngrok-free.app/hooks",
"description": "Pruebas locales",
"events": ["*"]
}'
Guarda el secret ahora. Es la única vez que se muestra completo. Después solo vas a ver whsec_…aB3d.
Receptor mínimo
const express = require('express');
const crypto = require('crypto');
const app = express();
const SECRETO = 'whsec_aB3dE...';
app.post('/hooks', express.raw({ type: 'application/json' }), (req, res) => {
const crudo = req.body.toString('utf8');
const cab = req.get('X-Hapee-Signature') || '';
const { t, v1 } = Object.fromEntries(
cab.split(',').map(p => p.split('=').map(s => s.trim())));
const esperado = crypto.createHmac('sha256', SECRETO)
.update(`${t}.${crudo}`).digest('hex');
if (esperado !== v1) return res.sendStatus(401);
console.log('evento:', JSON.parse(crudo).type);
res.sendStatus(200);
});
app.listen(3000);
En producción hace falta comparación en tiempo constante y una ventana de frescura. Está completo en Webhooks, con ejemplos en Node, Python, PHP y C#.
5. Disparar el primer evento · 1 min
curl -s -X POST "$HAPEE_URL/webhooks/endpoints/12/ping" \
-H "Authorization: Bearer $HAPEE_KEY"
En tu consola: evento: webhook.test
Y ahora uno de verdad — actualiza el contacto del paso 2:
curl -s -X POST "$HAPEE_URL/contacts/upsert" \
-H "Authorization: Bearer $HAPEE_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: mi-primera-prueba-002" \
-d '{"external_id": "ERP-DEMO-1", "match_by": "external_id",
"first_name": "Ana María"}'
En tu consola: evento: contact.updated
Los eventos se disparan por todo lo que pasa en la subcuenta, no solo por lo que haces tú. Si alguien del equipo comercial mueve un negocio a «ganado» desde la aplicación, te llega igual.
6. Si no puedes exponer una URL · 2 min
Lo mismo, pero consultando tú:
curl -s "$HAPEE_URL/events?limit=10" -H "Authorization: Bearer $HAPEE_KEY"
Guarda el next_cursor y pásalo la próxima vez. Mismos eventos, mismo cuerpo.
7. Ver qué pasó con una entrega
curl -s "$HAPEE_URL/webhooks/deliveries?endpoint_id=12" \
-H "Authorization: Bearer $HAPEE_KEY"
Cada entrega dice su estado, cuántos intentos lleva, qué respondió tu endpoint y cuándo es el próximo intento.
Listo. ¿Y ahora?
Integrar un ERP
Los flujos completos, el mapeo de campos y el checklist de salida.
Webhooks
Firma en cuatro lenguajes y las reglas del receptor.
Referencia completa
Todos los endpoints con sus parámetros.
Antes de pasar a producción, el checklist está al final de la guía de integración. Pasar a live es cambiar la credencial y la URL del webhook: nada más.