Megérkezett a ThunderPhone 2.0.Önkiszolgálóan, már 2¢/perctől.Olvassa el a bejelentést

Webhooks

Webhookok áttekintése

Ismerje meg, hogyan továbbítja a ThunderPhone a valós idejű eseményeket, hogyan ellenőrizheti az aláírásokat, és hogyan viszonyul egymáshoz a régi és a végpontalapú kézbesítési modell.

ThunderPhone HTTP POST kéréseket küld az Ön szerverére, amikor egy hívás során események történnek — bejövő hívás indul, hívás ér véget, értékelési futás fejeződik be, riasztás aktiválódik stb. Két kézbesítési modell érhető el:

Az eseménykatalógusban felsorolt összes eseménytípus webhook-végpontokon keresztül kerül kézbesítésre. A hat hívás-életciklus esemény (telephony.incoming, telephony.complete, telephony.tool, web.incoming, web.complete, web.tool) szintén elküldésre kerül az örökölt, egy URL-es webhookhoz — ha örökölt URL-lel és megfelelő végponttal is rendelkezik, az eseményt mindkét útvonalon megkapja. A blokkoló viselkedés (a telephony.incoming / web.incoming konfigurációs adatcsere és a webhook módú eszközindítás) kizárólag az örökölt útvonalon érhető el; minden végpontkézbesítés indítás utáni értesítés.

Hasznos adat formátuma

A végpontkézbesítések data, event_id és type mezőket tartalmazó JSON-objektumok:

{
  "data": {
    "call_id": 987654321,
    "from_number": "+14155550199",
    "to_number": "+15551234567"
  },
  "event_id": "3f6b2ad0-1c9e-4a57-9f2b-8f6f0f9d2f11",
  "type": "telephony.incoming"
}

Az event_id minden kibocsátott eseményhez egyedi. Újrapróbálkozások és az eseményt fogadó összes végpont esetén azonos — ez alapján végezzen deduplikációt.

Az örökölt, egy URL-es webhook ugyanazt a type és data mezőt küldi, de event_id nélkül:

{
  "type": "telephony.incoming",
  "data": { "call_id": 987654321, "from_number": "+14155550199", "to_number": "+15551234567" }
}

A hálózaton minden törzs kanonikus formában szerializálódik — a kulcsok ábécérendben vannak, nincs szóköz, a kódolás UTF-8. A dokumentációban szereplő, formázott példák kizárólag az olvashatóságot szolgálják.

Az eseménytípusok és a hasznosadat-mezők teljes listáját az Eseménykatalógusban találja.

Aláírás-ellenőrzés

Minden kérés két aláírást tartalmaz, mindkettő HMAC-SHA256, amelynek kulcsa a végpont secret értéke (vagy régebbi kézbesítések esetén a szervezetszintű webhook secret értéke):

  • Az X-ThunderPhone-Signature-V2: t=<unix seconds>,v1=<hex> aláírja az időbélyeget, a metódust, az útvonalat és a lekérdezést, valamint a nyers törzset. Ellenőrizze ezt, és utasítsa el azokat a kéréseket, amelyeknél a t értéke több mint 5 perccel eltér az Ön órájától, hogy egy elfogott kérést később ne lehessen újra lejátszani. Az újrapróbálkozásokat elküldéskor ismét aláírjuk.
  • Az X-ThunderPhone-Signature csak a nyers törzset írja alá. Változatlanul továbbra is elküldjük, hogy a meglévő ellenőrzők továbbra is működjenek.

Lépések

  1. Olvassa be a fejlécet, a metódust, a nyers elérési utat és lekérdezést, valamint a nyers törzset bármilyen feldolgozás előtt.
  2. Számítsa ki a <t>\n<METHOD>\n<path and query>\n<body> hexadecimális HMAC-SHA256 értékét a titkával.
  3. Utasítsa el a kérést, ha a t több mint 300 másodperccel eltér, vagy ha az eredmény konstans idejű összehasonlításban nem egyezik a v1 értékkel.

A törzsek kanonikus JSON-szerializálásúak (rendezett kulcsokkal, tömör elválasztókkal), és pontosan az általunk továbbított bájtokat írjuk alá. Az ellenőrzési útmutató tartalmazza a pontos aláírt karakterláncot, egy kidolgozott példát, SDK nélküli kódot és az örökölt fejlécet.

Python (Flask)
from flask import Flask, abort, request
from thunderphone import verify_signature
 
app = Flask(__name__)
 
@app.post("/thunderphone-webhook")
def handle():
    query = request.query_string.decode()
    if not verify_signature(
        request.headers.get("X-ThunderPhone-Signature-V2"),
        secret=WEBHOOK_SECRET,
        method=request.method,
        path=request.path + (f"?{query}" if query else ""),
        body=request.get_data(),  # raw bytes
    ):
        abort(401)
    event = request.get_json()
    # dispatch on event["type"] …
    return "", 204
Node.js (Express)
import express from "express";
import { verifySignature } from "@thunderphone/sdk";
 
