GuidesNotifications
Frontend Inbox with Hooks
Build a production inbox with pagination, scoped filters, mutation actions, and resilient refresh behavior.
Frontend Inbox with Hooks
useNotifications gives you the core read model and mutation actions for inbox UX.
What the hook provides
- Cursor pagination via
loadMore(). - Filtered list by scope/channels/severity/state.
- Item actions: read/unread, archive, star.
- Bulk actions:
markAllAsRead(),archiveAllRead(). - Stream-assisted freshness via internal
useNotificationStreamwiring.
Inbox composition example
import { useNotifications } from "@wacht/react-router";
export function NotificationsInbox() {
const {
notifications,
loading,
hasMore,
loadMore,
markAsRead,
markAsUnread,
archiveNotification,
starNotification,
markAllAsRead,
archiveAllRead,
refetch,
} = useNotifications({
scope: "all",
is_archived: false,
limit: 25,
severity: "warning",
});
if (loading) return <div>Loading notifications...</div>;
return (
<section>
<div>
<button onClick={() => markAllAsRead()}>Mark all read</button>
<button onClick={() => archiveAllRead()}>Archive all read</button>
<button onClick={() => refetch()}>Refresh</button>
</div>
{notifications.map((n) => (
<article key={n.id}>
<h4>{n.title}</h4>
<p>{n.body}</p>
<button onClick={() => markAsRead(n.id)}>Read</button>
<button onClick={() => markAsUnread(n.id)}>Unread</button>
<button onClick={() => archiveNotification(n.id)}>Archive</button>
<button onClick={() => starNotification(n.id)}>Star</button>
</article>
))}
<button disabled={!hasMore} onClick={() => loadMore()}>
Load more
</button>
</section>
);
}UX guidance
- Mark-as-read on explicit row open, not hover.
- Keep active filters in URL state for shareable support context.
- Render clear empty states for “no data” vs “error”.
- Show mutation progress on action buttons for repeated actions.
State consistency guidance
- Let hook-managed optimistic updates handle immediate UX.
- Call
refetch()after bulk operations when consistency matters. - Treat backend as source of truth after reconnect or tab refocus.
Validation checklist
- Filtered views remain consistent after mutations.
- Bulk actions affect intended filtered set.
- Cursor pagination preserves ordering and no duplicates.
- Error states are actionable and recoverable.