Skip to content

Processing of a meeting failed ​

POST to your own endpoint meeting.failed

Protoki calls this address when processing a meeting breaks off — there are no minutes in that case.

This event is NOT on by default. A newly registered endpoint gets meeting.ready only; you add meeting.failed in the admin area under "Webhooks". That way an automation that already runs does not suddenly receive calls without minutes.

Signature check, retries and deduplication are identical to meeting.ready.

⚠️ retryable is always true: a meeting can be processed again from the app. Treat the event as a hint, not as a final verdict — a later meeting.ready for the same meeting is possible and normal.

Headers ​

NameTypeRequiredDescription
Protoki-SignaturestringyesTimestamp and signature: t=1770000000,v1=<hex>.
Protoki-EventstringyesValues: meeting.failed.
Protoki-DeliveryuuidyesDelivery id, for deduplication.

Body ​

Example

json
{
  "event": "meeting.failed",
  "delivery_id": "e07b6d13-84af-4c92-b5d7-0a9e1f83c246",
  "occurred_at": "2026-08-04T09:04:15Z",
  "workspace_id": "3b1f7c02-5d64-4c1a-9f88-2ac0e6b41d77",
  "data": {
    "meeting": {
      "id": "e07b6d13-84af-4c92-b5d7-0a9e1f83c246",
      "title": "Quarterly review",
      "platform": "string",
      "source": "string",
      "status": "string",
      "starts_at": "2026-08-04T08:00:00Z",
      "ends_at": "2026-08-04T09:00:00Z",
      "organizer_email": "anna@company.example",
      "join_url": "https://teams.microsoft.com/l/meetup-join/…"
    },
    "failure": {
      "stage": "transcribe",
      "retryable": true
    }
  },
  "links": {
    "meeting": "https://protoki.com/api/v1/meetings/e07b6d13-84af-4c92-b5d7-0a9e1f83c246",
    "app": "https://protoki.com/api/v1/meetings/e07b6d13-84af-4c92-b5d7-0a9e1f83c246"
  }
}
FieldTypeRequiredDescription
eventmeeting.failedyesWhich event this is. Branch on it, not on the shape of data.
delivery_iduuidyesStays the same across every retry — this is what you deduplicate double deliveries on.
occurred_atdate-timeyesWhen the event happened on our side, not when this attempt was sent.
workspace_iduuidyesThe workspace the meeting belongs to.
dataobjectyesThe payload of the event.
data.meetingobjectyesThe meeting this event is about.
data.meeting.iduuid—Identifies the meeting everywhere in this API.
data.meeting.titlestring—Subject, as the calendar or the upload spelled it.
data.meeting.platformstring—Where the meeting took place.
data.meeting.sourcestring—How the meeting reached Protoki.
data.meeting.statusstring—Where the meeting stood when this call went out.
data.meeting.starts_atdate-time | null—Start of the appointment. null for an upload, which has none.
data.meeting.ends_atdate-time | null—End of the appointment. null for an upload.
data.meeting.organizer_emailstring | null—Who invited. null when the calendar gave nothing.
data.meeting.join_urlstring | null—The link the recorder used to join. null for an upload.
data.failureobjectyesWhat went wrong, as far as it is safe to say.
data.failure.stagestringyesThe processing stage it broke off at (for example transcribe, protocol). Deliberately coarse — an internal error text is not handed out.
data.failure.retryablebooleanyesAlways true: a meeting can be processed again from the app, and the reconciler picks up anything left hanging anyway.
linksobjectyesReady-made addresses, so nothing has to be assembled by hand.
links.meetinguriyesThe meeting in this API.
links.appuriyesThe meeting in the Protoki app, for a person to open.

Response 200 ​

Accepted.

Other answers ​

CodeMeaning
410This receiver is gone — Protoki stops sending.

Protoki — EU/GDPR-compliant meeting notetaker.