Skip to content

Webhook events ​

Every event Omaya can POST to an endpoint of yours, what fires it, and how to verify it really came from us.

Read out of the platform

This page is generated from the code that runs your instance, so it cannot drift from what the platform actually does.

Subscribe on Connectors → Outbound webhooks (/admin/connector/outbound-webhooks). One endpoint can subscribe to several event types; the same event type can go to several endpoints.

The catalog on that page also shows which events your tenant has actually received in the last 30 days, which is usually the faster way to answer "why am I not getting anything?" — if an event has never fired for you, the subscription is probably not the problem.

What a delivery looks like ​

POST to your URL, Content-Type: application/json, with these headers:

HeaderWhat it carries
X-Omaya-EventThe event type, e.g. zone.occupancy.status. Route on this, not on the payload.
X-Omaya-DeliveryA UID that is the same across every retry of one logical delivery. Use it to de-duplicate.
X-Omaya-TimestampUnix seconds at the moment the attempt was signed.
X-Omaya-Signaturesha256= + HMAC-SHA256 of <timestamp>.<raw body>, keyed with your endpoint's secret.
User-AgentOmaya-Webhook/1.1

Verify the signature against the raw request body, before any JSON parsing or re-serialisation — a re-encoded body will not match. In PHP that is:

php
$expected = 'sha256=' . hash_hmac('sha256', $timestamp . '.' . $rawBody, $secret);
hash_equals($expected, $signatureHeader);   // never ===

Also check the timestamp is recent (a few minutes) so an old, valid, captured delivery cannot be replayed at you.

Timeout and retries. We wait 10 seconds for your response. Anything outside 2xx — or no response at all — is retried: 6 attempts in total, backing off 1 min, 5 min, 15 min, 1 h, 6 h after each failure. After the last one the delivery is parked in the dead-letter queue (/admin/connector/outbound-webhooks/dead-letter) for you to inspect and replay.

Answer 200 as soon as you have the body; do the work afterwards. A handler that does its processing before responding will eventually exceed the timeout and be sent the same event again.

Built-in events ​

These ship with Omaya and are available to every tenant.

Event typeFires when
device.anomalyA device stopped reporting, is draining its battery unusually fast, or is reporting far less than its baseline (critical or warning only).
device.battery_forecastA device's battery is forecast to reach the low threshold within two weeks, from its own drain rate over the last 14 days.
device.recoveredA device that had been flagged silent is reporting again; its silent anomaly was auto-closed.
emergency.activatedA panic button was pressed and matched at least one configured panic-button routing (Devices → Panic Buttons).
emergency.clearedAn alarm a device raised and ended itself is over: a cellular badge's SOS, Alert or man-down (MOKO PS101-M) ended on the badge, by an exit-alarm command, or a later report said no alarm is active.
geofence.enteredA tag with GPS (a tracker, or one an Omaya Scout phone places) went into a geofence (Space > Location > Map).
geofence.exitedA tag with GPS left a geofence.
rule.firedAny rule action dispatches (alert, email, webhook, telegram, whatsapp, sms, mqtt, write_record, home_assistant, or a module channel).
tenant.health_score.criticalA tenant's health score fell into the critical band (< 40).
tenant.health_score.driftA tenant's health score dropped by >= 10 points (or crossed a band boundary: good -> fair -> poor -> critical) compared to yesterday's snapshot.
venue.coverage.degradedFewer of a venue's gateways are online than positioning needs (default 3), so devices there fall back to nearest-gateway presence.
venue.coverage.restoredEnough of the venue's gateways are online again for positioning.
zone.occupancy.statusA zone's occupancy status changed: empty, normal, busy (from 50 % of capacity) or over (at capacity) — the same status the Right Now page and /api/v1/occupancy show, on the same count (radar or fixed sensor where the zone has one, otherwise BLE tags).

The device events ​

device.anomaly ​

Device Anomaly · added 2026-09-11

