{ "name": "budget-guard", "type": "registry:ui", "title": "Budget Guard", "description": "Spend and token caps against what a run has consumed. A soft limit warns and a hard limit stops — collapsing them into one bar is how a team ends up believing they have a spend cap when what they have is a notification.", "category": "Agents", "dependencies": [ "lucide-react@^1.39.0" ], "registryDependencies": [ "badge", "lib-motion", "lib-styles", "lib-utils" ], "files": [ { "path": "components/ui/budget-guard.tsx", "type": "registry:ui", "content": "import type { ComponentProps, ReactNode } from 'react'\nimport { Ban, TriangleAlert } from 'lucide-react'\nimport { Badge } from '@/components/ui/badge'\nimport { enterFade, growIn } from '@/lib/motion'\nimport { radius, surface } from '@/lib/styles'\nimport { cn } from '@/lib/utils'\n\n/**\n * Spend and token caps, against what a run has actually consumed.\n *\n * The distinction the component is built around: a **soft** limit warns, a\n * **hard** limit stops. Collapsing them into one bar is how a team ends up\n * believing they have a spend cap when what they have is a notification.\n *\n * So a hard limit is drawn as a wall on the track — a solid marker with a stop\n * glyph — and a soft one as a dashed threshold. Once a hard limit is passed the\n * whole row is destructive and says `stopped`, because at that point the run is\n * not running and every other reading on the screen is historical.\n *\n * Bars are scaled to the hard limit when there is one, so \"how much room is\n * left before it stops\" is the length being read. Scaling to the soft limit\n * makes a run look finished when it has half its budget left.\n */\nexport type Budget = {\n id: string\n label: ReactNode\n /** Consumed so far, in whatever unit `format` renders. */\n used: number\n /** Warns when passed. */\n soft?: number\n /** Stops the run when passed. */\n hard?: number\n format?: (value: number) => string\n note?: ReactNode\n}\n\ntype BudgetGuardProps = Omit, 'children'> & {\n budgets: Budget[]\n stoppedLabel?: string\n warningLabel?: string\n hardLabel?: string\n softLabel?: string\n emptyLabel?: string\n label?: string\n}\n\nfunction BudgetGuard({\n budgets,\n stoppedLabel = 'stopped',\n warningLabel = 'over the warning threshold',\n hardLabel = 'hard limit',\n softLabel = 'warn at',\n emptyLabel = 'No budgets configured — this run is uncapped.',\n label = 'Budgets',\n className,\n ...props\n}: BudgetGuardProps) {\n return (\n \n

\n {label}\n

\n\n {budgets.length === 0 ? (\n

\n \n {emptyLabel}\n

\n ) : (\n \n )}\n \n )\n}\n\nexport { BudgetGuard }\nexport type { BudgetGuardProps }\n" } ] }