2.4 KiB
2.4 KiB
Notifications Hardening Guide
Last updated: 2025-11-25 (Docs Tasks Md.V · DOCS-NOTIFY-40-001)
Threat model
- Tenant data isolation breaches (cross-tenant deliveries).
- Channel compromise (webhook leaks, OAuth token theft).
- Message tampering or replay.
- Flooding / notification storms.
Controls
- Tenant isolation: every rule/channel/template includes
tenant; APIs enforceX-Stella-Tenant. PostgreSQL tables are filtered by tenant with indexes on(tenant_id, id)and row-level security. - Secrets: channels reference Authority
secretRef; secrets never stored in Notify DB. Rotate via Authority and:refresh-secret. - Outbound allowlist: restrict hosts/ports per tenant; defaults block public internet in air-gapped kits.
- Signing: webhook deliveries include
X-Stella-SignatureHMAC-SHA256 over body+nonce; receivers must reject stale timestamps (>5m) and verify signature. - Replay protection: delivery ledger de-dupes on
(channel, bodyHash)for 24h; escalation tokens are single-use DSSE-signed. - Rate limits/throttles: per-rule and per-channel throttles; quiet hours for non-critical traffic.
- Templates sandboxed: no file/network access; helpers are pure and deterministic.
- Logging/PII: payloads redacted based on rule labels; logs avoid full body, store hashes instead.
- Audit: all admin actions (create/update/delete channel or rule) logged with actor, trace id, and diff.
Deployment checklist
- Authority scopes
notify.viewer|operator|adminconfigured; service accounts least-privilege. - HTTPS everywhere; TLS 1.2+; HSTS on WebService front-door.
- Valkey protected by auth and network policy; PostgreSQL TLS + auth enabled.
- Outbound allowlists defined per environment; no wildcard
*. - Webhook receivers validate signatures and enforce host/IP allowlists.
Incident playbook (channel compromise)
- Disable affected channel via
PATCH /channels/{id}(enabled=false). - Rotate secret in Authority; refresh channel secret.
- Search ledger for deliveries to compromised endpoint and notify tenants if required.
- Re-enable with new endpoint/secret after validation.
Offline/air-gap notes
- Ship channel manifests and secrets via sealed bundles; keep hash manifest with signed checksum.
- Disable any channel type not supported in the enclave (e.g., external Slack) and use in-app or file-drop channels instead.