This is the policy layer — the whether and what to notify. It sits above Push Delivery Store (delivery guarantee) and before Real-Time Push Notifications (transport).
Quick Start
1
Gate a notification with the default policy
Apply
DEFAULT_PREFERENCE to decide whether an agent’s event should notify you.2
Per-recipient preference with quiet hours
Subscribe to specific categories and stay silent overnight unless the event is urgent.
3
Detail-level redaction
Pick how much content leaves the gateway with
DetailLevel.How It Works
Every notifier calls one pure function before delivery; the decision carries the send flag and the already-redacted content.evaluate() is pure and side-effect-free, so any process can call it at delivery-decision time without I/O. Pass prefs=None to fall back to DEFAULT_PREFERENCE; pass now=None to use the current time localised to prefs.timezone.
The Three Concerns
Categories
A recipient opts into each event class independently; an un-opted category is suppressed with reasoncategory_not_subscribed.
Quiet Hours
A per-recipient local window suppresses non-urgent categories; urgent events override whenurgent_overrides_quiet=True.
The window is half-open [start, end). When start == end the window is empty (never quiet). When start > end it wraps past midnight — (22:00, 07:30) means 22:00–24:00 ∪ 00:00–07:30. A naive now is treated as already local; an aware now is converted to prefs.timezone via stdlib zoneinfo. An unknown timezone name falls back silently to the naive time.
Detail Levels
Three levels control how much content leaves the gateway.Which Detail Level Should I Pick?
Match the level to how trusted the destination surface is.Configuration Options
NotificationPreference
Also exposes
.allows(category) → bool, whether this recipient opted into category.
NotificationDecision
evaluate(...)
DEFAULT_PREFERENCE
Applied when a recipient has set nothing: the two interaction-blocking categories are on, at the identified (no-content) detail level, with no quiet hours.
Common Patterns
Gate a scheduler completion notification — the recipient opts intoAGENT_FINISHED, and it is not urgent.
DetailLevel.PRIVATE so the lock-screen never shows content.
Best Practices
Pick a sensible default per product surface
Pick a sensible default per product surface
Match the default
detail to where notifications land. Use PRIVATE for mobile lock-screens where anyone nearby can read the preview, IDENTIFIED for shared team channels that route by agent, and DETAILED only for trusted single-user desktops. DEFAULT_PREFERENCE uses IDENTIFIED as a safe middle ground.Reserve urgency for interaction-blocking events
Reserve urgency for interaction-blocking events
Treat
APPROVAL_REQUESTED and AGENT_QUESTION as urgent by convention — they block an agent from continuing until you answer. Pass is_urgent=True for these so quiet hours never strand a paused agent. Keep failure alerts (SCHEDULED_TASK_FAILED, BACKGROUND_TASK_FAILED) non-urgent unless your operations demand overnight paging.Get quiet-hours edge cases right
Get quiet-hours edge cases right
The window is half-open
[start, end). A same-day window needs start < end (e.g. (09:00, 17:00)); an overnight window needs start > end (e.g. (22:00, 07:30)), which wraps across midnight. Setting start == end produces an empty window — never quiet. Always set timezone to the recipient’s IANA zone so now localises correctly; a naive now is assumed already local and an unknown zone falls back to the naive time.Balance lock-screen privacy against actionability
Balance lock-screen privacy against actionability
Lower detail protects content but forces the recipient to open the app to act. If a notification only exists to prompt an approval,
IDENTIFIED is usually enough — the recipient knows which agent to open. Reserve DETAILED for events where the content itself is the action (e.g. a failure stack trace) and the destination is trusted.User Interaction Flow
An operator sets a preference once; later events are gated automatically by the policy.Related
Real-Time Push Notifications
The PushClient / WebSocket transport this policy sits above
Push Delivery Store
The durable at-least-once delivery this policy composes with

