Approval inbox
Every pending approval across runs in one list. Approve or deny in a batch, filter by run or tool, and expand any row to read the reason and the exact tool input.
On this page
Five requests from three runs. Filter, select, approve or deny in a batch, or expand a row to read the input.
Installation
Usage
import { ApprovalInbox } from "@/components/ui/chatcn/approval-inbox"
<ApprovalInbox
approvals={pending}
onApprove={(ids, scope) => approve(ids, scope)}
onDeny={(ids, reason) => deny(ids, reason)}
/>Each approval names its run and tool, so the filters build themselves. Handled rows fold away and then report, so remove them from approvals in your handler.
Examples
Empty
Nothing waiting.
Props
| Prop | Type | Notes |
|---|---|---|
approvals | PendingApproval[] | { id, runId, runTitle, tool, title, detail?, reason?, input?, requestedAt?, icon? } |
onApprove | (ids, scope) => void | scope is once or always |
onDeny | (ids, reason?) => void | reason is the note typed in the expanded row |
title | ReactNode | Default Approvals |
showShortcuts | boolean | Keyboard hint row. Default true, hidden on touch |
Keyboard
| Key | Action |
|---|---|
A | Allow the focused row |
D | Deny the focused row |
X, Space on the checkbox | Select the focused row |
Enter on a row | Expand the reason and the tool input |
Accessibility
- Checkboxes report
aria-checked, and Select all reportsmixedwhen some rows are selected. - Row details come from Base UI Collapsible, so the row button has
aria-expanded. - After a row is handled, focus moves to the next row instead of falling to the page.
Motion
- Handled rows fold over 160 ms. Rows handled with the keyboard leave at once.
- The batch actions swap in for the filters with a 150 ms fade and scale from 0.97.
- Details open with a 200 ms height and opacity transition.