You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Turn the bell into an action queue: route governance + remediation events to
the users who can act on them, not the whole fleet.
New primitives:
- auth.RolesWithPermission(p) — resolve a permission to the built-in roles that
grant it (pure helper over BuiltInRoles).
- notifyfeed.Store.RecordForRoles — fan one row per active user holding any of
the given roles (EXISTS, so a multi-role user gets one row), same
upsert/collapse as RecordFanout.
Producer: notifyfeed.GovernanceProjector
- ExceptionRequested -> users who can approve (roles granting exception:approve:
auditor, security_admin, admin), kind exception_pending, high, deep-link
/settings/policies, grouped per exception.
- ExceptionDecided -> the requester only, exception_approved/_rejected, medium.
- RemediationFailed -> users who can act (roles granting remediation:execute:
ops_lead, security_admin, admin), kind remediation_failed, high, deep-link
/hosts/{id}, grouped per host+rule. Fires on a TERMINAL failure (execute that
failed, or a rollback that did not restore) — NOT a successful user-initiated
rollback (that is intended, not an alarm).
Producer hooks (best-effort, never fail the transition/job; nil-safe):
- exception.Service.WithNotifier + calls in Request/Approve/Reject.
- worker.RemediationWorker GovernanceNotifier + calls on the two failure sites.
- wired in cmd/openwatch/main.go (serve) and worker.go (dedicated worker).
Both producers hold interfaces in their own packages, so neither imports
notifyfeed. Spec system-notifications v1.5.0: C-08 + AC-15/16/17. Tests:
auth.RolesWithPermission unit test; DB-backed governance fan-out tests
(approver-scoped, requester-only, operator-scoped). No frontend change — rows
render in the existing bell drawer.
0 commit comments