const app = express();
app.post(
  "/thunderphone-webhook",
  express.raw({ type: "application/json" }),
  (req, res) => {
    const ok = verifySignature({
      header: req.header("X-ThunderPhone-Signature-V2"),
      secret: process.env.WEBHOOK_SECRET,
      method: req.method,
      path: req.originalUrl,
      body: req.body,
    });
    if (!ok) return res.sendStatus(401);
    const event = JSON.parse(req.body.toString("utf8"));
    // dispatch on event.type …
    res.sendStatus(204);
  },
);

Kézbesítési szemantika

Ezek a szemantikák az endpoint kézbesítésekre vonatkoznak. A régi, egyetlen URL-t használó webhook egyetlen szinkron kísérletből áll, újrapróbálkozás nélkül, kivéve a telefonhívások telephony.incoming konfigurációs egyeztetését, amelyet egyszer újrapróbálunk.

Újrapróbálkozások

Minden eseményt azonnal egyszer próbálunk kézbesíteni. Bármely 2xx válasz visszaigazolja a kézbesítést. Bármilyen más eredmény esetén (nem 2xx, kapcsolati hiba, időtúllépés) az első kísérlet után 1 p, 5 p, 30 p, 2 ó, 6 ó, 12 ó és 24 ó múlva próbáljuk újra — összesen 8 kísérlet 24 órán keresztül. Ha minden kísérlet sikertelen, a kézbesítés leáll, és az endpoint status="failing" jelölést kap a webhook endpointok között; e-mailt küldünk a szervezet tulajdonosainak és rendszergazdáinak, és ezt az irányítópulton is megjelenítjük. A 2xx választ adja vissza, amint a hasznos adat tartósan elfogadásra került; a feldolgozást végezze aszinkron módon. Az endpoint teszt API-jából indított tesztküldések az első kísérlet után körülbelül egy perccel egy újrapróbálkozást kapnak, és soha nem módosítják az endpoint állapotát.

Sorrendiség

A kézbesítési sorrend nem garantált. A gyakorlatban az eseményeket a kibocsátásuk sorrendjében kézbesítjük, de hibák esetén az újrapróbálkozások megváltoztathatják a sorrendet. Mindig deduplikáljon és egyeztessen call_id / objektumazonosító alapján.

Duplikátumok

A kézbesítés legalább egyszeri: egy olyan válasz utáni újrapróbálkozás, amelyet soha nem láttunk, megkettőzhet egy eseményt. Minden újrapróbálkozás ugyanazt az event_id értéket tartalmazza, ezért tárolja a feldolgozott azonosítókat, és hagyja ki az ismétlődéseket. Az event_id a végpontok között is közös — ugyanarra az eseményre feliratkozott két végpont ugyanazt az event_id értéket kapja.

Időtúllépések

Az endpoint-kézbesítések kísérletenként 30 mp időtúllépési idővel rendelkeznek. A régi útvonalon az élő hívási viselkedést vezérlő blokkoló kérések — a telephony.incoming / web.incoming konfigurációs egyeztetése — telefonhívás esetén az első kísérletnél 10 mp-re, a teljes egyeztetésnél az egyetlen újrapróbálkozást is beleértve 13 mp-re, widget-munkamenet esetén pedig 10 mp-re vannak korlátozva. A lassú válasz késlelteti a hívás felvételét, ezért törekedjen arra, hogy néhány másodpercen belül válaszoljon. Webhook módú eszközindítás esetén alapértelmezetten 20 mp engedélyezett, és az eszközdeklarációk felső szintű timeout értéket is megadhatnak.

Forrás IP-címek

A kimenő webhookok a ThunderPhone felhőbeli IP-tartományából érkeznek. Ha a tűzfal engedélyezési listát igényel, lépjen kapcsolatba az ügyfélszolgálattal, és megosztjuk az aktuális tartományokat.

Választás a régi és a végpont-alapú webhookok között

FunkcióÖrökölt (/v1/webhook)Végpontok (/v1/developer/webhook-endpoints)
URL-ek száma1 szervezetenkéntTöbb szervezetenként
Események lefedettségeCsak telephony.* / web.*Mind a 10 eseménytípus
Eseményszűrő—Végpontonként
ÚjrapróbálkozásokNincs, kivéve egyet a telefonhívás-konfiguráció cseréjéhez8 kísérlet 24 óra alatt
Borítéktype + datatype + data + event_id
Titkos kulcs rotációjaLecseréli az egyetlen titkos kulcsotVégpontonkénti titkos kulcs
Letiltás törlés nélkülPUT /v1/webhook ezzel: {"url": ""}status=disabled
Állapot láthatósága—active / disabled / failing
Blokkoló konfigurációcsereIgen (telephony.incoming / web.incoming)Soha — csak értesítések
Legjobb erreDinamikus híváskonfigurációEsemények feldolgozása éles környezetben

Az új integrációknak végpont-alapú webhookokon keresztül kell eseményeket fogadniuk. Csak akkor tartson meg (vagy adjon hozzá) régi URL-t, ha a hívásokat dinamikusan konfigurálja felvételkor, vagy webhook módú eszközmeghívást használ — ezek a kérés/válasz cserék csak a régi útvonalon futnak.


Kapcsolódó