AI workspace
BlockProA whole AI application surface: conversations down one side, the active transcript with reasoning, tool calls and sources in the middle, and the context — window usage, attachments and a structured result — on the other.
Contract review — Acme MSA
A still, rendered at build time from the same story the tests run. The block itself is interactive; the copy that runs is the one the CLI installs.
Installation
The block is written to your blocks directory, and everything it is built from is installed alongside it. This one needs a licence: sign in once with the CLI and the install is the same command.
pnpm dlx @dowel-ui/cli add ai-workspaceBuilt from
A block is not a black box. Every piece is a component you already have documentation for, and can change independently.
- ai-conversation
- ai-message
- ai-model-selector
- ai-prompt-input
- ai-reasoning
- ai-response
- ai-sources
- ai-structured-output
- ai-token-usage
- ai-tool
- button
- empty-state
- sidebar
Props
AiWorkspaceBlock
| Prop | Type | Default |
|---|---|---|
messages (required)The transcript of the active thread. | WorkspaceMessage[] | — |
threads (required) | WorkspaceThread[] | — |
activeThread | string | — |
attachments | WorkspaceAttachment[] | [] |
busyA response is in flight. | boolean | false |
headerActionsAnything else for the top bar — a share button, a settings link. | ReactNode | — |
model | string | — |
models | ModelOption[] | — |
nameThe application's name, at the top of the conversation list. | string | "Workspace" |
onAttach | () => void | — |
onModelChange | (model: string) => void | — |
onNewThread | () => void | — |
onRemoveAttachment | (attachment: WorkspaceAttachment) => void | — |
onSelectThread | (id: string) => void | — |
onSend | (message: string) => void | — |
onStop | () => void | — |
outputA structured result the conversation is filling in, shown beside it. | WorkspaceOutput | — |
placeholder | string | "Ask anything…" |
tokenLimit | number | — |
tokensUsedContext consumed so far, and the window. Both or neither. | number | — |
waitingShown before the first token arrives. | boolean | false |
className | string | — |
Accessibility
Three landmarks, each named: the conversation list is a navigation called Conversations, the transcript is the main content, and the context is a complementary region called Context, so a screen reader user can jump between them and skip the one they do not want. The transcript is a list and never a live region; the response state is announced from a separate status line, so a streaming answer does not read itself aloud token by token. Each attachment's remove button is named after its file. On a narrow screen the conversation list becomes a sheet with a focus trap and an Escape key, not a div slid over content that stays reachable by Tab.
Source
One file, written by dowel add ai-workspace with imports rewritten to your own path alias, and yours to edit from then on.
This is a Pro block.
The preview is the real block, rendered from its own story — a still of it, not a copy of it. The source is installed by the CLI once this machine is signed in with a licence key — dowel login checks the key against the registry before storing it — and lands in your project as a file you own, exactly like a free block.
Registry name: ai-workspace