Your AI Connector Docs

API-ul Webhooks

Webhooks permit platformei să notifice celelalte sisteme ale tale în momentul în care se întâmplă ceva — un contact nou, un răspuns, o programare efectuată și multe altele. Acest API gestionează abonamentele propriu-zise: ce URL-uri primesc ce evenimente. Pentru detalii despre cum să primești și să verifici payload-urile pe care le primește endpoint-ul tău, consultă Webhooks.

Toate căile de mai jos sunt relative la URL-ul de bază al API-ului:

https://api.youraiconnector.com/v1

Fiecare cerere trebuie autentificată. Consultați Autentificare pentru cele patru metode acceptate. Exemplele de aici utilizează antetul X-API-Key (și o formă de parametru de interogare pentru cURL).

Notă: Webhook-urile trebuie să fie activate pentru contul tău. Dacă nu sunt, aceste endpoint-uri returnează un 403.


Cum sunt adresate abonamentele

Fiecare abonament are un id și un name opțional. Oricare dintre acestea poate fi utilizat ca {webhookId} în cale pentru actualizare, ștergere, testare, stare de sănătate și reactivare.

Preferă numele. ID-urile abonamentelor sunt poziționale, deci se pot schimba după ce un alt abonament este șters. Dacă setezi un name stabil atunci când creezi un abonament, adresează-l prin nume pentru a evita surprizele.


Listarea abonamentelor

GET /webhooks

cURL

curl "https://api.youraiconnector.com/v1/webhooks?apiKey=YOUR_API_KEY"

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks", {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/webhooks",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()

Răspuns

{
  "success": true,
  "webhooks": [
    {
      "id": "0",
      "name": "Order updates hook",
      "url": "https://hooks.example.com/incoming",
      "subscribed_to": ["Contact Created", "Replies"],
      "subscribed_to_tags": [],
      "created_at": "2026-06-09T12:00:00.000Z",
      "signing_enabled": true,
      "signing_secret_created_at": "2026-07-15T09:30:00.000Z",
      "retries_enabled": true,
      "enabled": true,
      "apply_to_sub_accounts": false
    }
  ]
}

signing_enabled și retries_enabled sunt opțiuni activate per abonament, ambele fiind dezactivate implicit până când le activați. Consultați Payload-uri semnate și Reîncercări.

apply_to_sub_accounts este opțiunea de moștenire a agenției — consultați Un abonament pentru toate conturile clienților. Dezactivată implicit și inertă în conturile care nu au conturi de clienți.

enabled este comutatorul pornit/oprit al abonamentului — consultați Dezactivarea unui abonament. Abonamentele dezactivate sunt în continuare listate aici.

Secretul de semnare în sine nu este inclus niciodată aici — citiți-l din GET /webhooks/{id}/signing-secret.


Listarea tipurilor de evenimente la care te poți abona

Returnează șirurile exacte pe care le poți utiliza în subscribed_to. Folosește acest lucru pentru a descoperi numele valide ale evenimentelor în loc să le introduci hard-coded.

GET /webhooks/events

cURL

curl "https://api.youraiconnector.com/v1/webhooks/events" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks/events", {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/webhooks/events",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()

Răspuns

Răspunsul este {"success": true, "events": [...]}, unde events conține în prezent 22 de șiruri exacte: Contact Created, Human Alerted, Appointment Booked, Replies, Reads, Deliveries, Credits Spent, Credits Recharged, Low Credit Balance, Contact Paused, Contact Do Not Disturb, Contact Unarchived, New Message, Contact Resumed, Chat Concluded, Task Created, Task Updated, Task Completed, Daily Summary Created, Channel Connected, Broadcast Started și Broadcast Completed (Channel Connected este acceptat în subscribed_to, dar nimic nu îl emite în prezent, așa că nu vă bazați pe el).

Pentru semnificația fiecărui eveniment și codul event pe care îl trimite în payload, consultați Cele 22 de evenimente Webhook. Acest endpoint reprezintă lista autoritară în orice moment — citiți-o în timp real în loc să codați numele în mod fix.


Crearea unui abonament

POST /webhooks

