BotanaryBotanary
Integration

Notifications

The alerts feed - every action, every block, every depeg drift - and the shape of a Notification.

Notifications are Botanary's general alerts feed - its own tag description puts it plainly: "every action, every block, every depeg drift."

Endpoints

  • GET /notifications lists them, with an optional unreadOnly boolean query param (default false). It returns a plain array of Notification.
  • POST /notifications/{notificationId}/read marks one as read, returning the updated notification (404 if the id doesn't exist).
  • POST /notifications/read-all marks every notification read at once, returning 204.

On the backend, all three are thin: the controller resolves the caller's signer address and delegates straight to the notifications service - list, mark-all-read, or mark-one-read.

The Notification shape

Required fields: id, tone, title, body, createdAt, read. Optional fields: timeLabel (nullable), relatedType (nullable - links a notification back to a delegation, an activity event, or a depeg event), relatedId (nullable), and action (nullable) - a NotificationAction of { label, target }, where target is a frontend deep-link key.

A real example from the contract: a notification titled "Action blocked," body "Uniswap tried to spend 120 USDC - over the 50 USDC per-action cap." - the kind of alert that surfaces a rules decline (see Rules & AgentGuard) directly in the feed rather than leaving you to go find it in the activity log.

Reading the feed on the frontend

The topbar notification popover marks a notification read then, if it carries an action.target, navigates there - so an alert can double as a deep link into whatever it's actually about:

const markAll = $api.useMutation('post', '/notifications/read-all');
const markOne = $api.useMutation('post', '/notifications/{notificationId}/read');
const invalidate = () => queryClient.invalidateQueries({ queryKey: ['get', '/notifications'] });
const onMarkAll = () => markAll.mutate({}, { onSuccess: invalidate });

Both mutations invalidate the notifications query on success, so the popover's own list stays in sync with whatever you just marked read.

TODO: whether notifications are poll-only or delivered through a push channel isn't confirmed in v1 - verify before documenting. What's confirmed today is the pattern above: mutate, then invalidate the list query, is how the frontend keeps the feed current.

On this page