Referência da API
Webhooks
Receber notificações de eventos em tempo real via webhooks.
Webhooks
Receba notificações em tempo real quando eventos ocorrem no OctaBuild. Webhooks permitem que sua aplicação reaja automaticamente a mudanças em terrenos, empreendimentos, unidades e registros financeiros.
Webhooks estão em desenvolvimento. Esta documentação descreve a interface planejada.
Como Funciona
OctaBuild Sua Aplicação
│ │
│ 1. Evento ocorre │
│ (ex: terreno criado) │
│ │
│ 2. POST com payload ──────────► │
│ │
│ ◄──────── 3. Responde 200 OK │
│ │Eventos Disponíveis
Terrenos
| Evento | Descrição |
|---|---|
land_plot.created | Terreno cadastrado |
land_plot.updated | Terreno atualizado |
land_plot.status_changed | Status do terreno alterado |
land_plot.score_updated | Score IA recalculado |
land_plot.deleted | Terreno removido |
Empreendimentos
| Evento | Descrição |
|---|---|
development.created | Empreendimento criado |
development.updated | Empreendimento atualizado |
development.phase_changed | Fase do empreendimento alterada |
development.archived | Empreendimento arquivado |
Unidades
| Evento | Descrição |
|---|---|
unit.created | Unidade cadastrada |
unit.updated | Unidade atualizada |
unit.status_changed | Status da unidade alterado |
unit.bulk_created | Unidades criadas em lote |
Clientes
| Evento | Descrição |
|---|---|
client.created | Cliente cadastrado |
client.updated | Cliente atualizado |
client.deactivated | Cliente desativado |
Financeiro
| Evento | Descrição |
|---|---|
financial.payable_created | Conta a pagar criada |
financial.payable_paid | Conta a pagar quitada |
financial.receivable_created | Conta a receber criada |
financial.receivable_confirmed | Recebimento confirmado |
financial.overdue | Conta vencida sem pagamento |
Formato do Payload
Todos os webhooks enviam um payload JSON via POST:
{
"id": "wh_evt_550e8400e29b41d4a716446655440000",
"event": "land_plot.status_changed",
"created_at": "2026-02-25T10:30:00Z",
"data": {
"id": "550e8400-e29b-41d4-a716-446655440000",
"name": "Terreno Alphaville",
"status": "due_diligence",
"previous_status": "negociacao"
}
}Headers
Cada requisição webhook inclui os seguintes headers:
| Header | Descrição |
|---|---|
Content-Type | application/json |
X-OctaBuild-Event | Nome do evento (ex: land_plot.created) |
X-OctaBuild-Signature | Assinatura HMAC-SHA256 do payload |
X-OctaBuild-Timestamp | Timestamp Unix da requisição |
X-OctaBuild-Delivery | ID único da entrega |
Verificando a Assinatura
Para garantir que o webhook veio do OctaBuild, verifique a assinatura:
import crypto from 'crypto';
function verifyWebhookSignature(payload, signature, secret) {
const expected = crypto
.createHmac('sha256', secret)
.update(payload)
.digest('hex');
return crypto.timingSafeEqual(
Buffer.from(signature),
Buffer.from(expected)
);
}
// No seu endpoint
app.post('/webhooks/octabuild', (req, res) => {
const signature = req.headers['x-octabuild-signature'];
const isValid = verifyWebhookSignature(
JSON.stringify(req.body),
signature,
process.env.OCTABUILD_WEBHOOK_SECRET
);
if (!isValid) {
return res.status(401).send('Invalid signature');
}
const { event, data } = req.body;
switch (event) {
case 'land_plot.status_changed':
console.log(`Terreno ${data.name}: ${data.previous_status} → ${data.status}`);
break;
case 'development.created':
console.log(`Empreendimento criado: ${data.name}`);
break;
case 'financial.overdue':
console.log(`Conta vencida: ${data.description}`);
break;
}
res.status(200).send('OK');
});import hmac
import hashlib
def verify_webhook_signature(payload, signature, secret):
expected = hmac.new(
secret.encode(),
payload.encode(),
hashlib.sha256
).hexdigest()
return hmac.compare_digest(signature, expected)
# No seu endpoint Flask
@app.route('/webhooks/octabuild', methods=['POST'])
def handle_webhook():
signature = request.headers.get('X-OctaBuild-Signature')
is_valid = verify_webhook_signature(
request.data.decode(),
signature,
os.environ['OCTABUILD_WEBHOOK_SECRET']
)
if not is_valid:
return 'Invalid signature', 401
event = request.json['event']
data = request.json['data']
if event == 'land_plot.status_changed':
print(f"Terreno {data['name']}: {data['previous_status']} → {data['status']}")
return 'OK', 200Política de Retry
Se sua aplicação não responder com 2xx dentro de 10 segundos, o OctaBuild tentará novamente:
| Tentativa | Intervalo |
|---|---|
| 1ª | Imediata |
| 2ª | 1 minuto |
| 3ª | 5 minutos |
| 4ª | 30 minutos |
| 5ª | 2 horas |
Após 5 tentativas sem sucesso, o webhook é marcado como falho.
Boas Práticas
- Responda rápido — Retorne
200 OKimediatamente e processe o evento em background - Seja idempotente — O mesmo evento pode ser entregue mais de uma vez
- Verifique a assinatura — Sempre valide o header
X-OctaBuild-Signature - Use HTTPS — Registre apenas URLs com HTTPS
- Monitore falhas — Acompanhe o dashboard de webhooks para identificar problemas
Suporte
- Email: suporte@octabuild.ai
- Documentação: Você está aqui!