Documentation → Webhooks

Webhooks

RoverDrop POSTs a JSON payload to your endpoint every time a packet changes hands. The payload is deliberately flat, so no-code tools — Zapier, Make, Power Automate — can map any field directly, and signed, so your systems can trust it.

Setting up

In Settings → Integrations, set a webhook URL and a signing secret (both required). Every event below then POSTs to that URL with these headers:

Content-Type: application/json
X-RoverDrop-Event: packet.accepted
X-RoverDrop-Signature: <hex HMAC-SHA256 of the raw body>

Delivery is at-least-once with one automatic retry; treat the combination of event + packet_id + timestamp as your idempotency hint. Respond with any 2xx status within 5 seconds.

Events

  • packet.submitted A crew member submitted a packet (all files verified).
  • packet.accepted Someone in the office accepted the packet and took responsibility.
  • packet.unaccepted An accept was undone; the packet is back in the queue.
  • packet.filed The packet was confirmed placed in its final destination.
  • packet.unfiled A filed packet was reopened as accepted.
  • packet.reassigned Responsibility moved to another office/admin user.
  • packet.returned The packet was returned to the submitter for correction.
  • packet.return_undone A return was undone; the packet is back in the queue.

Payload

Every event carries the same shape — the event name plus the packet's current state. Timestamps are ISO 8601 UTC; fields that don't apply yet are null.

{
  "event": "packet.accepted",
  "timestamp": "2026-07-17T19:04:11.302Z",
  "packet_id": "0b6f2b6e-3d0e-4c1a-9a44-1f2ab33c9d10",
  "packet_number": 1042,
  "packet_url": "https://app.roverdrop.com/packets/0b6f2b6e-…",
  "title": "Miller Rd — site photos, day 2",
  "status": "accepted",
  "job_number": "24-118",
  "submitter_name": "Sam Alvarez",
  "external_name": null,
  "responsible_name": "Dana Whitfield",
  "submitted_at": "2026-07-17T16:55:03.114Z",
  "accepted_at": "2026-07-17T19:04:11.032Z",
  "filed_at": null,
  "returned_at": null,
  "return_reason": null,
  "legal_hold": false,
  "supplement_to_id": null,
  "gps_lat": 41.8781,
  "gps_lng": -87.6298,
  "file_count": 14,
  "total_bytes": 268435456
}

gps_lat/gps_lng are present only when the submitter attached their device location. legal_hold is true whenever the packet is covered by a hold — its own, or one on its job (holds are managed per job in Settings). external_nameis set when the packet arrived through a file-request link: it is the outside sender's typed name, and submitter_name is then the link's creator — prefer external_name when announcing who sent the files.

Verifying signatures

The X-RoverDrop-Signature header is the hex HMAC-SHA256 of the raw request body using your signing secret. Verify before trusting:

import { createHmac, timingSafeEqual } from "crypto";

function verify(rawBody: string, signatureHeader: string, secret: string) {
  const expected = createHmac("sha256", secret).update(rawBody).digest("hex");
  const a = Buffer.from(expected);
  const b = Buffer.from(signatureHeader);
  return a.length === b.length && timingSafeEqual(a, b);
}

Using Zapier

  1. In Zapier, create a Zap with the trigger Webhooks by Zapier → Catch Hook. Copy the hook URL Zapier gives you.
  2. Paste that URL into Settings → Integrations → Webhook URL in RoverDrop, set a signing secret, and save.
  3. Move a test packet (accept one, or submit one) so a real event fires, then click Find new records in Zapier — the flat fields (title, packet_number, status…) appear ready to map.
  4. Add a Filter step on event if you only want certain transitions (e.g. only packet.filed rows into a spreadsheet, only packet.returned into a Slack alert).
  5. Map fields into your action — a Google Sheets row per filed packet, a Slack message per return, a QuickBooks/job-costing update per acceptance. One webhook feeds any number of Zaps.

The same catch-hook pattern works in Make (Custom webhook) and Power Automate (When an HTTP request is received).

Need to pull data instead?

Webhooks push events as they happen. For pulling state on your schedule, use the read-only API — Bearer-token access to packets, files, checksums, and the full audit trail.