Errors
Every error response has the same JSON body:
{ "code": "hook_not_found", "message": "We couldn't find this webhook. Check the link or create a new one in the app.", "docs": "https://developers.ggspeak.app/webhooks/erros#hook_not_found"}codeis stable: branch on it in your code.messageis for a person to read.messagecomes in the language of theAccept-Languageheader (Portuguese, Spanish or English). With no header it’s Portuguese.docspoints to the section of the Portuguese page named after thecode. The same sections live on this page, under the same names.- A
429also carriesretry_after.
| Status | code |
When |
|---|---|---|
| 404 | hook_not_found |
Wrong id or token, deleted webhook or channel |
| 404 | message_not_found |
A message that isn’t from the webhook |
| 410 | hook_paused |
The webhook is paused |
| 413 | payload_too_large |
Body over 16 KB |
| 422 | payload_unrecognized |
No format recognized |
| 422 | payload_invalid |
Broken JSON or an invalid field |
| 429 | rate_limited |
Over the send rate |
| 500 | internal |
Our side failed |
hook_not_found
Section titled “hook_not_found”404. The link doesn’t lead to any webhook. The response is the same for a wrong id and a wrong token, so it never confirms that an id exists.
{ "code": "hook_not_found", "message": "We couldn't find this webhook. Check the link or create a new one in the app.", "docs": "https://developers.ggspeak.app/webhooks/erros#hook_not_found"}Causes: the link was copied partially, the webhook was deleted, its token was replaced with New link, the channel was deleted, Integrations are turned off on the platform, or the URL suffix doesn’t exist (only /discord, /slack and /betterstack).
What to do: check the whole link. If it’s no longer in the app, generate a new one under Integrations and update the tool.
message_not_found
Section titled “message_not_found”404. On PATCH or DELETE of a message, the id doesn’t exist, belongs to a person, or belongs to another webhook.
{ "code": "message_not_found", "message": "This message doesn't exist or wasn't sent by this webhook.", "docs": "https://developers.ggspeak.app/webhooks/erros#message_not_found"}What to do: use the id returned by a ?wait=true response. A webhook can only touch messages it sent itself.
hook_paused
Section titled “hook_paused”410. Someone who manages the community paused the webhook.
{ "code": "hook_paused", "message": "This webhook is paused. Someone who manages the community can resume it.", "docs": "https://developers.ggspeak.app/webhooks/erros#hook_paused"}What to do: ask whoever manages the community to use Resume on the webhook. Retrying won’t help while it’s paused.
payload_too_large
Section titled “payload_too_large”413. The body is over 16 KB.
{ "code": "payload_too_large", "message": "The body is over 16 KB. Send less text.", "docs": "https://developers.ggspeak.app/webhooks/erros#payload_too_large"}What to do: send only the essentials. A card takes a title, a body and up to 6 fields: a whole log won’t fit, so send a summary and a link (Limits).
payload_unrecognized
Section titled “payload_unrecognized”422. The JSON arrived, but it lacks the fields of the expected format: with a suffix (/discord, /slack, /betterstack), that format’s fields; on the bare URL, no format matched (detection goes GGspeak, then Discord, then Slack).
{ "code": "payload_unrecognized", "message": "We don't recognize this format. Send text or card, or a Discord or Slack body.", "docs": "https://developers.ggspeak.app/webhooks/erros#payload_unrecognized"}On the bare URL, the body must be a JSON object with card or key (GGspeak), content or embeds (Discord), or text, attachments or blocks (Slack). With a suffix, that format applies: /betterstack expects the incident body (data.attributes). A Better Stack body is only read on the URL ending in /betterstack.
What to do: use one of the formats. If your tool sends its own JSON that GGspeak doesn’t know, add a step in between that builds a text or a card.
payload_invalid
Section titled “payload_invalid”422. The body isn’t valid JSON, or a field is outside what GGspeak accepts. The message names the field and the reason.
{ "code": "payload_invalid", "message": "Check the card.state field: use alert, warn, ok or info.", "docs": "https://developers.ggspeak.app/webhooks/erros#payload_invalid"}Broken JSON comes back as “The body isn’t valid JSON.” The field reasons:
| Reason | When |
|---|---|
| must be an object | card isn’t an object |
| must be a string | text, key or card.body isn’t a string |
| must be a list | card.fields isn’t a list |
| each field needs name and value as strings | An item in card.fields with no name or value |
| use alert, warn, ok or info | card.state has any other value |
| title is missing | card.title empty or absent |
| content or embeds is missing | content or embeds is present but has nothing to show (with neither field, it is payload_unrecognized) |
| text or card is missing | A GGspeak body with neither text nor card |
| text or attachments is missing | text, attachments or blocks is present but there is no text and no attachments with a color (with none of the three fields, it is payload_unrecognized) |
| is over 2,000 characters | text is too long |
| must be 1 to 128 visible ASCII characters, no spaces | key has the wrong shape |
What to do: fix the field the message names.
rate_limited
Section titled “rate_limited”429. Too many sends in a row. The body carries retry_after (seconds, decimal), and the Retry-After header carries the same value in whole seconds, like Discord.
{ "code": "rate_limited", "message": "Too many requests in a row. Wait a moment and try again.", "docs": "https://developers.ggspeak.app/webhooks/erros#rate_limited", "retry_after": 0.8}What to do: wait retry_after seconds and send again. If your tool fires a lot at once, fold the notices into one card or use the key (Card and key). The numbers are in Limits.
internal
Section titled “internal”500. Something went wrong on our side.
{ "code": "internal", "message": "Something went wrong on our side. Try again.", "docs": "https://developers.ggspeak.app/webhooks/erros#internal"}What to do: try again shortly. If it keeps happening, tell the GGspeak team.