Trigger via Webhooks
Notify your AI employees when something happens in your system. Fire-and-forget: you get 202 Accepted immediately, the employee processes the event in the background using their skills and tools.
TL;DR
POST an event to /api/webhook/ with your API key, an employee ID, and a payload describing what happened. The employee picks it up and acts on it. No waiting for a response.
This page covers inbound webhooks (external systems trigger your employee). For outbound webhooks (your employee sends data to external systems), see Send Outbound Webhooks in the Tools and Capabilities section.
When to Use This
Use webhooks when you want to tell an employee that something happened but do not need an immediate answer. The employee receives the event, understands the context, and takes action on its own.
- CI/CD. Notify when builds fail, deploys complete, or tests break
- E-commerce. Alert on new orders, refund requests, or inventory changes
- Support. Forward new tickets, escalations, or customer feedback
- Monitoring. Send alerts from Datadog, PagerDuty, or custom health checks
- CRM. Trigger follow-ups when deals close, contacts update, or meetings are scheduled
Webhook vs API: The API waits for a response (request-response). Webhooks are fire-and-forget, meaning you send the event and move on. The employee processes it in the background.
How It Works
Unlike the REST API (which waits for a response), webhooks are asynchronous. You fire an event and move on. The employee receives it, understands the context, and takes action, the same way they would if you told them in chat.
- Fire-and-forget. You get 202 immediately, the employee processes in the background
- Same execution. Webhook events run through the Dispatcher and execution pipeline, identical to every other channel
- Same billing. Credits are tracked and charged the same way
- Shared keys. API keys work across all programmatic channels
Enable the Channel
The Webhook channel is disabled by default. Enable it before sending events:
- Go to Settings, Technical, Communications
- Find Webhook under the Inbound channels
- Toggle it on
Authentication
Same as all programmatic channels. Bearer token in the Authorization header.
- Go to Settings, Communications
- Expand the Programmatic group
- Expand any channel card (API, MCP, Webhook, etc.)
- Click "New Key", give it a name, hit Enter
- Copy the key from the green banner. It will not be shown again
Endpoint
POST /api/webhook/
Send an event to an AI employee.
Request body:
| Field | Type | Required | Description |
|---|---|---|---|
employee_id |
UUID string | Yes | Which employee to notify |
payload |
string | Yes | What happened, plain text describing the event |
event |
string | No | Event type label (e.g., order.completed, deploy.failed) |
Request headers (optional):
| Header | Description |
|---|---|
Idempotency-Key |
Prevents duplicate processing. If the same key is sent within 5 minutes, the request is rejected as a duplicate |
Response (202 Accepted):
| Field | Type | Description |
|---|---|---|
message_id |
UUID string | Unique ID for this event |
employee_id |
UUID string | The employee that received it |
status |
string | Always "accepted" |
What the Employee Sees
The employee receives the event formatted as:
[Webhook: order.completed] Customer John placed order #1234 for $99.
If no event type is provided:
[Webhook] Customer John placed order #1234 for $99.
The employee then acts on it using their skills, duties, tools, and memory, just like any other message.
Error Responses
| Status | Meaning |
|---|---|
| 400 | Bad request: missing fields, invalid UUID, or malformed JSON |
| 401 | Invalid or missing API key |
| 403 | Channel not enabled, or email not verified |
| 413 | Request body exceeds 64 KB |
| 429 | Rate limit exceeded |
| 502 | Employee unreachable (infrastructure error) |
Rate Limits
- Per-IP (failed auth): 10 attempts per minute
- Per-API-key: 120 requests per minute
Exceeding limits returns 429 Too Many Requests.
Quick Start
curl
curl -X POST https://api-sistava.com/api/webhook/ \
-H "Authorization: Bearer sk-your-key" \
-H "Content-Type: application/json" \
-d '{
"employee_id": "YOUR_EMPLOYEE_UUID",
"event": "order.completed",
"payload": "Customer John placed order #1234 for $99."
}'
Python
import requests
requests.post(
"https://api-sistava.com/api/webhook/",
headers={"Authorization": "Bearer sk-your-key"},
json={
"employee_id": "YOUR_EMPLOYEE_UUID",
"event": "deploy.failed",
"payload": "Deploy to production failed: timeout on health check."
},
)
# 202: employee will handle it in the background
JavaScript / Node
await fetch("https://api-sistava.com/api/webhook/", {
method: "POST",
headers: {
"Authorization": "Bearer sk-your-key",
"Content-Type": "application/json",
},
body: JSON.stringify({
employee_id: "YOUR_EMPLOYEE_UUID",
event: "ticket.created",
payload: "New support ticket #567: 'Cannot log in after password reset'",
}),
});
// 202: fire and forget
With Idempotency Key
curl -X POST https://api-sistava.com/api/webhook/ \
-H "Authorization: Bearer sk-your-key" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: order-1234-completed" \
-d '{
"employee_id": "YOUR_EMPLOYEE_UUID",
"event": "order.completed",
"payload": "Customer John placed order #1234 for $99."
}'
Sending the same Idempotency-Key within 5 minutes returns 200 {"status": "duplicate"} instead of processing the event again. Use this to safely retry without triggering duplicate work.
Event Type Best Practices
Use dot-notation event types for clarity:
order.completedsupport.ticket_createddeploy.faileduser.signed_up
The event type is prepended to the payload as context for the employee: [Webhook: order.completed] Customer John placed order #1234...
Good to Know
- No response content. Webhooks are fire-and-forget. If you need the employee's answer, use the REST API instead
- Team leaders. If the employee is a team leader, they may delegate the event to a team member
- Idempotency. Use the
Idempotency-Keyheader to prevent duplicate processing during retries. The key is valid for 5 minutes - Payload size. Request body cannot exceed 64 KB. Keep payloads concise, include only the information the employee needs to act on
- Managing keys. Create, rename, and revoke from the Communications page. Revoking blocks all channels immediately
Troubleshooting
- 401 Unauthorized. Missing or invalid API key. Include
Authorization: Bearer sk-...in the request header. - 403 Forbidden. The webhook channel is not enabled. Enable it in Settings, Technical, Communications.
- 400 Bad Request. Check that
employee_idis a valid UUID andpayloadis a non-empty string. The body must be valid JSON. - 429 Too Many Requests. You are exceeding rate limits (120 per minute per key). Back off and retry.
- Employee not acting on the event. Make sure the
payloadtext clearly describes what happened and what action is expected. Use theeventfield for context.
Frequently Asked Questions
Q: Can I get the employee's response from a webhook? A: No. Webhooks are fire-and-forget. The employee processes the event in the background. If you need a response, use the REST API or A2A channel instead.
Q: How do I prevent duplicate events?
A: Include an Idempotency-Key header with a unique value per event. If the same key is sent within 5 minutes, the duplicate request is rejected.
Q: What format should the payload be in? A: Plain text describing what happened. Write it the way you would tell a colleague: "New order #1234 from John for $99, requesting express shipping."
Q: Can I send structured JSON in the payload?
A: The payload field must be a string. You can JSON-stringify an object and pass it as a string, but plain text usually works better because the employee reads it as a natural language prompt.
Q: Do webhooks cost credits? A: Yes. The employee processes the event the same way it would process any message. Token credits and runtime credits apply.