Câmp Obligatoriu Descriere
url Da URL HTTPS care va primi payload-urile evenimentelor prin POST. Trebuie să fie accesibil public.
subscribed_to Da O matrice nevidă de nume de evenimente (consultați /webhooks/events).
name Nu Un nume de afișare. Poate fi folosit ulterior și ca {webhookId}. Implicit este un nume cu marcaj temporal.
subscribed_to_tags Nu ID-uri de etichete care restrâng etichetele ce produc o notificare de rezumat al conversației. Nu limitează evenimentele abonamentului la acele etichete — pentru a primi o solicitare atunci când este aplicată o anumită etichetă, setați un URL webhook pe acea etichetă în fila Etichete a agentului (sau campaniei).
retries_enabled Nu Boolean, implicit false. Optați pentru reîncercări ale livrărilor eșuate.
generate_signing_secret Nu Boolean, implicit false. Generați un secret de semnare HMAC împreună cu abonamentul. Secretul este returnat o singură dată, ca un signing_secret de nivel superior în răspuns.
enabled Nu Boolean, implicit true. Treceți false pentru a crea abonamentul în stare dezactivată. Consultați Dezactivarea unui abonament.
apply_to_sub_accounts Nu Boolean, implicit false. Într-un cont de agenție, true face ca acest abonament să primească și evenimente din fiecare cont de client — consultați Un abonament pentru toate conturile clienților.

Reguli URL: URL-ul trebuie să utilizeze https:// și să fie accesibil public. Adresele http:// simple, localhost, adresele de rețea privată și adresele interne ale platformei sunt respinse cu un 400.

cURL

curl -X POST "https://api.youraiconnector.com/v1/webhooks?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "url": "https://hooks.example.com/incoming",
    "subscribed_to": ["Contact Created", "Replies"],
    "name": "Order updates hook"
  }'

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({
    url: "https://hooks.example.com/incoming",
    subscribed_to: ["Contact Created", "Replies"],
    name: "Order updates hook",
  }),
});
const data = await res.json();

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/webhooks",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "url": "https://hooks.example.com/incoming",
        "subscribed_to": ["Contact Created", "Replies"],
        "name": "Order updates hook",
    },
)
data = res.json()

Răspuns

{
  "success": true,
  "webhook_id": "1",
  "webhook": {
    "id": "1",
    "name": "Order updates hook",
    "url": "https://hooks.example.com/incoming",
    "subscribed_to": ["Contact Created", "Replies"],
    "subscribed_to_tags": [],
    "created_at": "2026-06-09T12:00:00.000Z"
  }
}

Actualizarea unui abonament

Furnizați cel puțin unul dintre url, subscribed_to, name, subscribed_to_tags, retries_enabled, enabled sau apply_to_sub_accounts. Câmpurile omise își păstrează valorile curente. subscribed_to și subscribed_to_tags sunt înlocuiri, nu îmbinări.

PUT /webhooks/{webhookId}

Actualizarea unui abonament nu afectează niciodată secretul său de semnare — gestionați acest lucru prin rutele pentru secretul de semnare.

Când URL-ul se modifică, livrarea pentru noul URL este reactivată automat, oferind unui punct final care a eșuat anterior un nou început.

cURL

curl -X PUT "https://api.youraiconnector.com/v1/webhooks/Order%20updates%20hook" \
  -H "X-API-Key: YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "url": "https://hooks.example.com/v2/incoming",
    "subscribed_to": ["Replies", "Chat Concluded"]
  }'

JavaScript

const res = await fetch(
  `https://api.youraiconnector.com/v1/webhooks/${encodeURIComponent("Order updates hook")}`,
  {
    method: "PUT",
    headers: {
      "X-API-Key": "YOUR_API_KEY",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      url: "https://hooks.example.com/v2/incoming",
      subscribed_to: ["Replies", "Chat Concluded"],
    }),
  }
);
const data = await res.json();

Python

import requests

res = requests.put(
    "https://api.youraiconnector.com/v1/webhooks/Order updates hook",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={
        "url": "https://hooks.example.com/v2/incoming",
        "subscribed_to": ["Replies", "Chat Concluded"],
    },
)
data = res.json()

Răspuns

{
  "success": true,
  "webhook_id": "0",
  "webhook": {
    "id": "0",
    "name": "Order updates hook",
    "url": "https://hooks.example.com/v2/incoming",
    "subscribed_to": ["Replies", "Chat Concluded"],
    "subscribed_to_tags": [],
    "created_at": "2026-06-09T12:00:00.000Z"
  }
}

Un ID sau nume necunoscut returnează 404 cu { "success": false, "error": "Webhook not found" }.


Ștergerea unui abonament

Elimină abonamentul astfel încât URL-ul său să nu mai primească sarcini utile. Contoarele sale de sănătate a livrării sunt resetate, deci re-adăugarea aceluiași URL ulterior începe cu o înregistrare curată.