A device stopped reporting, is draining its battery unusually fast, or is reporting far less than its baseline (critical or warning only). Sent once per episode — a silent device fires when it goes quiet and not again until it has been seen and goes quiet again. Payload: anomaly_uid, anomaly_type, severity, device_uid, device_name, mac_address, last_seen_at, detected_at.

device.battery_forecast ​

Battery Replacement Due Soon · added 2026-09-11

A device's battery is forecast to reach the low threshold within two weeks, from its own drain rate over the last 14 days. Sent once per forecast episode. Payload: device_uid, device_name, mac_address, battery_pct, drain_pct_per_day, days_left, threshold_pct.

device.recovered ​

Device Reporting Again · added 2026-09-11

A device that had been flagged silent is reporting again; its silent anomaly was auto-closed. Payload: anomaly_uid, device_uid, device_name, mac_address, last_seen_at, flagged_at.

The emergency events ​

emergency.activated ​

Emergency Activated · added 2026-09-14

A panic button was pressed and matched at least one configured panic-button routing (Devices → Panic Buttons). Sent once per press however many routings matched, after the recipients were paged. Payload: button_uid, button_labels, buttons_matched, device_mac, press_type, gateway_mac (the gateway that heard the press), pressed_at, location (where the button is: kind indoor | outdoor | last_gps, text, place, latitude, longitude, map_url, position_at; null when unknown), recipients_paged, test (true for a test press from the Panic Buttons page), source (ingestion | rule | test).

emergency.cleared ​

Emergency Cleared · added 2026-10-10

An alarm a device raised and ended itself is over: a cellular badge's SOS, Alert or man-down (MOKO PS101-M) ended on the badge, by an exit-alarm command, or a later report said no alarm is active. Sent once per alarm, after the emergency.activated that started it. Payload: device_mac, device_uid, alarm (sos | alert | man_down), started_at, ended_at, ended_how (device | command | no_alarm), buttons_matched.

The geofence events ​

geofence.entered ​

Geofence Entered · added 2026-10-05

A tag with GPS (a tracker, or one an Omaya Scout phone places) went into a geofence (Space > Location > Map). Sent once per crossing, from the fix that crossed; coming back out of a building inside the same geofence is not a new crossing. Payload: geofence_uid, geofence_name, device_uid, device_mac, entity_uid, entity_type, latitude, longitude, at.

geofence.exited ​

Geofence Exited · added 2026-10-05

A tag with GPS left a geofence. Sent before geofence.entered when it moved straight into another one. Same payload as geofence.entered.

The rule events ​

rule.fired ​

Rule Fired · added in H38 (2026-07-23)

Any rule action dispatches (alert, email, webhook, telegram, whatsapp, sms, mqtt, write_record, home_assistant, or a module channel). Fires once per matched action — a single rule with 3 actions produces 3 events.

The tenant events ​

tenant.health_score.critical ​

Tenant Health Score Critical · added in H27 (B4.3) 2026-07-23

A tenant's health score fell into the critical band (< 40). Sent once per day per tenant while they remain critical, so the notification can drive a ticket/escalation workflow. Use this to kick off customer-success outreach, not to spam them on every snapshot.

tenant.health_score.drift ​

Tenant Health Score Drifted · added in H27 (B4.3) 2026-07-23

A tenant's health score dropped by >= 10 points (or crossed a band boundary: good -> fair -> poor -> critical) compared to yesterday's snapshot. Payload includes tenant_id, previous_score, current_score, previous_band, current_band, and the per-component breakdown. Use this to alert account managers before a customer notices.

The venue events ​

venue.coverage.degraded ​

Positioning Coverage Degraded · added 2026-09-11

Fewer of a venue's gateways are online than positioning needs (default 3), so devices there fall back to nearest-gateway presence. Only for venues with at least that many gateways registered. Sent on the transition, once. Payload: venue_uid, venue_name, online_gateways, active_gateways, min_anchors.

venue.coverage.restored ​

Positioning Coverage Restored · added 2026-09-11

Enough of the venue's gateways are online again for positioning. Same payload as venue.coverage.degraded.

The zone events ​

zone.occupancy.status ​

Zone Occupancy Status Changed · added 2026-09-12

