Getting Started
Components
- Agent Status
- Agent Template Card
- API Key Card
- Audio Player
- Bar Visualizer
- Channel Status Card
- Chat Composer
- Code Editor
- Condition Builder
- Confirm Dialog
- Conversation
- Conversation Bar
- Dataset Card
- Document Status Badge
- Extraction Strategy Select
- File Icon
- File Upload
- Indexing Progress
- Live Waveform
- Matrix
- Message
- Mic Selector
- Model Diff View
- Model Selector
- Model Type Filter
- Node Catalog
- Option Editor
- Orb
- Output Variables View
- Package Card
- Prompt Editor
- Provider Status Card
- Radio Card
- Resource Card
- Resource Sidebar
- Response
- Run Node List
- Scrub Bar
- Segment Card
- Shimmering Text
- Speech Input
- Token Trend Chart
- Tool Call Card
- Transcript Viewer
- Usage Stat Card
- Variable Binding Editor
- Variable Selector
- Voice Button
- Voice Picker
- Waveform
- Workflow Node Card
- Workspace Selector
Run nodes
4Start
Trigger12 msReceived user message and workspace context.
Classify intent
LLM824 msDetected billing_question with 0.86 confidence.
Retrieve knowledge
RAGrunningSearching product docs and billing policy chunks.
Draft answer
LLMimport { RunNodeList } from "@/components/ui/run-node-list"
const nodes = [
{
id: "start",
title: "Start",
type: "Trigger",
status: "success" as const,
duration: "12 ms",
summary: "Received user message and workspace context.",
},
{
id: "classify",
title: "Classify intent",
type: "LLM",
status: "success" as const,
duration: "824 ms",
summary: "Detected billing_question with 0.86 confidence.",
},
{
id: "retrieve",
title: "Retrieve knowledge",
type: "RAG",
status: "running" as const,
duration: "running",
summary: "Searching product docs and billing policy chunks.",
},
{
id: "answer",
title: "Draft answer",
type: "LLM",
status: "pending" as const,
},
]
export function RunNodeListDemo() {
return (
<RunNodeList
nodes={nodes}
activeId="retrieve"
className="w-full max-w-xl"
/>
)
}
Installation
pnpm dlx shadcn@latest add https://ui.zgi.ai/r/run-node-list.jsonpnpm dlx shadcn@latest add https://ui.zgi.ai/r/run-node-list.json
yarn dlx shadcn@latest add https://ui.zgi.ai/r/run-node-list.jsonComponent
"use client"
import * as React from "react"
import {
AlertCircleIcon,
CheckCircle2Icon,
Clock3Icon,
Loader2Icon,
} from "lucide-react"
import { cn } from "@/lib/utils"
import { Badge } from "@/components/ui/badge"
export type RunNodeStatus = "pending" | "running" | "success" | "error"
export interface RunNodeItem {
id: string
title: React.ReactNode
type?: React.ReactNode
status: RunNodeStatus
duration?: React.ReactNode
summary?: React.ReactNode
}
export interface RunNodeListProps
extends Omit<React.ComponentProps<"div">, "title"> {
nodes: RunNodeItem[]
title?: React.ReactNode
activeId?: string
}
const statusConfig: Record<
RunNodeStatus,
{
label: string
icon: React.ComponentType<{ className?: string }>
className: string
}
> = {
pending: {
label: "Pending",
icon: Clock3Icon,
className: "border-border bg-muted text-muted-foreground",
},
running: {
label: "Running",
icon: Loader2Icon,
className:
"border-blue-500/20 bg-blue-500/10 text-blue-700 dark:text-blue-300",
},
success: {
label: "Success",
icon: CheckCircle2Icon,
className:
"border-emerald-500/20 bg-emerald-500/10 text-emerald-700 dark:text-emerald-300",
},
error: {
label: "Error",
icon: AlertCircleIcon,
className: "border-destructive/20 bg-destructive/10 text-destructive",
},
}
export function RunNodeList({
nodes,
title = "Run nodes",
activeId,
className,
...props
}: RunNodeListProps) {
return (
<div
className={cn(
"border-border bg-card text-card-foreground overflow-hidden rounded-lg border shadow-sm",
className
)}
{...props}
>
<div className="border-border flex min-h-11 items-center justify-between border-b px-3">
<p className="text-sm font-medium">{title}</p>
<Badge variant="secondary" className="rounded-md">
{nodes.length}
</Badge>
</div>
<div className="divide-border divide-y">
{nodes.map((node, index) => {
const config = statusConfig[node.status]
const Icon = config.icon
return (
<div
key={node.id}
className={cn(
"flex gap-3 p-3",
activeId === node.id && "bg-accent/40"
)}
>
<div className="flex flex-col items-center">
<span
className={cn(
"flex size-7 items-center justify-center rounded-full border",
config.className
)}
>
<Icon
className={cn(
"size-3.5",
node.status === "running" && "animate-spin"
)}
/>
</span>
{index < nodes.length - 1 ? (
<span className="bg-border mt-2 h-full w-px" />
) : null}
</div>
<div className="min-w-0 flex-1 pb-1">
<div className="flex min-w-0 items-center gap-2">
<p className="truncate text-sm font-medium">{node.title}</p>
{node.type ? (
<Badge variant="outline" className="h-6 rounded-md px-2">
{node.type}
</Badge>
) : null}
{node.duration ? (
<span className="text-muted-foreground ml-auto shrink-0 text-xs">
{node.duration}
</span>
) : null}
</div>
{node.summary ? (
<p className="text-muted-foreground mt-1 line-clamp-2 text-xs leading-5">
{node.summary}
</p>
) : null}
</div>
</div>
)
})}
</div>
</div>
)
}
Usage
import { RunNodeList } from "@/components/ui/run-node-list"
export function Example() {
return (
<RunNodeList
nodes={[{ id: "start", title: "Start", status: "success" }]}
/>
)
}Deploy and Scale Agents with ZGI
ZGI delivers the infrastructure and developer experience you need to ship reliable audio & agent applications at scale.
Talk to an expert