{"$schema":"https://json-schema.org/draft/2020-12/schema","$id":"watchdog-webhook-v1.schema.json","title":"FTSOBest Watchdog webhook payload v1","description":"Verify X-Watchdog-Signature as HMAC-SHA256 over <timestamp>.<raw body>. Reject timestamps outside a short local window before comparing signatures in constant time.\n\nNode: const expected='sha256='+createHmac('sha256',secret).update(ts+'.'+rawBody).digest('hex'); if(Math.abs(Date.now()/1000-Number(ts))>300 || expected.length!==received.length || !timingSafeEqual(Buffer.from(expected),Buffer.from(received))) throw new Error('invalid');\n\nPython: expected='sha256='+hmac.new(secret.encode(),f'{ts}.{raw_body}'.encode(),hashlib.sha256).hexdigest(); valid=abs(time.time()-int(ts))<=300 and hmac.compare_digest(expected,received)","type":"object","required":["deliveryId","alertId","watchId","label","type","event","severity","data","firedAt","rendered","renderedMessage"],"properties":{"deliveryId":{"type":"string","format":"uuid"},"alertId":{"type":["integer","null"]},"watchId":{"type":["integer","null"]},"label":{"type":["string","null"]},"type":{"enum":["wallet-balance","feed-move","provider-eligibility","credits-balance","reward-signing","provider-fsp",null]},"event":{"type":"string","enum":["credits.low-balance","credits.recovered","feed-move.threshold","fsp.balance-low","fsp.balance-low.recovered","fsp.fast-updates","fsp.fast-updates.recovered","fsp.fdc-bitvote","fsp.fdc-bitvote-length","fsp.fdc-bitvote-length.recovered","fsp.fdc-bitvote.recovered","fsp.fdc-consensus","fsp.fdc-consensus.recovered","fsp.fdc-reveal-offence","fsp.fdc-reveal-offence.recovered","fsp.fdc-signature","fsp.fdc-signature.recovered","fsp.fdc-submit1","fsp.fdc-submit1.recovered","fsp.ftso-commit","fsp.ftso-commit.recovered","fsp.ftso-reveal","fsp.ftso-reveal.recovered","fsp.ftso-signature","fsp.ftso-signature.recovered","fsp.mc-anchor","fsp.mc-anchor.recovered","fsp.mc-fdc","fsp.mc-fdc.recovered","fsp.mc-uptime","fsp.mc-uptime.recovered","fsp.monitoring","fsp.monitoring.recovered","fsp.not-in-policy","fsp.not-in-policy.recovered","fsp.registration","fsp.registration.recovered","fsp.reveal-offence","fsp.reveal-offence.recovered","fsp.rewards-unclaimed","fsp.rewards-unclaimed.recovered","fsp.signature-grace","fsp.signature-grace.recovered","fsp.signature-mismatch","fsp.signature-mismatch.recovered","fsp.tx-failed","fsp.tx-failed.recovered","fsp.validator-not-listed","fsp.validator-not-listed.recovered","provider.eligibility-lost","provider.recovered","provider.unregistered","signing.done","signing.missed","signing.rewards-open","signing.rewards-reminder","signing.uptime-open","wallet-balance.moved"]},"severity":{"enum":["info","warning","critical"]},"data":{"type":"object","description":"Event-specific evaluator data. Consumers must tolerate additional properties."},"firedAt":{"type":"string","format":"date-time"},"rendered":{"type":"object","required":["locale","title","body"],"properties":{"locale":{"enum":["en","de","fr","bn","zh","hi","ar"]},"title":{"type":"string"},"body":{"type":"string"}},"additionalProperties":false},"renderedMessage":{"type":"object","description":"Complete localized adapter-neutral message.","additionalProperties":true}},"additionalProperties":false,"examples":[{"deliveryId":"00000000-0000-4000-8000-000000000001","alertId":1,"watchId":1,"label":"Example watch","type":"wallet-balance","event":"wallet-balance.moved","severity":"warning","data":{},"firedAt":"2026-01-01T00:00:00.000Z","rendered":{"locale":"en","title":"Example alert","body":"Example body"},"renderedMessage":{"alertId":1,"watchId":1,"watchLabel":"Example watch","event":"wallet-balance.moved","severity":"warning","title":"Example alert","body":"Example body","fields":[],"link":"https://example.invalid/wallet-center/watchdog","firedAt":"2026-01-01T00:00:00.000Z","test":false}}]}