A zone's occupancy status changed: empty, normal, busy (from 50 % of capacity) or over (at capacity) — the same status the Right Now page and /api/v1/occupancy show, on the same count (radar or fixed sensor where the zone has one, otherwise BLE tags). Sent once per transition after the new status has held for a minute, so a tag flickering at a zone edge does not fire every minute. Payload: zone_uid, zone_name, venue_uid, venue_name, status, previous_status, previous_since, count, tags, source, capacity, occupancy_pct, as_of.

Module events ​

These exist only when the module that owns them is enabled for your tenant. If a module is not installed, its events simply never appear in the catalog.

Roll Call — rollcall.* ​

Owned by the RollCall module.

Roll-call module events: rollcall.event_started (a roll call, drill or real muster, was started from the app, the mobile app or a rule) and rollcall.event_ended (it was ended and its counts frozen). Payloads carry event_uid, name, type, is_drill, priority, the gathering point and timestamps.

Event typeFires when
rollcall.event_startedA roll call (drill or real muster) was started. Payload: event_uid, name, type, is_drill, priority, gathering_point, gathering_zone_uid/venue_uid, expected (people on the roster), started_at.
rollcall.event_endedA roll call was ended. Payload adds: present, excused, off_site (outside on GPS, accounted for), unaccounted (missing + late + badge not heard + never classified), accountability_pct ((present + excused + off_site) / expected), duration_seconds, ended_at.

Visitor Management — visitor.* ​

Owned by the Visitor module.

Visitor Management events: a visit registered, approved or denied by its host companies, checked in, checked out, or cancelled. Payloads carry the visit uid, status, the visitor's name, and each company's approval.

Event typeFires when
visitor.registeredA visit was registered — at reception, by pre-registration, or by the visitor. Payload: visit uid, visitor, companies asked for and their initial approval.
visitor.approvedEvery host company approved the visit.
visitor.deniedA host company denied the visit; payload carries the reason.
visitor.checked_inThe visitor was checked in; payload carries the badge MAC when one was assigned.
visitor.checked_outThe visitor was checked out; payload carries the method (reception, auto_presence, expired, gate, self).
visitor.cancelledAn open visit was cancelled by reception, the visitor, a company withdrawing its approval while the visitor was on site, or the meeting the guest was invited to being cancelled.
visitor.badge_changedThe badge on an open stay was swapped and the access card with it; payload carries the old and new card numbers.

Warehouse — warehouse.* ​

Owned by the Warehouse module.

Warehouse app events for the ERP: goods received, shipped, adjusted, counted, issued to and reported from production, returned, rejected by QC, and storage breaches. Payloads carry the ERP codes (SKU, order type and number, partner code), never Omaya ids. GET /api/v1/warehouse/movements carries every ledger line in order.

Event typeFires when
warehouse.receiptGoods received against a PO (receiving closed): lines with SKU, batch, quantity, serials.
warehouse.return_receivedA customer return was received; it is held for QC.
warehouse.qc_rejectedInspection failed units on a receipt or pick list; they are quarantined. Payload adds units_failed.
warehouse.shipmentA pick list was shipped: lines with SKU, batch, quantity, plus vehicle and carrier.
warehouse.adjustmentStock adjusted in or out by hand (stock in, stock out, scrap), with the reason and who did it.
warehouse.count_approvedA stock count was approved; payload carries each variance line posted and its quantity change.
warehouse.materials_issuedMaterials issued to a work order.
warehouse.materials_returnedUnused material returned from a work order to stock; payload lines carry the quantity back and the new unit label.
warehouse.supplier_returnGoods returned to a supplier left at the gate (return to supplier): the RTV number, the supplier's RMA / debit note, and lines with SKU, batch, serial, quantity and the PO they came in on.
warehouse.production_reportedFinished goods reported on a work order, with the new unit labels.
warehouse.condition_breachA storage area left its temperature or humidity range; payload lists the units inside.
warehouse.movementEvery ledger line, when the ERP connector asks for it (the movement feed is the better way to read these).

Last updated:

Omaya platform documentation