DELETE /webhooks/{webhookId}

cURL

curl -X DELETE "https://api.youraiconnector.com/v1/webhooks/0" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks/0", {
  method: "DELETE",
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();

Python

import requests

res = requests.delete(
    "https://api.youraiconnector.com/v1/webhooks/0",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()

Răspuns

{
  "success": true
}

Trimiterea unei sarcini utile de test

Trimite o sarcină utilă (payload) eșantion către URL-ul abonamentului, astfel încât să puteți verifica receptorul capăt-la-capăt. Opțional, transmiteți un event pentru a controla ce tip de eveniment simulează eșantionul. Livrările de test nu afectează niciodată contoarele de sănătate ale abonamentului.

POST /webhooks/{webhookId}/test

Răspunsul returnează întotdeauna 200 și raportează rezultatul cu un indicator delivered — un test eșuat nu returnează o stare de eroare. Când delivered este false, răspunsul include detaliile eșecului.

Câmp Obligatoriu Descriere
event Nu Tipul de eveniment de simulat (trebuie să fie unul dintre /webhooks/events). Implicit este un eveniment de livrare.

cURL

curl -X POST "https://api.youraiconnector.com/v1/webhooks/0/test?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{ "event": "Contact Created" }'

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks/0/test", {
  method: "POST",
  headers: {
    "X-API-Key": "YOUR_API_KEY",
    "Content-Type": "application/json",
  },
  body: JSON.stringify({ event: "Contact Created" }),
});
const data = await res.json();

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/webhooks/0/test",
    headers={"X-API-Key": "YOUR_API_KEY"},
    json={"event": "Contact Created"},
)
data = res.json()

Răspuns (livrat)

{
  "success": true,
  "webhook_id": "0",
  "delivered": true
}

Răspuns (eșuat)

{
  "success": true,
  "webhook_id": "0",
  "delivered": false,
  "failure_type": "permanent",
  "status_code": 404,
  "error_message": "Request failed with status code 404"
}

failure_type este unul dintre permanent, temporary, timeout, network sau unknown.


Verifică starea livrării

Returnează înregistrarea stării livrării pentru URL-ul abonamentului: câte livrări au reușit și câte au eșuat, dacă livrarea este momentan suspendată după eșecuri repetate și detaliile celui mai recent eșec. Returnează "health": null atunci când nu a fost încercată nicio livrare încă.

GET /webhooks/{webhookId}/health

cURL

curl "https://api.youraiconnector.com/v1/webhooks/0/health" \
  -H "X-API-Key: YOUR_API_KEY"

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks/0/health", {
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();

Python

import requests

