Post an alert to an integration
The endpoint external monitoring tools call, and the one to call yourself to prove an integration you just created actually works end to end.
Authentication is the integration secret, not an API key. Send Authorization: Bearer <secret> or X-WardenPoint-Secret: <secret>; CloudWatch integrations may also use ?secret=<secret> because AWS SNS cannot set headers. The secret is the one returned once by the create endpoint (or the newer one a dashboard rotation issued — after such a rotation the previous secret is still accepted for a grace window, so a sender that has not been updated yet keeps delivering). A request that fails to authenticate answers 401 and stores NOTHING: no alert, no event, nobody is paged. The rejection is recorded on the integration's last_error and in the wardenpoint_observability_inbound_auth_failures_total counter, so a sender left on a stale secret is visible rather than silent. An API key is neither needed nor accepted here — this route sits outside the key middleware entirely, and the tenant is taken from the integration in the path.
When the integration has hmac_enabled: true, the plain secret stops working. Signed requests need X-WardenPoint-Timestamp (current Unix seconds, within 300 s of server time) and X-WardenPoint-Signature (lowercase hex hmac_sha256("<timestamp>.<raw body>", secret)). Each signature is accepted exactly once inside the tolerance window, so a replayed request answers 401. GitHub integrations ignore the flag and always use GitHub's own X-Hub-Signature-256 over the raw body, keyed by the same secret.
Not idempotent, and deliberately so. Repeating the same body does not overwrite anything: the alert is deduplicated by identity, so you get one alert with N events, and every one of those N counts toward the accumulation threshold that decides whether people get paged. A client that retries on timeout inflates the count. Send a stable external_alert_id (or deduplication_key) so repeats collapse onto one alert rather than creating several, and expect the event counter to grow.
Unknown formats are accepted, not rejected. Keys outside the whitelist are dropped and the rest is normalised as best it can be: an unrecognised body still produces an alert, titled External alert, severity unknown, status firing. That is what "the webhook worked but nothing sensible arrived" looks like — check title in the response's alert rather than assuming 202 means the mapping is right. The one shape that is refused outright is a malformed value in a recognised key: a source_url that is not a URL, or a title over 255 characters, answers 422.
The severity you send does not set the notification priority. It decides which routing rule matches; the matched rule's ACTION then decides how loudly the alert arrives. escalate produces a critical notification and starts the escalation chain. message produces a normal one and starts no chain at all — only the initial step of the escalation policy runs, so a policy that would have reached three people reaches one, and nothing waits for an acknowledgement. A severity: warning alert matched by an escalate rule wakes people; a severity: critical alert matched by a message rule wakes nobody. Read the action field of the response to see which of the two happened.
202 does not mean somebody was paged. Read notification_queued: when it is false, queue_skip_reason says why in machine-readable form — suppressed_by_rule (the accumulation policy is holding it back, see event_count vs threshold_count), no_group (no routing rule matched and the integration has no fallback group), group_has_no_recipients, all_recipients_inactive (the group has members but every one of them is switched off — their contacts are fine, the people are not), channel_not_configured (the people are switched on and their contacts are fine — the channel that would carry the alert is not set up on this installation, e.g. no mailer configured, so fix the setup rather than the contacts), no_routable_contacts (at least one member is switched on and still has no working contact for the configured channels) or deferred_to_inbox_digest. Verifying a fresh integration means checking that field, not the status code.\n\nWhen the reason is about routing, read queue_skip_detail before touching anything. no_routable_contacts and channel_not_configured name a symptom, and the repair depends on how the channel was chosen. The detail says which channel and provider the first step resolved to (resolved_channel, resolved_provider, the whole ladder in resolved_steps) and where that decision came from (source): group_rule / group_policy mean the group's own configuration picked it, company_default_no_group_rule means the group has no rule for this priority and the account-wide default was used, company_default_empty_group_rule means its rule carries no immediate step. message states all of it in one sentence. A null resolved_channel means no step resolved at all — the company can deliver on none of the channels of that priority, and nothing about the recipients or their contacts is wrong.\n\nAnd notification_queued: true still does not promise a page. A queued notification whose every channel fails ends failed, and at that point the umbrella guarantee fires: the account owner is emailed that the alert reached nobody. That email is not a page — the people this alert was routed to received nothing. It shows up as a notification of its own in GET /notifications, marked is_owner_fallback: true, while the alert's own notification keeps delivered_via_owner_fallback: true in its metadata and stays failed. When verifying an integration, read the notification's status through GET /notifications/{notification}/status; a rescue email in the account is evidence that delivery failed, never that it worked.
Two integration types short-circuit before an alert is created and answer 200 instead of 202: an AWS SNS SubscriptionConfirmation (which is confirmed for you) or UnsubscribeConfirmation on a CloudWatch integration, and a GitHub ping or a lifecycle event that is not a finished pass/fail run.
Request
- Base URL: https://wardenpoint.com (the document declares no server; this is the origin it was published from)
- URL: https://wardenpoint.com/api/v1/integrations/alerts/{integration}
- Auth: HTTP bearer
Path parameters
UUID of the observability integration — the last path segment of its endpoint_url.
Request body
Response
A control message was handled and no alert was created: an SNS subscription confirmed or unsubscribe acknowledged (CloudWatch), or a GitHub ping or non-actionable lifecycle event. Body carries success and a human-readable message; GitHub ignores also set ignored: true.
Changes
No recorded changes to this operation across all 1 revision of this API.