Real-time webhooks
Subscribe to REALM Experiences Radar and receive a signed HTTP POST every time a matching experience is published. Faster than polling the RSS feed, ideal for partner sites and CRMs.
How it works
- Email partners@realmgroup.global with your endpoint URL and filter.
- We create a subscription, generate a unique signing secret, and share it back.
- Every ~5 minutes we deliver new matching experiences via POST.
- You verify the
X-Realm-Signatureheader and ingest the payload.
Filter examples
JSON filters applied per subscription:
// Australia conservation experiences only
{ "country": "AU", "category": "Conservation/Regen" }
// Any working holiday, any country
{ "category": "Working Holiday" }
// Multiple countries (array = OR)
{ "country": ["AU", "NZ", "CA"] }Payload format
POST https://your-endpoint.example.com/webhooks/realm
Content-Type: application/json
X-Realm-Signature: sha256=<hex>
X-Realm-Event: experience.published
User-Agent: REALM-Radar-Webhook/1.0
{
"event": "experience.published",
"delivered_at": "2026-05-16T03:45:00.000Z",
"item": {
"id": "5990ac32-…",
"title": "6-Week Regenerative Agriculture Immersion — Gippsland",
"summary": "…",
"link": "https://realm-experiences-radar.vercel.app/experiences/…",
"source_name": "Gippsland Farm Stay",
"source_url": "https://provider.example.com/…",
"category": "Conservation/Regen",
"state_or_region": "Victoria",
"country": "AU",
"published_at": "2026-05-16T03:00:00Z"
}
}Verifying the signature
Compute sha256=HMAC-SHA256(secret, raw_body) as hex and compare to the X-Realm-Signature header using constant-time comparison.
// Node.js example
import { createHmac, timingSafeEqual } from 'crypto';
const expected = 'sha256=' + createHmac('sha256', SECRET)
.update(rawBody)
.digest('hex');
if (!timingSafeEqual(Buffer.from(expected), Buffer.from(req.headers['x-realm-signature']))) {
return res.status(401).send('bad signature');
}Reliability
- Deliveries are deduped per (subscription, experience) — safe to retry.
- We retry up to 10 consecutive failures before pausing the subscription.
- 10-second timeout. Return any 2xx to acknowledge.
- If you miss deliveries, fall back to polling /feeds/all.json.
Also see
- RSS & JSON feeds — pull-based syndication
- Full feed directory — browse every slice