res = requests.get(
    "https://api.youraiconnector.com/v1/webhooks/0/health",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()

Răspuns

{
  "success": true,
  "webhook_id": "0",
  "url": "https://hooks.example.com/incoming",
  "health": {
    "consecutive_failures": 0,
    "total_failures": 2,
    "total_successes": 120,
    "is_disabled": false,
    "disabled_at": null,
    "disabled_reason": null,
    "last_failure": null,
    "last_success_at": "2026-06-09T12:00:00.000Z",
    "created_at": "2026-05-01T08:00:00.000Z",
    "updated_at": "2026-06-09T12:00:00.000Z"
  }
}

Când is_disabled este true, livrarea către URL a fost suspendată automat după eșecuri repetate. Remediază receptorul, apoi reactivează-l (mai jos).


Reactivează livrarea

Reia livrarea pentru un webhook al cărui URL a fost suspendat automat după eșecuri repetate. Aceasta resetează indicatorul de suspendare și contoarele de eșecuri, dar nu încearcă o livrare — folosește punctul final de testare ulterior pentru a confirma că receptorul tău este din nou funcțional.

POST /webhooks/{webhookId}/reenable

cURL

curl -X POST "https://api.youraiconnector.com/v1/webhooks/0/reenable?apiKey=YOUR_API_KEY"

JavaScript

const res = await fetch("https://api.youraiconnector.com/v1/webhooks/0/reenable", {
  method: "POST",
  headers: { "X-API-Key": "YOUR_API_KEY" },
});
const data = await res.json();

Python

import requests

res = requests.post(
    "https://api.youraiconnector.com/v1/webhooks/0/reenable",
    headers={"X-API-Key": "YOUR_API_KEY"},
)
data = res.json()

Răspuns

{
  "success": true,
  "webhook_id": "0"
}

Dezactivarea unui abonament

enabled este propriul comutator pornit/oprit al abonamentului. Dezactivarea acestuia oprește livrările, păstrând în același timp intacte URL-ul, lista de evenimente și secretul de semnare.

# Off
curl -X PUT "https://api.youraiconnector.com/v1/webhooks/0?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"enabled": false}'

# Back on
curl -X PUT "https://api.youraiconnector.com/v1/webhooks/0?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"enabled": true}'
  • Absența înseamnă pornit. Un abonament creat înainte de existența acestui câmp nu are nicio valoare enabled stocată și livrează normal. GET /webhooks raportează întotdeauna un boolean concret.
  • Abonamentele dezactivate sunt încă listate de GET /webhooks — așa le găsiți pentru a le reactiva.
  • O reîncercare pusă în coadă înainte de dezactivare nu se reia: reîncercarea recitește abonamentul în momentul trimiterii și renunță dacă acesta este dezactivat.
  • Nimic din ceea ce a fost suprimat în timpul dezactivării nu este redat atunci când îl reactivați.

Distinct de dezactivarea automată după eșecuri repetate, care este raportată de GET /webhooks/{id}/health ca is_disabled și ștearsă cu POST /webhooks/{id}/reenable. enabled este comutatorul contului; is_disabled este al nostru. Niciunul nu îl anulează pe celălalt — un abonament trebuie să fie atât activat, cât și să nu fie dezactivat automat pentru a livra.


Un abonament pentru toate conturile clienților (agenții)

Într-un cont de agenție, setați apply_to_sub_accounts: true pe un abonament (la momentul creării sau prin PUT) și acesta va primi și evenimentele care au loc în fiecare dintre conturile clienților agenției — un singur endpoint acoperă întreaga agenție, în loc să recreați abonamentul pe fiecare cont de client.

curl -X PUT "https://api.youraiconnector.com/v1/webhooks/0?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"apply_to_sub_accounts": true}'

Cum funcționează:

  • Blocul user diferențiază conturile. Blocul user al fiecărui payload identifică contul pe care a avut loc efectiv evenimentul, astfel încât receptorul dvs. să poată direcționa per client.
  • Setările proprii ale abonamentului agenției se aplică peste tot. Lista sa de evenimente, secretul de semnare și opțiunea de reîncercare sunt utilizate și pentru livrările moștenite.
  • Abonamentul propriu al unui cont de client la același URL are prioritate. Dacă un cont de client are propriul abonament care indică același URL, acesta este utilizat pentru evenimentele acelui cont — același eveniment nu este livrat niciodată de două ori către un singur endpoint.
  • Conturile clienților nu îl văd. Abonamentele moștenite nu apar în lista proprie de webhook-uri a unui cont de client, iar clientul nu le poate dezactiva — doar agenția le gestionează.
  • Starea livrării este urmărită per cont de client. Un endpoint care continuă să eșueze este dezactivat automat pentru contul ale cărui livrări au eșuat, nu pentru întreaga agenție.
  • subscribed_to_tags nu se moștenește. Lista de etichete face referire la etichetele proprii ale agenției, care nu există în conturile clienților — restrângerea rezumatului conversației se aplică doar evenimentelor proprii ale agenției.
  • Inert în altă parte. Într-un cont fără conturi de clienți, indicatorul este stocat corect și nu face nimic.

Antete pentru fiecare livrare

Aceste trei antete sunt trimise la fiecare livrare, indiferent dacă abonamentul este semnat sau nu:

Antet Semnificație
X-Webhook-Delivery ID stabil pentru evenimentul logic. Identic între reîncercări — utilizați-l pentru deduplicare.
X-Webhook-Attempt Numărul încercării (începând de la 1).
X-Webhook-Event Numele evenimentului.

Payload-uri semnate

Semnarea este opțională, dezactivată implicit și setată per abonament. Când un abonament are un secret de semnare, fiecare livrare conține încă două antete pe lângă cele trei trimise la fiecare livrare (X-Webhook-Delivery, X-Webhook-Attempt și X-Webhook-Event):

Antet Semnificație
X-Webhook-Signature v1=<hex> — HMAC-SHA256 al șirului "<timestamp>.<raw request body>", chemat cu secretul de semnare per webhook pe care îl generați și rotiți la GET/POST/DELETE /v1/webhooks/{webhookId}/signing-secret.
X-Webhook-Timestamp Ora trimiterii, în secunde Unix. Inclusă în semnătură, deci nu poate fi modificată independent.

Pentru verificare, recalculați HMAC-SHA256 peste corpul brut (raw) cu secretul dumneavoastră și comparați-l cu antetul. Verificați împotriva corpului cererii brute. Re-serializarea JSON-ului analizat modifică octeții și strică comparația. Respingeți livrările al căror marcaj temporal este în afara unei ferestre de prospețime (300s este o valoare implicită rezonabilă) pentru a preveni atacurile de tip replay și comparați folosind o funcție sigură la sincronizare (timing-safe).

Consultați Payload-uri semnate pentru exemple complete de verificare în Node și Python.

Semnarea nu este același lucru cu autentificarea API. API-ul REST în sine se autentifică cu chei API în loc de OAuth (OAuth 2.1 există pentru serverele MCP pe care le înregistrați ca instrumente bot) și nu există încă pachete SDK oficiale pentru npm sau PyPI — apelați endpoint-urile cu orice client HTTP.

Citiți secretul de semnare

GET /webhooks/{id}/signing-secret

curl "https://api.youraiconnector.com/v1/webhooks/0/signing-secret?apiKey=YOUR_API_KEY"

Răspuns

{
  "success": true,
  "webhook_id": "0",
  "signing_enabled": true,
  "signing_secret": "whsec_1a2b3c...",
  "signing_secret_created_at": "2026-07-15T09:30:00.000Z"
}

Când semnarea este dezactivată, signing_enabled este false și signing_secret este null.

Generați sau rotiți secretul de semnare

POST /webhooks/{id}/signing-secret

Creează un secret (activând semnarea) sau îl înlocuiește pe cel existent. Returnează noul secret.

curl -X POST "https://api.youraiconnector.com/v1/webhooks/0/signing-secret?apiKey=YOUR_API_KEY"

Răspuns

{
  "success": true,
  "webhook_id": "0",
  "signing_enabled": true,
  "signing_secret": "whsec_9f8e7d...",
  "signing_secret_created_at": "2026-07-15T10:00:00.000Z"
}

Rotația intră în vigoare imediat — următoarea livrare este semnată doar cu noul secret. Acceptați ambele secrete pentru o scurtă perioadă în timp ce implementați modificarea pe un endpoint activ.

De asemenea, puteți genera un secret în momentul creării transmițând "generate_signing_secret": true către POST /webhooks; răspunsul va include apoi un câmp signing_secret la nivel superior.

Dezactivarea semnării

DELETE /webhooks/{id}/signing-secret

curl -X DELETE "https://api.youraiconnector.com/v1/webhooks/0/signing-secret?apiKey=YOUR_API_KEY"

Răspuns

{
  "success": true,
  "webhook_id": "0",
  "signing_enabled": false
}

Toate cele trei rute pentru secrete de semnare necesită permisiunea edit pentru integrări, inclusiv GET — secretul este o credențială care poate falsifica livrări, deci nu este expus rolurilor cu drept de citire.


Reîncercări

Opțional, dezactivat implicit și configurat per abonament prin intermediul booleanului retries_enabled din POST /webhooks sau PUT /webhooks/{id}.

curl -X PUT "https://api.youraiconnector.com/v1/webhooks/0?apiKey=YOUR_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"retries_enabled": true}'

Când este activată, o livrare eșuată este reîncercată la 1m, 5m, 30m și 2h după prima încercare (aproximativ 2h 40m de acoperire).

  • Reîncercate: răspunsuri 5xx, timeout-uri și eșecuri de conexiune.
  • Nereîncercate: orice 4xx. Receptorul respinge cererea în sine, deci retrimiterea ei neschimbată doar reproduce respingerea.

Reîncercările fac posibilă livrarea duplicată — un endpoint care a procesat un eveniment, dar a expirat înainte de a răspunde, îl va primi din nou. Folosește X-Webhook-Delivery pentru deduplicare, deoarece acesta rămâne constant pe parcursul încercărilor. Acesta este motivul pentru care reîncercările sunt opționale.

Contoarele delivery-health numără o livrare întreagă, nu fiecare încercare: un eșec este înregistrat doar după epuizarea tuturor reîncercărilor, deci activarea reîncercărilor nu face ca declanșatorul de dezactivare automată să fie activat mai devreme.


Erori

Toate erorile folosesc plicul standard:

{
  "success": false,
  "error": "Webhook not found"
}

Cazuri comune: un URL care nu este permis, un subscribed_to gol/invalid sau câmpuri lipsă returnează 400; un id sau nume necunoscut returnează 404; iar un 403 înseamnă că webhook-urile nu sunt activate pentru contul tău. Consultă Erori pentru lista completă.


Pașii următori