@neuronection/assistant-ui 0.53.1 → 0.55.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +21 -0
- package/README.md +1 -0
- package/dist/capability-chips.js +1 -1
- package/dist/chunk-6G7H6YP6.js +180 -0
- package/dist/chunk-6G7H6YP6.js.map +1 -0
- package/dist/chunk-7IP3JP3Z.js +54 -0
- package/dist/chunk-7IP3JP3Z.js.map +1 -0
- package/dist/chunk-FQXVZVA5.js +68 -0
- package/dist/chunk-FQXVZVA5.js.map +1 -0
- package/dist/chunk-FY3NCPFO.js +112 -0
- package/dist/chunk-FY3NCPFO.js.map +1 -0
- package/dist/{chunk-SY5FR4HC.js → chunk-H5KOC7Z5.js} +2 -2
- package/dist/{chunk-SY5FR4HC.js.map → chunk-H5KOC7Z5.js.map} +1 -1
- package/dist/chunk-KKZLR3YD.js +3 -0
- package/dist/chunk-KKZLR3YD.js.map +1 -0
- package/dist/chunk-RRT3DOPJ.js +3 -0
- package/dist/chunk-RRT3DOPJ.js.map +1 -0
- package/dist/chunk-SESPLTG7.js +3 -0
- package/dist/chunk-SESPLTG7.js.map +1 -0
- package/dist/chunk-YDQW2WJH.js +70 -0
- package/dist/chunk-YDQW2WJH.js.map +1 -0
- package/dist/{chunk-I5H4KYEZ.js → chunk-YHMVPFEN.js} +3 -3
- package/dist/{chunk-I5H4KYEZ.js.map → chunk-YHMVPFEN.js.map} +1 -1
- package/dist/chunk-YSBGF44F.js +104 -0
- package/dist/chunk-YSBGF44F.js.map +1 -0
- package/dist/index.d.ts +217 -1
- package/dist/index.js +14 -8
- package/dist/model-registry.js +1 -1
- package/dist/provider-logo.d.ts +16 -0
- package/dist/provider-logo.js +3 -0
- package/dist/provider-logo.js.map +1 -0
- package/dist/provider-setup-form.d.ts +74 -0
- package/dist/provider-setup-form.js +3 -0
- package/dist/provider-setup-form.js.map +1 -0
- package/dist/provider-setup-tiles.d.ts +52 -0
- package/dist/provider-setup-tiles.js +3 -0
- package/dist/provider-setup-tiles.js.map +1 -0
- package/dist/setup-first-run-card.d.ts +23 -0
- package/dist/setup-first-run-card.js +3 -0
- package/dist/setup-first-run-card.js.map +1 -0
- package/dist/setup-review.d.ts +51 -0
- package/dist/setup-review.js +3 -0
- package/dist/setup-review.js.map +1 -0
- package/dist/styles.css +1 -1
- package/dist/switch-row.d.ts +19 -0
- package/dist/switch-row.js +3 -0
- package/dist/switch-row.js.map +1 -0
- package/package.json +25 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,26 @@
|
|
|
1
1
|
# @neuronection/assistant-ui
|
|
2
2
|
|
|
3
|
+
## 0.55.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [`20e78c5`](https://github.com/neuronection/assistant-ui/commit/20e78c58c3b1397afa7f2ca88e8fd99bf4361caf) Thanks [@constLiakos](https://github.com/constLiakos)! - **ProviderSetupTiles: per-tile capability chips (plan 26 §13.3 follow-up).** Preset entries gain an additive optional `chips?: { key: string; label: string }[]` (`ProviderSetupTileChip`), rendered with the existing `CapabilityChips` badge pattern — neutral styling, i18n labels prop-injected per the family rule (the app derives chips from its preset data: wire type → chat/vision/stt, `decision_models` → decision, keyless-local → local). Frozen props untouched; chips carry text (part of the tile's accessible name) and never rank tiles. Story, docs page, a11y row and README updated in the same change — visual baselines need the CI rebaseline flow for the `ai-settings-setup-tiles-story`.
|
|
8
|
+
|
|
9
|
+
## 0.54.0
|
|
10
|
+
|
|
11
|
+
### Minor Changes
|
|
12
|
+
|
|
13
|
+
- [`93991a7`](https://github.com/neuronection/assistant-ui/commit/93991a73ce3dc376060a9575c30c0c7e503840fb) Thanks [@constLiakos](https://github.com/constLiakos)! - **AI settings: the plan-26 one-click setup kit (Phase 2 promotion)** — the six BYOK/decision setup primitives the family's three hand-built references (desktop `SetupWizard`, study `ProviderSetupModal`, health `byok/` port) converge on. All presentational + controlled (ADR-006): preset data, validation calls, secrets and i18n stay app-side.
|
|
14
|
+
|
|
15
|
+
- **`ProviderSetupTiles`** (`provider-setup-tiles`) — neutral equal-weight preset grid in the app's family order; no "recommended" ever; `local` captions, `disabled` tiles with reasons (health overlay), `configured` badges, `suggestedKey` paste-prefix highlight (sr-only note, never color alone); `ProviderSetupManualTile` companion for the manual/custom entry.
|
|
16
|
+
- **`ProviderSetupForm`** (`provider-setup-form`) — guided setup form: vendor checklist with `{url}` interpolation + copy buttons, get-a-key link (or button via `onOpenKeyUrl` for Electron `openExternal`), free-tier note, connection name, write-only API key (`type="password"` + `autoComplete="new-password"`), Advanced `<details>` disclosure with read-only base URL for `fixedBase` presets, `advancedExtra` slot (hosting/country — study/health), and classified error copy keyed off the shared §15 enum (`SETUP_ERROR_CODES` / `SetupErrorCode`) with **labels prop-injected** (`errorLabels`, `suspectedVendorHint` `{vendor}`).
|
|
17
|
+
- **`SetupReview`** (`setup-review`) — editable pre-flight review: model-select cards with capability icons (incl. `decision`) + gap-fill switch rows with `now:` sub-lines and the never-removes footnote. Every edit emits the full five-bind options body `{curatedIds, bindChat, bindVision, bindStt, bindDecision}` (plan 26 D14); decision-only presets show the decision slot only.
|
|
18
|
+
- **`SwitchRow`** (`switch-row`) — labeled `role="switch"` row with animated knob and `currentValue` sub-line; the standalone settings toggle desktop/study/health all hand-rolled.
|
|
19
|
+
- **`ProviderLogo`** (`provider-logo`) — simple-icons path data keyed by preset key, inline (no dependency), `currentColor`, monogram fallback; openai/groq marks are gone upstream so those keys intentionally fall back to the monogram.
|
|
20
|
+
- **`SetupFirstRunCard`** (`setup-first-run-card`) — empty-state CTA when no provider is configured: title/body, `localProbing` status, Set up / optional Dismiss, `children` slot for the app's detected-local banner; chat empty states deep-link to it.
|
|
21
|
+
|
|
22
|
+
Companions: `docs/guides/ai-settings.md` rewritten to the full family assembly (first-run card → wizard → defaults-first list → re-configure), per-component docs pages + accessibility rows + Ladle stories (`ai-settings-assembly`), and a composition test proving the five-bind body end-to-end next to the TaskAssignmentPicker Decision group. This release also carries the Phase 0 decision-descriptor verification work (`decision` descriptor + `decision:<cap>` slot coverage in stories/tests, landed unreleased on 4128640) — one release for the whole promotion set, per plan 26.
|
|
23
|
+
|
|
3
24
|
## 0.53.1
|
|
4
25
|
|
|
5
26
|
### Patch Changes
|
package/README.md
CHANGED
|
@@ -112,6 +112,7 @@ Visual reference: [gallery](https://neuronection.github.io/assistant-ui/).
|
|
|
112
112
|
| [`flow-status`](./docs/components/flow-status.md) | `FlowStatusCard` (multi-step AI-flow progress from the family event vocabulary: per-node status, current-step emphasis, progress summary, error + retryable, controlled retry/cancel/resume, `detail` slot for HITL cards) | [stories](https://neuronection.github.io/assistant-ui/?story=flow-status--running) |
|
|
113
113
|
| [`flow-trace`](./docs/components/flow-trace.md) | `FlowTraceCard` (run ledger over the library-owned `FlowTrace` schema: outcome badge, stage timeline, per-call LLM table with tokens/latency/prompt version, ops ✓/✗ list, simulated badge for mock rows) + `FlowTelemetryStrip` (compact `calls · tokens in/out · edits` live counters) | [stories](https://neuronection.github.io/assistant-ui/?story=flow-trace--completed-run) |
|
|
114
114
|
| [`settings-shell`](./docs/components/settings-shell.md) / [`provider-form`](./docs/components/provider-form.md) / [`connection-test-row`](./docs/components/connection-test-row.md) | `SettingsShell` (controlled two-pane nav) · `ProviderForm` (write-only API-key field) · `ConnectionTestRow` (idle/testing/ok/fail + latency, `inline` variant + meta slot) | [stories](https://neuronection.github.io/assistant-ui/?story=settings-trio--provider-form-story) |
|
|
115
|
+
| [`provider-setup-tiles`](./docs/components/provider-setup-tiles.md) / [`provider-setup-form`](./docs/components/provider-setup-form.md) / [`setup-review`](./docs/components/setup-review.md) / [`switch-row`](./docs/components/switch-row.md) / [`provider-logo`](./docs/components/provider-logo.md) / [`setup-first-run-card`](./docs/components/setup-first-run-card.md) | The plan-26 one-click setup kit (BYOK + decision models): neutral equal-weight preset tiles (family order, no "recommended", optional per-tile capability chips — chat/vision/decision/local, i18n labels prop-injected) · guided setup form (checklist + copy buttons, write-only `new-password` key, Advanced disclosure with fixed-base read-only, §15 error enum copy prop-injected) · editable pre-flight review emitting the five-bind options body `{curatedIds, bindChat, bindVision, bindStt, bindDecision}` (decision-only presets show the decision slot only) · labeled `role="switch"` row with `now:` sub-line · simple-icons provider mark with monogram fallback (openai/groq gone upstream), `currentColor` · first-run CTA card with local-probe status | [stories](https://neuronection.github.io/assistant-ui/?story=ai-settings-assembly--ai-settings-setup-tiles-story) |
|
|
115
116
|
| [`admin-user-table`](./docs/components/admin-user-table.md) | `AdminUserTable` — controlled admin user management table (email + "(you)" marker, activity count, role/status, promote/demote, activate/deactivate, inline password reset with min-length gate, force logout; guard-rail 403s as friendly messages) | [stories](https://neuronection.github.io/assistant-ui/?story=admin-user-table--default) |
|
|
116
117
|
| [`instance-mode-control`](./docs/components/instance-mode-control.md) | `InstanceModeControl` — controlled §4.5 instance access-mode panel (current mode, open→authenticated with owner credential set, authenticated→open with password + explicit ack, blocked states, audit note) | [stories](https://neuronection.github.io/assistant-ui/?story=instance-mode-control--open) |
|
|
117
118
|
| [`login-form`](./docs/components/login-form.md) / [`register-form`](./docs/components/register-form.md) | `LoginForm` — controlled sign-in form (labelled email + password with visibility toggle, loading/error props, register/forgot link slots; no remember-me — HttpOnly sessions are server-owned) · `RegisterForm` — controlled registration form (confirm-password mismatch gate, optional full-name field, min-length hint, login link slot) | [stories](https://neuronection.github.io/assistant-ui/?story=login-form--default) |
|
package/dist/capability-chips.js
CHANGED
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
import { CopyButton } from './chunk-XFYCNCPS.js';
|
|
2
|
+
import { Input } from './chunk-GQDW6BBO.js';
|
|
3
|
+
import { Button } from './chunk-4WBBF5LH.js';
|
|
4
|
+
import { cn } from './chunk-RVVXVTH3.js';
|
|
5
|
+
import * as React from 'react';
|
|
6
|
+
import { ExternalLink } from 'lucide-react';
|
|
7
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
8
|
+
|
|
9
|
+
var SETUP_ERROR_CODES = [
|
|
10
|
+
"invalid_key",
|
|
11
|
+
"insufficient_credit",
|
|
12
|
+
"new_user_quota",
|
|
13
|
+
"region_unavailable",
|
|
14
|
+
"timeout",
|
|
15
|
+
"local_not_running",
|
|
16
|
+
"unknown"
|
|
17
|
+
];
|
|
18
|
+
var DEFAULT_SETUP_ERROR_COPY = {
|
|
19
|
+
invalid_key: "The API key was rejected \u2014 check it and try again.",
|
|
20
|
+
insufficient_credit: "The account has no credit or quota left for this key.",
|
|
21
|
+
new_user_quota: "The provider hit a rate or quota limit \u2014 try again later.",
|
|
22
|
+
region_unavailable: "This provider or model is not available in your region.",
|
|
23
|
+
timeout: "The provider took too long to answer \u2014 try again.",
|
|
24
|
+
local_not_running: "Could not reach the local engine \u2014 make sure it is running.",
|
|
25
|
+
unknown: "The provider reported an unknown error."
|
|
26
|
+
};
|
|
27
|
+
var ProviderSetupForm = React.forwardRef(function ProviderSetupForm2({
|
|
28
|
+
preset,
|
|
29
|
+
value,
|
|
30
|
+
error,
|
|
31
|
+
testing = false,
|
|
32
|
+
onSubmit,
|
|
33
|
+
onCancel,
|
|
34
|
+
onChange,
|
|
35
|
+
errorLabels,
|
|
36
|
+
suspectedVendorHint = "This looks like a {vendor} API key.",
|
|
37
|
+
onCopyStep,
|
|
38
|
+
onOpenKeyUrl,
|
|
39
|
+
advancedExtra,
|
|
40
|
+
checklistLabel = "Setup steps",
|
|
41
|
+
copyLabel = "Copy",
|
|
42
|
+
getKeyLabel = "Get an API key",
|
|
43
|
+
nameLabel = "Connection name",
|
|
44
|
+
apiKeyLabel = "API key",
|
|
45
|
+
keyPlaceholder = "sk-\u2026",
|
|
46
|
+
noKeyLabel = "Runs on your machine \u2014 no API key needed.",
|
|
47
|
+
advancedLabel = "Advanced",
|
|
48
|
+
baseUrlLabel = "API base URL",
|
|
49
|
+
baseUrlHint,
|
|
50
|
+
submitLabel = "Connect",
|
|
51
|
+
cancelLabel = "Back",
|
|
52
|
+
className,
|
|
53
|
+
...props
|
|
54
|
+
}, ref) {
|
|
55
|
+
const stepText = (step) => step.replaceAll("{url}", preset.keyUrl ?? "");
|
|
56
|
+
const errorCopy = error ? errorLabels?.[error.code] ?? DEFAULT_SETUP_ERROR_COPY[error.code] ?? errorLabels?.unknown ?? DEFAULT_SETUP_ERROR_COPY.unknown : null;
|
|
57
|
+
return /* @__PURE__ */ jsxs(
|
|
58
|
+
"form",
|
|
59
|
+
{
|
|
60
|
+
ref,
|
|
61
|
+
"data-as": "provider-setup-form",
|
|
62
|
+
className: cn("flex w-full flex-col gap-3", className),
|
|
63
|
+
onSubmit: (event) => {
|
|
64
|
+
event.preventDefault();
|
|
65
|
+
if (!testing) onSubmit(value);
|
|
66
|
+
},
|
|
67
|
+
...props,
|
|
68
|
+
children: [
|
|
69
|
+
/* @__PURE__ */ jsx("h3", { className: "text-sm font-semibold text-[var(--as-fg)]", children: preset.name }),
|
|
70
|
+
preset.steps && preset.steps.length > 0 ? /* @__PURE__ */ jsx(
|
|
71
|
+
"ol",
|
|
72
|
+
{
|
|
73
|
+
"aria-label": checklistLabel,
|
|
74
|
+
className: "list-inside list-decimal space-y-1 text-sm text-[var(--as-muted-fg)]",
|
|
75
|
+
children: preset.steps.map((step, index) => /* @__PURE__ */ jsxs("li", { className: "flex items-start justify-between gap-2", children: [
|
|
76
|
+
/* @__PURE__ */ jsx("span", { children: stepText(step) }),
|
|
77
|
+
/* @__PURE__ */ jsx(
|
|
78
|
+
CopyButton,
|
|
79
|
+
{
|
|
80
|
+
value: step,
|
|
81
|
+
label: copyLabel,
|
|
82
|
+
size: 14,
|
|
83
|
+
className: "mt-0.5 size-6 shrink-0",
|
|
84
|
+
onClick: () => onCopyStep?.(step)
|
|
85
|
+
}
|
|
86
|
+
)
|
|
87
|
+
] }, index))
|
|
88
|
+
}
|
|
89
|
+
) : null,
|
|
90
|
+
preset.keyUrl ? onOpenKeyUrl ? /* @__PURE__ */ jsx("div", { children: /* @__PURE__ */ jsxs(
|
|
91
|
+
Button,
|
|
92
|
+
{
|
|
93
|
+
type: "button",
|
|
94
|
+
variant: "outline",
|
|
95
|
+
size: "sm",
|
|
96
|
+
onClick: () => onOpenKeyUrl(preset.keyUrl),
|
|
97
|
+
children: [
|
|
98
|
+
/* @__PURE__ */ jsx(ExternalLink, { "aria-hidden": true }),
|
|
99
|
+
getKeyLabel
|
|
100
|
+
]
|
|
101
|
+
}
|
|
102
|
+
) }) : /* @__PURE__ */ jsxs(
|
|
103
|
+
"a",
|
|
104
|
+
{
|
|
105
|
+
href: preset.keyUrl,
|
|
106
|
+
target: "_blank",
|
|
107
|
+
rel: "noreferrer",
|
|
108
|
+
className: "inline-flex w-fit items-center gap-1 text-sm font-medium text-[var(--as-primary)] underline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)]",
|
|
109
|
+
children: [
|
|
110
|
+
/* @__PURE__ */ jsx(ExternalLink, { className: "size-3.5", "aria-hidden": true }),
|
|
111
|
+
getKeyLabel
|
|
112
|
+
]
|
|
113
|
+
}
|
|
114
|
+
) : null,
|
|
115
|
+
preset.freeTierNote ? /* @__PURE__ */ jsx("p", { className: "text-xs text-[var(--as-muted-fg)]", children: preset.freeTierNote }) : null,
|
|
116
|
+
/* @__PURE__ */ jsx(
|
|
117
|
+
Input,
|
|
118
|
+
{
|
|
119
|
+
label: nameLabel,
|
|
120
|
+
value: value.name,
|
|
121
|
+
placeholder: preset.name,
|
|
122
|
+
onChange: (event) => onChange({ ...value, name: event.target.value })
|
|
123
|
+
}
|
|
124
|
+
),
|
|
125
|
+
preset.local ? /* @__PURE__ */ jsx("p", { className: "text-sm text-[var(--as-muted-fg)]", children: noKeyLabel }) : /* @__PURE__ */ jsx(
|
|
126
|
+
Input,
|
|
127
|
+
{
|
|
128
|
+
label: apiKeyLabel,
|
|
129
|
+
type: "password",
|
|
130
|
+
autoComplete: "new-password",
|
|
131
|
+
placeholder: keyPlaceholder,
|
|
132
|
+
value: value.apiKey,
|
|
133
|
+
onChange: (event) => onChange({ ...value, apiKey: event.target.value })
|
|
134
|
+
}
|
|
135
|
+
),
|
|
136
|
+
/* @__PURE__ */ jsxs("details", { className: "rounded-[var(--as-radius)] border border-[var(--as-border)] px-3 py-2", children: [
|
|
137
|
+
/* @__PURE__ */ jsx("summary", { className: "cursor-pointer text-sm font-medium text-[var(--as-fg)]", children: advancedLabel }),
|
|
138
|
+
/* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-1 pt-2", children: [
|
|
139
|
+
/* @__PURE__ */ jsx(
|
|
140
|
+
Input,
|
|
141
|
+
{
|
|
142
|
+
label: baseUrlLabel,
|
|
143
|
+
value: value.baseUrl ?? "",
|
|
144
|
+
readOnly: preset.fixedBase,
|
|
145
|
+
className: "font-mono data-[readonly]:cursor-default data-[readonly]:opacity-80",
|
|
146
|
+
onChange: (event) => onChange({ ...value, baseUrl: event.target.value })
|
|
147
|
+
}
|
|
148
|
+
),
|
|
149
|
+
!preset.fixedBase && baseUrlHint ? /* @__PURE__ */ jsx("p", { className: "text-xs text-[var(--as-muted-fg)]", children: baseUrlHint }) : null,
|
|
150
|
+
advancedExtra
|
|
151
|
+
] })
|
|
152
|
+
] }),
|
|
153
|
+
error && errorCopy ? /* @__PURE__ */ jsxs("div", { role: "alert", className: "space-y-1", children: [
|
|
154
|
+
/* @__PURE__ */ jsx("p", { className: "text-sm font-medium text-[var(--as-danger)]", children: errorCopy }),
|
|
155
|
+
error.suspectedVendor ? /* @__PURE__ */ jsx("p", { className: "text-sm text-[var(--as-muted-fg)]", children: suspectedVendorHint.replaceAll(
|
|
156
|
+
"{vendor}",
|
|
157
|
+
error.suspectedVendor
|
|
158
|
+
) }) : null
|
|
159
|
+
] }) : null,
|
|
160
|
+
/* @__PURE__ */ jsxs("div", { className: "flex items-center justify-end gap-2", children: [
|
|
161
|
+
onCancel ? /* @__PURE__ */ jsx(Button, { type: "button", variant: "ghost", size: "sm", onClick: onCancel, children: cancelLabel }) : null,
|
|
162
|
+
/* @__PURE__ */ jsx(
|
|
163
|
+
Button,
|
|
164
|
+
{
|
|
165
|
+
type: "submit",
|
|
166
|
+
size: "sm",
|
|
167
|
+
loading: testing,
|
|
168
|
+
disabled: testing || !preset.local && value.apiKey.trim() === "",
|
|
169
|
+
children: submitLabel
|
|
170
|
+
}
|
|
171
|
+
)
|
|
172
|
+
] })
|
|
173
|
+
]
|
|
174
|
+
}
|
|
175
|
+
);
|
|
176
|
+
});
|
|
177
|
+
|
|
178
|
+
export { DEFAULT_SETUP_ERROR_COPY, ProviderSetupForm, SETUP_ERROR_CODES };
|
|
179
|
+
//# sourceMappingURL=chunk-6G7H6YP6.js.map
|
|
180
|
+
//# sourceMappingURL=chunk-6G7H6YP6.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/components/provider-setup-form/ProviderSetupForm.tsx"],"names":["ProviderSetupForm"],"mappings":"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","file":"chunk-6G7H6YP6.js","sourcesContent":["import * as React from 'react'\nimport { ExternalLink } from 'lucide-react'\nimport { cn } from '../../lib/utils'\nimport { Button } from '../button/Button'\nimport { CopyButton } from '../copy-button/CopyButton'\nimport { Input } from '../input/Input'\n\n/** The shared §15 error-routing enum (family contract — apps key their i18n\n * off exactly these codes). */\nexport const SETUP_ERROR_CODES = [\n 'invalid_key',\n 'insufficient_credit',\n 'new_user_quota',\n 'region_unavailable',\n 'timeout',\n 'local_not_running',\n 'unknown',\n] as const\n\nexport type SetupErrorCode = (typeof SETUP_ERROR_CODES)[number]\n\n/** English fallback copy per code — apps inject translated labels via\n * `errorLabels` (the library ships no i18n engine, ADR-006). */\nexport const DEFAULT_SETUP_ERROR_COPY: Record<SetupErrorCode, string> = {\n invalid_key: 'The API key was rejected — check it and try again.',\n insufficient_credit: 'The account has no credit or quota left for this key.',\n new_user_quota: 'The provider hit a rate or quota limit — try again later.',\n region_unavailable: 'This provider or model is not available in your region.',\n timeout: 'The provider took too long to answer — try again.',\n local_not_running: 'Could not reach the local engine — make sure it is running.',\n unknown: 'The provider reported an unknown error.',\n}\n\n/** Guided-setup preset slice (app data; snake_case API fields map app-side). */\nexport interface ProviderSetupFormPreset {\n name: string\n keyUrl?: string\n steps?: string[]\n freeTierNote?: string\n fixedBase?: boolean\n baseUrl: string\n /** Keyless local preset — renders `noKeyLabel` instead of the key field. */\n local?: boolean\n}\n\nexport interface ProviderSetupFormValue {\n name: string\n apiKey: string\n baseUrl?: string\n}\n\n/** Classified setup failure (§15 error routing) — copy comes from\n * `errorLabels`, keyed off the code. */\nexport interface ProviderSetupFormError {\n code: SetupErrorCode | string\n suspectedVendor?: string | null\n}\n\nexport interface ProviderSetupFormProps\n extends Omit<React.ComponentProps<'form'>, 'onChange' | 'onSubmit'> {\n preset: ProviderSetupFormPreset\n /** Controlled field values. */\n value: ProviderSetupFormValue\n error?: ProviderSetupFormError | null\n /** Validation/connection test in flight — disables + marks the submit. */\n testing?: boolean\n onSubmit: (value: ProviderSetupFormValue) => void\n onCancel?: () => void\n onChange: (value: ProviderSetupFormValue) => void\n /** Translated error copy per §15 code (`{vendor}` interpolates in the hint). */\n errorLabels?: Partial<Record<string, string>>\n suspectedVendorHint?: string\n /** Notified when a checklist step is copied (Electron apps mirror the copy\n * through their IPC clipboard; the browser write always happens). */\n onCopyStep?: (step: string) => void\n /** Opens the key page — render an anchor by default; Electron apps pass\n * their `openExternal` bridge to get a button instead. */\n onOpenKeyUrl?: (url: string) => void\n /** Extra app content inside the Advanced disclosure (hosting toggle,\n * country select — study/health pattern). */\n advancedExtra?: React.ReactNode\n checklistLabel?: string\n copyLabel?: string\n getKeyLabel?: string\n nameLabel?: string\n apiKeyLabel?: string\n keyPlaceholder?: string\n noKeyLabel?: string\n advancedLabel?: string\n baseUrlLabel?: string\n baseUrlHint?: string\n submitLabel?: string\n cancelLabel?: string\n}\n\n/** Guided one-click setup form (plan 26 §6): vendor checklist with copy\n * buttons and key link, connection name, write-only API key\n * (`autoComplete=\"new-password\"`), and an Advanced disclosure whose base URL\n * is read-only for fixed-endpoint presets. Validation, secrets and IPC are\n * the app's business (ADR-006) — the form reports `onSubmit`. */\nexport const ProviderSetupForm = React.forwardRef<\n HTMLFormElement,\n ProviderSetupFormProps\n>(function ProviderSetupForm(\n {\n preset,\n value,\n error,\n testing = false,\n onSubmit,\n onCancel,\n onChange,\n errorLabels,\n suspectedVendorHint = 'This looks like a {vendor} API key.',\n onCopyStep,\n onOpenKeyUrl,\n advancedExtra,\n checklistLabel = 'Setup steps',\n copyLabel = 'Copy',\n getKeyLabel = 'Get an API key',\n nameLabel = 'Connection name',\n apiKeyLabel = 'API key',\n keyPlaceholder = 'sk-…',\n noKeyLabel = 'Runs on your machine — no API key needed.',\n advancedLabel = 'Advanced',\n baseUrlLabel = 'API base URL',\n baseUrlHint,\n submitLabel = 'Connect',\n cancelLabel = 'Back',\n className,\n ...props\n },\n ref,\n) {\n const stepText = (step: string): string =>\n step.replaceAll('{url}', preset.keyUrl ?? '')\n\n const errorCopy = error\n ? (errorLabels?.[error.code] ??\n DEFAULT_SETUP_ERROR_COPY[error.code as SetupErrorCode] ??\n errorLabels?.unknown ??\n DEFAULT_SETUP_ERROR_COPY.unknown)\n : null\n\n return (\n <form\n ref={ref}\n data-as=\"provider-setup-form\"\n className={cn('flex w-full flex-col gap-3', className)}\n onSubmit={(event) => {\n event.preventDefault()\n if (!testing) onSubmit(value)\n }}\n {...props}\n >\n <h3 className=\"text-sm font-semibold text-[var(--as-fg)]\">{preset.name}</h3>\n\n {preset.steps && preset.steps.length > 0 ? (\n <ol\n aria-label={checklistLabel}\n className=\"list-inside list-decimal space-y-1 text-sm text-[var(--as-muted-fg)]\"\n >\n {preset.steps.map((step, index) => (\n <li key={index} className=\"flex items-start justify-between gap-2\">\n <span>{stepText(step)}</span>\n <CopyButton\n value={step}\n label={copyLabel}\n size={14}\n className=\"mt-0.5 size-6 shrink-0\"\n onClick={() => onCopyStep?.(step)}\n />\n </li>\n ))}\n </ol>\n ) : null}\n\n {preset.keyUrl ? onOpenKeyUrl ? (\n <div>\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n onClick={() => onOpenKeyUrl(preset.keyUrl!)}\n >\n <ExternalLink aria-hidden />\n {getKeyLabel}\n </Button>\n </div>\n ) : (\n <a\n href={preset.keyUrl}\n target=\"_blank\"\n rel=\"noreferrer\"\n className=\"inline-flex w-fit items-center gap-1 text-sm font-medium text-[var(--as-primary)] underline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)]\"\n >\n <ExternalLink className=\"size-3.5\" aria-hidden />\n {getKeyLabel}\n </a>\n ) : null}\n\n {preset.freeTierNote ? (\n <p className=\"text-xs text-[var(--as-muted-fg)]\">{preset.freeTierNote}</p>\n ) : null}\n\n <Input\n label={nameLabel}\n value={value.name}\n placeholder={preset.name}\n onChange={(event) => onChange({ ...value, name: event.target.value })}\n />\n\n {preset.local ? (\n <p className=\"text-sm text-[var(--as-muted-fg)]\">{noKeyLabel}</p>\n ) : (\n <Input\n label={apiKeyLabel}\n type=\"password\"\n autoComplete=\"new-password\"\n placeholder={keyPlaceholder}\n value={value.apiKey}\n onChange={(event) => onChange({ ...value, apiKey: event.target.value })}\n />\n )}\n\n <details className=\"rounded-[var(--as-radius)] border border-[var(--as-border)] px-3 py-2\">\n <summary className=\"cursor-pointer text-sm font-medium text-[var(--as-fg)]\">\n {advancedLabel}\n </summary>\n <div className=\"flex flex-col gap-1 pt-2\">\n <Input\n label={baseUrlLabel}\n value={value.baseUrl ?? ''}\n readOnly={preset.fixedBase}\n className=\"font-mono data-[readonly]:cursor-default data-[readonly]:opacity-80\"\n onChange={(event) =>\n onChange({ ...value, baseUrl: event.target.value })\n }\n />\n {!preset.fixedBase && baseUrlHint ? (\n <p className=\"text-xs text-[var(--as-muted-fg)]\">{baseUrlHint}</p>\n ) : null}\n {advancedExtra}\n </div>\n </details>\n\n {error && errorCopy ? (\n <div role=\"alert\" className=\"space-y-1\">\n <p className=\"text-sm font-medium text-[var(--as-danger)]\">\n {errorCopy}\n </p>\n {error.suspectedVendor ? (\n <p className=\"text-sm text-[var(--as-muted-fg)]\">\n {suspectedVendorHint.replaceAll(\n '{vendor}',\n error.suspectedVendor,\n )}\n </p>\n ) : null}\n </div>\n ) : null}\n\n <div className=\"flex items-center justify-end gap-2\">\n {onCancel ? (\n <Button type=\"button\" variant=\"ghost\" size=\"sm\" onClick={onCancel}>\n {cancelLabel}\n </Button>\n ) : null}\n <Button\n type=\"submit\"\n size=\"sm\"\n loading={testing}\n disabled={testing || (!preset.local && value.apiKey.trim() === '')}\n >\n {submitLabel}\n </Button>\n </div>\n </form>\n )\n})\n"]}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { cn } from './chunk-RVVXVTH3.js';
|
|
2
|
+
import * as React from 'react';
|
|
3
|
+
import { jsx } from 'react/jsx-runtime';
|
|
4
|
+
|
|
5
|
+
var ICON_PATHS = {
|
|
6
|
+
gemini: "M11.04 19.32Q12 21.51 12 24q0-2.49.93-4.68.96-2.19 2.58-3.81t3.81-2.55Q21.51 12 24 12q-2.49 0-4.68-.93a12.3 12.3 0 0 1-3.81-2.58 12.3 12.3 0 0 1-2.58-3.81Q12 2.49 12 0q0 2.49-.96 4.68-.93 2.19-2.55 3.81a12.3 12.3 0 0 1-3.81 2.58Q2.49 12 0 12q2.49 0 4.68.96 2.19.93 3.81 2.55t2.55 3.81",
|
|
7
|
+
openrouter: "M16.778 1.844v1.919q-.569-.026-1.138-.032-.708-.008-1.415.037c-1.93.126-4.023.728-6.149 2.237-2.911 2.066-2.731 1.95-4.14 2.75-.396.223-1.342.574-2.185.798-.841.225-1.753.333-1.751.333v4.229s.768.108 1.61.333c.842.224 1.789.575 2.185.799 1.41.798 1.228.683 4.14 2.75 2.126 1.509 4.22 2.11 6.148 2.236.88.058 1.716.041 2.555.005v1.918l7.222-4.168-7.222-4.17v2.176c-.86.038-1.611.065-2.278.021-1.364-.09-2.417-.357-3.979-1.465-2.244-1.593-2.866-2.027-3.68-2.508.889-.518 1.449-.906 3.822-2.59 1.56-1.109 2.614-1.377 3.978-1.466.667-.044 1.418-.017 2.278.02v2.176L24 6.014Z",
|
|
8
|
+
anthropic: "M17.3041 3.541h-3.6718l6.696 16.918H24Zm-10.6082 0L0 20.459h3.7442l1.3693-3.5527h7.0052l1.3693 3.5528h3.7442L10.5363 3.5409Zm-.3712 10.2232 2.2914-5.9456 2.2914 5.9456Z",
|
|
9
|
+
mistral: "M17.143 3.429v3.428h-3.429v3.429h-3.428V6.857H6.857V3.43H3.43v13.714H0v3.428h10.286v-3.428H6.857v-3.429h3.429v3.429h3.429v-3.429h3.428v3.429h-3.428v3.428H24v-3.428h-3.43V3.429z",
|
|
10
|
+
deepseek: "M23.748 4.651c-.254-.124-.364.113-.512.233-.051.04-.094.09-.137.137-.372.397-.806.657-1.373.626-.829-.046-1.537.214-2.163.848-.133-.782-.575-1.248-1.247-1.548-.352-.155-.708-.311-.955-.65-.172-.24-.219-.509-.305-.774-.055-.16-.11-.323-.293-.35-.2-.031-.278.136-.356.276-.313.572-.434 1.202-.422 1.84.027 1.436.633 2.58 1.838 3.393.137.094.172.187.129.323-.082.28-.18.553-.266.833-.055.179-.137.218-.328.14a5.5 5.5 0 0 1-1.737-1.179c-.857-.828-1.631-1.743-2.597-2.46a12 12 0 0 0-.689-.47c-.985-.957.13-1.743.387-1.836.27-.098.094-.433-.778-.428-.872.003-1.67.295-2.687.685a3 3 0 0 1-.465.136 9.6 9.6 0 0 0-2.883-.101c-1.885.21-3.39 1.1-4.497 2.622C.082 8.776-.231 10.854.152 13.02c.403 2.284 1.568 4.175 3.36 5.653 1.857 1.533 3.997 2.284 6.438 2.14 1.482-.085 3.132-.284 4.994-1.86.47.234.962.328 1.78.398.629.058 1.235-.031 1.705-.129.735-.155.684-.836.418-.961-2.155-1.004-1.682-.595-2.112-.926 1.095-1.295 2.768-3.598 3.284-6.733.05-.346.115-.834.108-1.114-.004-.171.035-.238.23-.257a4.2 4.2 0 0 0 1.545-.475c1.397-.763 1.96-2.016 2.093-3.517.02-.23-.004-.467-.247-.588M11.58 18.168c-2.088-1.642-3.101-2.183-3.52-2.16-.39.024-.32.472-.234.763.09.288.207.487.371.74.114.167.192.416-.113.603-.673.416-1.842-.14-1.897-.168-1.361-.801-2.5-1.86-3.301-3.306-.775-1.393-1.225-2.888-1.299-4.482-.02-.385.094-.522.477-.592a4.7 4.7 0 0 1 1.53-.038c2.131.311 3.946 1.264 5.467 2.774.868.86 1.525 1.887 2.202 2.89.72 1.066 1.494 2.082 2.48 2.915.348.291.626.513.892.677-.802.09-2.14.109-3.055-.615zm1.001-6.44a.306.306 0 0 1 .415-.287.3.3 0 0 1 .113.074.3.3 0 0 1 .086.214c0 .17-.136.307-.308.307a.303.303 0 0 1-.306-.307m3.11 1.596c-.2.081-.4.151-.591.16a1.25 1.25 0 0 1-.798-.254c-.274-.23-.47-.358-.551-.758a1.7 1.7 0 0 1 .015-.588c.07-.327-.007-.537-.238-.727-.188-.156-.426-.199-.689-.199a.6.6 0 0 1-.254-.078.253.253 0 0 1-.114-.358 1 1 0 0 1 .192-.21c.356-.202.767-.136 1.146.016.352.144.618.408 1.001.782.392.451.462.576.685.915.176.264.336.536.446.848.066.194-.02.353-.25.45",
|
|
11
|
+
ollama: "M16.361 10.26a.894.894 0 0 0-.558.47l-.072.148.001.207c0 .193.004.217.059.353.076.193.152.312.291.448.24.238.51.3.872.205a.86.86 0 0 0 .517-.436.752.752 0 0 0 .08-.498c-.064-.453-.33-.782-.724-.897a1.06 1.06 0 0 0-.466 0zm-9.203.005c-.305.096-.533.32-.65.639a1.187 1.187 0 0 0-.06.52c.057.309.31.59.598.667.362.095.632.033.872-.205.14-.136.215-.255.291-.448.055-.136.059-.16.059-.353l.001-.207-.072-.148a.894.894 0 0 0-.565-.472 1.02 1.02 0 0 0-.474.007zm4.184 2c-.131.071-.223.25-.195.383.031.143.157.288.353.407.105.063.112.072.117.136.004.038-.01.146-.029.243-.02.094-.036.194-.036.222.002.074.07.195.143.253.064.052.076.054.255.059.164.005.198.001.264-.03.169-.082.212-.234.15-.525-.052-.243-.042-.28.087-.355.137-.08.281-.219.324-.314a.365.365 0 0 0-.175-.48.394.394 0 0 0-.181-.033c-.126 0-.207.03-.355.124l-.085.053-.053-.032c-.219-.13-.259-.145-.391-.143a.396.396 0 0 0-.193.032zm.39-2.195c-.373.036-.475.05-.654.086-.291.06-.68.195-.951.328-.94.46-1.589 1.226-1.787 2.114-.04.176-.045.234-.045.53 0 .294.005.357.043.524.264 1.16 1.332 2.017 2.714 2.173.3.033 1.596.033 1.896 0 1.11-.125 2.064-.727 2.493-1.571.114-.226.169-.372.22-.602.039-.167.044-.23.044-.523 0-.297-.005-.355-.045-.531-.288-1.29-1.539-2.304-3.072-2.497a6.9 6.9 0 0 0-.855-.031zm.645.937a3.3 3.3 0 0 1 1.44.514c.223.148.537.458.671.662.166.251.26.508.303.82.02.143.01.251-.043.482-.08.345-.332.705-.672.957a3.1 3.1 0 0 1-.689.348c-.382.122-.632.144-1.525.138-.582-.006-.686-.01-.853-.042-.57-.107-1.022-.334-1.35-.68-.264-.28-.385-.535-.45-.946-.03-.192.025-.509.137-.776.136-.326.488-.73.836-.963.403-.269.934-.46 1.422-.512.187-.02.586-.02.773-.002zm-5.503-11a1.65 1.65 0 0 0-.683.298C5.617.74 5.173 1.666 4.985 2.819c-.07.436-.119 1.04-.119 1.503 0 .544.064 1.24.155 1.721.02.107.031.202.023.208a8 8 0 0 1-.187.152 5.3 5.3 0 0 0-.949 1.02 5.5 5.5 0 0 0-.94 2.339 6.6 6.6 0 0 0-.023 1.357c.091.78.325 1.438.727 2.04l.13.195-.037.064c-.269.452-.498 1.105-.605 1.732-.084.496-.095.629-.095 1.294 0 .67.009.803.088 1.266.095.555.288 1.143.503 1.534.071.128.243.393.264.407.007.003-.014.067-.046.141a7.4 7.4 0 0 0-.548 1.873c-.062.417-.071.552-.071.991 0 .56.031.832.148 1.279L3.42 24h1.478l-.05-.091c-.297-.552-.325-1.575-.068-2.597.117-.472.25-.819.498-1.296l.148-.29v-.177c0-.165-.003-.184-.057-.293a.9.9 0 0 0-.194-.25 1.74 1.74 0 0 1-.385-.543c-.424-.92-.506-2.286-.208-3.451.124-.486.329-.918.544-1.154a.79.79 0 0 0 .223-.531c0-.195-.07-.355-.224-.522a3.1 3.1 0 0 1-.817-1.729c-.14-.96.114-2.005.69-2.834.563-.814 1.353-1.336 2.237-1.475.199-.033.57-.028.776.01.226.04.367.028.512-.041.179-.085.268-.19.374-.431.093-.215.165-.333.36-.576.234-.29.46-.489.822-.729.413-.27.884-.467 1.352-.561.17-.035.25-.04.569-.04.319 0 .398.005.569.04a4.07 4.07 0 0 1 1.914.997c.117.109.398.457.488.602.034.057.095.177.132.267.105.241.195.346.374.43.14.068.286.082.503.045.343-.058.607-.053.943.016 1.144.23 2.14 1.173 2.581 2.437.385 1.108.276 2.267-.296 3.153-.097.15-.193.27-.333.419-.301.322-.301.722-.001 1.053.493.539.801 1.866.708 3.036-.062.772-.26 1.463-.533 1.854a2 2 0 0 1-.224.258.9.9 0 0 0-.194.25c-.054.109-.057.128-.057.293v.178l.148.29c.248.476.38.823.498 1.295.253 1.008.231 2.01-.059 2.581a.8.8 0 0 0-.044.098c0 .006.329.009.732.009h.73l.02-.074.036-.134c.019-.076.057-.3.088-.516.029-.217.029-1.016 0-1.258-.11-.875-.295-1.57-.597-2.226-.032-.074-.053-.138-.046-.141.008-.005.057-.074.108-.152.376-.569.607-1.284.724-2.228.031-.26.031-1.378 0-1.628-.083-.645-.182-1.082-.348-1.525a6 6 0 0 0-.329-.7l-.038-.064.131-.194c.402-.604.636-1.262.727-2.04a6.6 6.6 0 0 0-.024-1.358 5.5 5.5 0 0 0-.939-2.339 5.3 5.3 0 0 0-.95-1.02 8 8 0 0 1-.186-.152.7.7 0 0 1 .023-.208c.208-1.087.201-2.443-.017-3.503-.19-.924-.535-1.658-.98-2.082-.354-.338-.716-.482-1.15-.455-.996.059-1.8 1.205-2.116 3.01a6.8 6.8 0 0 0-.097.726c0 .036-.007.066-.015.066a1 1 0 0 1-.149-.078A4.9 4.9 0 0 0 12 3.03c-.832 0-1.687.243-2.456.698a1 1 0 0 1-.148.078c-.008 0-.015-.03-.015-.066a6.7 6.7 0 0 0-.097-.725C8.997 1.392 8.337.319 7.46.048a2 2 0 0 0-.585-.041zm.293 1.402c.248.197.523.759.682 1.388.03.113.06.244.069.292.007.047.026.152.041.233.067.365.098.76.102 1.24l.002.475-.12.175-.118.178h-.278c-.324 0-.646.041-.954.124l-.238.06c-.033.007-.038-.003-.057-.144a8.4 8.4 0 0 1 .016-2.323c.124-.788.413-1.501.696-1.711.067-.05.079-.049.157.013zm9.825-.012c.17.126.358.46.498.888.28.854.36 2.028.212 3.145-.019.14-.024.151-.057.144l-.238-.06a3.7 3.7 0 0 0-.954-.124h-.278l-.119-.178-.119-.175.002-.474c.004-.669.066-1.19.214-1.772.157-.623.434-1.185.68-1.382.078-.062.09-.063.159-.012z"
|
|
12
|
+
};
|
|
13
|
+
var ProviderLogo = React.forwardRef(
|
|
14
|
+
function ProviderLogo2({ preset, size = 20, className, style, ...props }, ref) {
|
|
15
|
+
const path = ICON_PATHS[preset];
|
|
16
|
+
return /* @__PURE__ */ jsx(
|
|
17
|
+
"span",
|
|
18
|
+
{
|
|
19
|
+
ref,
|
|
20
|
+
"data-as": "provider-logo",
|
|
21
|
+
"data-preset": preset,
|
|
22
|
+
"aria-hidden": "true",
|
|
23
|
+
className: cn(
|
|
24
|
+
"inline-flex shrink-0 items-center justify-center text-[var(--as-fg)]",
|
|
25
|
+
className
|
|
26
|
+
),
|
|
27
|
+
style: { width: size, height: size, ...style },
|
|
28
|
+
...props,
|
|
29
|
+
children: path ? /* @__PURE__ */ jsx(
|
|
30
|
+
"svg",
|
|
31
|
+
{
|
|
32
|
+
viewBox: "0 0 24 24",
|
|
33
|
+
width: size,
|
|
34
|
+
height: size,
|
|
35
|
+
fill: "currentColor",
|
|
36
|
+
focusable: "false",
|
|
37
|
+
children: /* @__PURE__ */ jsx("path", { d: path })
|
|
38
|
+
}
|
|
39
|
+
) : /* @__PURE__ */ jsx(
|
|
40
|
+
"span",
|
|
41
|
+
{
|
|
42
|
+
className: "flex h-full w-full items-center justify-center rounded-full border border-[var(--as-border)] font-semibold text-[var(--as-muted-fg)]",
|
|
43
|
+
style: { fontSize: Math.max(8, Math.round(size / 2)) },
|
|
44
|
+
children: preset.charAt(0).toUpperCase()
|
|
45
|
+
}
|
|
46
|
+
)
|
|
47
|
+
}
|
|
48
|
+
);
|
|
49
|
+
}
|
|
50
|
+
);
|
|
51
|
+
|
|
52
|
+
export { ProviderLogo };
|
|
53
|
+
//# sourceMappingURL=chunk-7IP3JP3Z.js.map
|
|
54
|
+
//# sourceMappingURL=chunk-7IP3JP3Z.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/components/provider-logo/ProviderLogo.tsx"],"names":["ProviderLogo"],"mappings":";;;;AASA,IAAM,UAAA,GAAqC;AAAA,EACzC,MAAA,EACE,8RAAA;AAAA,EACF,UAAA,EACE,4jBAAA;AAAA,EACF,SAAA,EACE,0KAAA;AAAA,EACF,OAAA,EACE,kLAAA;AAAA,EACF,QAAA,EACE,w7DAAA;AAAA,EACF,MAAA,EACE;AACJ,CAAA;AAcO,IAAM,YAAA,GAAqB,KAAA,CAAA,UAAA;AAAA,EAChC,SAASA,aAAAA,CAAa,EAAE,MAAA,EAAQ,IAAA,GAAO,EAAA,EAAI,SAAA,EAAW,KAAA,EAAO,GAAG,KAAA,EAAM,EAAG,GAAA,EAAK;AAC5E,IAAA,MAAM,IAAA,GAAO,WAAW,MAAM,CAAA;AAC9B,IAAA,uBACE,GAAA;AAAA,MAAC,MAAA;AAAA,MAAA;AAAA,QACC,GAAA;AAAA,QACA,SAAA,EAAQ,eAAA;AAAA,QACR,aAAA,EAAa,MAAA;AAAA,QACb,aAAA,EAAY,MAAA;AAAA,QACZ,SAAA,EAAW,EAAA;AAAA,UACT,sEAAA;AAAA,UACA;AAAA,SACF;AAAA,QACA,OAAO,EAAE,KAAA,EAAO,MAAM,MAAA,EAAQ,IAAA,EAAM,GAAG,KAAA,EAAM;AAAA,QAC5C,GAAG,KAAA;AAAA,QAEH,QAAA,EAAA,IAAA,mBACC,GAAA;AAAA,UAAC,KAAA;AAAA,UAAA;AAAA,YACC,OAAA,EAAQ,WAAA;AAAA,YACR,KAAA,EAAO,IAAA;AAAA,YACP,MAAA,EAAQ,IAAA;AAAA,YACR,IAAA,EAAK,cAAA;AAAA,YACL,SAAA,EAAU,OAAA;AAAA,YAEV,QAAA,kBAAA,GAAA,CAAC,MAAA,EAAA,EAAK,CAAA,EAAG,IAAA,EAAM;AAAA;AAAA,SACjB,mBAEA,GAAA;AAAA,UAAC,MAAA;AAAA,UAAA;AAAA,YACC,SAAA,EAAU,sIAAA;AAAA,YACV,KAAA,EAAO,EAAE,QAAA,EAAU,IAAA,CAAK,GAAA,CAAI,CAAA,EAAG,IAAA,CAAK,KAAA,CAAM,IAAA,GAAO,CAAC,CAAC,CAAA,EAAE;AAAA,YAEpD,QAAA,EAAA,MAAA,CAAO,MAAA,CAAO,CAAC,CAAA,CAAE,WAAA;AAAY;AAAA;AAChC;AAAA,KAEJ;AAAA,EAEJ;AACF","file":"chunk-7IP3JP3Z.js","sourcesContent":["import * as React from 'react'\nimport { cn } from '../../lib/utils'\n\n/**\n * Simple-icons path data keyed by preset key (inline — no runtime\n * dependency). The openai and groq marks were removed upstream by their\n * brands, so those keys (and any unknown key) intentionally fall back to the\n * monogram.\n */\nconst ICON_PATHS: Record<string, string> = {\n gemini:\n 'M11.04 19.32Q12 21.51 12 24q0-2.49.93-4.68.96-2.19 2.58-3.81t3.81-2.55Q21.51 12 24 12q-2.49 0-4.68-.93a12.3 12.3 0 0 1-3.81-2.58 12.3 12.3 0 0 1-2.58-3.81Q12 2.49 12 0q0 2.49-.96 4.68-.93 2.19-2.55 3.81a12.3 12.3 0 0 1-3.81 2.58Q2.49 12 0 12q2.49 0 4.68.96 2.19.93 3.81 2.55t2.55 3.81',\n openrouter:\n 'M16.778 1.844v1.919q-.569-.026-1.138-.032-.708-.008-1.415.037c-1.93.126-4.023.728-6.149 2.237-2.911 2.066-2.731 1.95-4.14 2.75-.396.223-1.342.574-2.185.798-.841.225-1.753.333-1.751.333v4.229s.768.108 1.61.333c.842.224 1.789.575 2.185.799 1.41.798 1.228.683 4.14 2.75 2.126 1.509 4.22 2.11 6.148 2.236.88.058 1.716.041 2.555.005v1.918l7.222-4.168-7.222-4.17v2.176c-.86.038-1.611.065-2.278.021-1.364-.09-2.417-.357-3.979-1.465-2.244-1.593-2.866-2.027-3.68-2.508.889-.518 1.449-.906 3.822-2.59 1.56-1.109 2.614-1.377 3.978-1.466.667-.044 1.418-.017 2.278.02v2.176L24 6.014Z',\n anthropic:\n 'M17.3041 3.541h-3.6718l6.696 16.918H24Zm-10.6082 0L0 20.459h3.7442l1.3693-3.5527h7.0052l1.3693 3.5528h3.7442L10.5363 3.5409Zm-.3712 10.2232 2.2914-5.9456 2.2914 5.9456Z',\n mistral:\n 'M17.143 3.429v3.428h-3.429v3.429h-3.428V6.857H6.857V3.43H3.43v13.714H0v3.428h10.286v-3.428H6.857v-3.429h3.429v3.429h3.429v-3.429h3.428v3.429h-3.428v3.428H24v-3.428h-3.43V3.429z',\n deepseek:\n 'M23.748 4.651c-.254-.124-.364.113-.512.233-.051.04-.094.09-.137.137-.372.397-.806.657-1.373.626-.829-.046-1.537.214-2.163.848-.133-.782-.575-1.248-1.247-1.548-.352-.155-.708-.311-.955-.65-.172-.24-.219-.509-.305-.774-.055-.16-.11-.323-.293-.35-.2-.031-.278.136-.356.276-.313.572-.434 1.202-.422 1.84.027 1.436.633 2.58 1.838 3.393.137.094.172.187.129.323-.082.28-.18.553-.266.833-.055.179-.137.218-.328.14a5.5 5.5 0 0 1-1.737-1.179c-.857-.828-1.631-1.743-2.597-2.46a12 12 0 0 0-.689-.47c-.985-.957.13-1.743.387-1.836.27-.098.094-.433-.778-.428-.872.003-1.67.295-2.687.685a3 3 0 0 1-.465.136 9.6 9.6 0 0 0-2.883-.101c-1.885.21-3.39 1.1-4.497 2.622C.082 8.776-.231 10.854.152 13.02c.403 2.284 1.568 4.175 3.36 5.653 1.857 1.533 3.997 2.284 6.438 2.14 1.482-.085 3.132-.284 4.994-1.86.47.234.962.328 1.78.398.629.058 1.235-.031 1.705-.129.735-.155.684-.836.418-.961-2.155-1.004-1.682-.595-2.112-.926 1.095-1.295 2.768-3.598 3.284-6.733.05-.346.115-.834.108-1.114-.004-.171.035-.238.23-.257a4.2 4.2 0 0 0 1.545-.475c1.397-.763 1.96-2.016 2.093-3.517.02-.23-.004-.467-.247-.588M11.58 18.168c-2.088-1.642-3.101-2.183-3.52-2.16-.39.024-.32.472-.234.763.09.288.207.487.371.74.114.167.192.416-.113.603-.673.416-1.842-.14-1.897-.168-1.361-.801-2.5-1.86-3.301-3.306-.775-1.393-1.225-2.888-1.299-4.482-.02-.385.094-.522.477-.592a4.7 4.7 0 0 1 1.53-.038c2.131.311 3.946 1.264 5.467 2.774.868.86 1.525 1.887 2.202 2.89.72 1.066 1.494 2.082 2.48 2.915.348.291.626.513.892.677-.802.09-2.14.109-3.055-.615zm1.001-6.44a.306.306 0 0 1 .415-.287.3.3 0 0 1 .113.074.3.3 0 0 1 .086.214c0 .17-.136.307-.308.307a.303.303 0 0 1-.306-.307m3.11 1.596c-.2.081-.4.151-.591.16a1.25 1.25 0 0 1-.798-.254c-.274-.23-.47-.358-.551-.758a1.7 1.7 0 0 1 .015-.588c.07-.327-.007-.537-.238-.727-.188-.156-.426-.199-.689-.199a.6.6 0 0 1-.254-.078.253.253 0 0 1-.114-.358 1 1 0 0 1 .192-.21c.356-.202.767-.136 1.146.016.352.144.618.408 1.001.782.392.451.462.576.685.915.176.264.336.536.446.848.066.194-.02.353-.25.45',\n ollama:\n 'M16.361 10.26a.894.894 0 0 0-.558.47l-.072.148.001.207c0 .193.004.217.059.353.076.193.152.312.291.448.24.238.51.3.872.205a.86.86 0 0 0 .517-.436.752.752 0 0 0 .08-.498c-.064-.453-.33-.782-.724-.897a1.06 1.06 0 0 0-.466 0zm-9.203.005c-.305.096-.533.32-.65.639a1.187 1.187 0 0 0-.06.52c.057.309.31.59.598.667.362.095.632.033.872-.205.14-.136.215-.255.291-.448.055-.136.059-.16.059-.353l.001-.207-.072-.148a.894.894 0 0 0-.565-.472 1.02 1.02 0 0 0-.474.007zm4.184 2c-.131.071-.223.25-.195.383.031.143.157.288.353.407.105.063.112.072.117.136.004.038-.01.146-.029.243-.02.094-.036.194-.036.222.002.074.07.195.143.253.064.052.076.054.255.059.164.005.198.001.264-.03.169-.082.212-.234.15-.525-.052-.243-.042-.28.087-.355.137-.08.281-.219.324-.314a.365.365 0 0 0-.175-.48.394.394 0 0 0-.181-.033c-.126 0-.207.03-.355.124l-.085.053-.053-.032c-.219-.13-.259-.145-.391-.143a.396.396 0 0 0-.193.032zm.39-2.195c-.373.036-.475.05-.654.086-.291.06-.68.195-.951.328-.94.46-1.589 1.226-1.787 2.114-.04.176-.045.234-.045.53 0 .294.005.357.043.524.264 1.16 1.332 2.017 2.714 2.173.3.033 1.596.033 1.896 0 1.11-.125 2.064-.727 2.493-1.571.114-.226.169-.372.22-.602.039-.167.044-.23.044-.523 0-.297-.005-.355-.045-.531-.288-1.29-1.539-2.304-3.072-2.497a6.9 6.9 0 0 0-.855-.031zm.645.937a3.3 3.3 0 0 1 1.44.514c.223.148.537.458.671.662.166.251.26.508.303.82.02.143.01.251-.043.482-.08.345-.332.705-.672.957a3.1 3.1 0 0 1-.689.348c-.382.122-.632.144-1.525.138-.582-.006-.686-.01-.853-.042-.57-.107-1.022-.334-1.35-.68-.264-.28-.385-.535-.45-.946-.03-.192.025-.509.137-.776.136-.326.488-.73.836-.963.403-.269.934-.46 1.422-.512.187-.02.586-.02.773-.002zm-5.503-11a1.65 1.65 0 0 0-.683.298C5.617.74 5.173 1.666 4.985 2.819c-.07.436-.119 1.04-.119 1.503 0 .544.064 1.24.155 1.721.02.107.031.202.023.208a8 8 0 0 1-.187.152 5.3 5.3 0 0 0-.949 1.02 5.5 5.5 0 0 0-.94 2.339 6.6 6.6 0 0 0-.023 1.357c.091.78.325 1.438.727 2.04l.13.195-.037.064c-.269.452-.498 1.105-.605 1.732-.084.496-.095.629-.095 1.294 0 .67.009.803.088 1.266.095.555.288 1.143.503 1.534.071.128.243.393.264.407.007.003-.014.067-.046.141a7.4 7.4 0 0 0-.548 1.873c-.062.417-.071.552-.071.991 0 .56.031.832.148 1.279L3.42 24h1.478l-.05-.091c-.297-.552-.325-1.575-.068-2.597.117-.472.25-.819.498-1.296l.148-.29v-.177c0-.165-.003-.184-.057-.293a.9.9 0 0 0-.194-.25 1.74 1.74 0 0 1-.385-.543c-.424-.92-.506-2.286-.208-3.451.124-.486.329-.918.544-1.154a.79.79 0 0 0 .223-.531c0-.195-.07-.355-.224-.522a3.1 3.1 0 0 1-.817-1.729c-.14-.96.114-2.005.69-2.834.563-.814 1.353-1.336 2.237-1.475.199-.033.57-.028.776.01.226.04.367.028.512-.041.179-.085.268-.19.374-.431.093-.215.165-.333.36-.576.234-.29.46-.489.822-.729.413-.27.884-.467 1.352-.561.17-.035.25-.04.569-.04.319 0 .398.005.569.04a4.07 4.07 0 0 1 1.914.997c.117.109.398.457.488.602.034.057.095.177.132.267.105.241.195.346.374.43.14.068.286.082.503.045.343-.058.607-.053.943.016 1.144.23 2.14 1.173 2.581 2.437.385 1.108.276 2.267-.296 3.153-.097.15-.193.27-.333.419-.301.322-.301.722-.001 1.053.493.539.801 1.866.708 3.036-.062.772-.26 1.463-.533 1.854a2 2 0 0 1-.224.258.9.9 0 0 0-.194.25c-.054.109-.057.128-.057.293v.178l.148.29c.248.476.38.823.498 1.295.253 1.008.231 2.01-.059 2.581a.8.8 0 0 0-.044.098c0 .006.329.009.732.009h.73l.02-.074.036-.134c.019-.076.057-.3.088-.516.029-.217.029-1.016 0-1.258-.11-.875-.295-1.57-.597-2.226-.032-.074-.053-.138-.046-.141.008-.005.057-.074.108-.152.376-.569.607-1.284.724-2.228.031-.26.031-1.378 0-1.628-.083-.645-.182-1.082-.348-1.525a6 6 0 0 0-.329-.7l-.038-.064.131-.194c.402-.604.636-1.262.727-2.04a6.6 6.6 0 0 0-.024-1.358 5.5 5.5 0 0 0-.939-2.339 5.3 5.3 0 0 0-.95-1.02 8 8 0 0 1-.186-.152.7.7 0 0 1 .023-.208c.208-1.087.201-2.443-.017-3.503-.19-.924-.535-1.658-.98-2.082-.354-.338-.716-.482-1.15-.455-.996.059-1.8 1.205-2.116 3.01a6.8 6.8 0 0 0-.097.726c0 .036-.007.066-.015.066a1 1 0 0 1-.149-.078A4.9 4.9 0 0 0 12 3.03c-.832 0-1.687.243-2.456.698a1 1 0 0 1-.148.078c-.008 0-.015-.03-.015-.066a6.7 6.7 0 0 0-.097-.725C8.997 1.392 8.337.319 7.46.048a2 2 0 0 0-.585-.041zm.293 1.402c.248.197.523.759.682 1.388.03.113.06.244.069.292.007.047.026.152.041.233.067.365.098.76.102 1.24l.002.475-.12.175-.118.178h-.278c-.324 0-.646.041-.954.124l-.238.06c-.033.007-.038-.003-.057-.144a8.4 8.4 0 0 1 .016-2.323c.124-.788.413-1.501.696-1.711.067-.05.079-.049.157.013zm9.825-.012c.17.126.358.46.498.888.28.854.36 2.028.212 3.145-.019.14-.024.151-.057.144l-.238-.06a3.7 3.7 0 0 0-.954-.124h-.278l-.119-.178-.119-.175.002-.474c.004-.669.066-1.19.214-1.772.157-.623.434-1.185.68-1.382.078-.062.09-.063.159-.012z',\n}\n\nexport interface ProviderLogoProps extends React.ComponentProps<'span'> {\n /** Preset key (`'openai'`, `'gemini'`, …) — unknown/unshipped marks fall\n * back to a monogram of the key's first letter. */\n preset: string\n /** Square icon size in px. */\n size?: number\n}\n\n/** Provider mark for setup tiles and rows: simple-icons path data keyed by\n * preset key, monogram fallback (openai/groq marks are gone upstream),\n * `currentColor` so it inherits app identity. Decorative by default\n * (`aria-hidden`) — name the tile/button it lives in. */\nexport const ProviderLogo = React.forwardRef<HTMLSpanElement, ProviderLogoProps>(\n function ProviderLogo({ preset, size = 20, className, style, ...props }, ref) {\n const path = ICON_PATHS[preset]\n return (\n <span\n ref={ref}\n data-as=\"provider-logo\"\n data-preset={preset}\n aria-hidden=\"true\"\n className={cn(\n 'inline-flex shrink-0 items-center justify-center text-[var(--as-fg)]',\n className,\n )}\n style={{ width: size, height: size, ...style }}\n {...props}\n >\n {path ? (\n <svg\n viewBox=\"0 0 24 24\"\n width={size}\n height={size}\n fill=\"currentColor\"\n focusable=\"false\"\n >\n <path d={path} />\n </svg>\n ) : (\n <span\n className=\"flex h-full w-full items-center justify-center rounded-full border border-[var(--as-border)] font-semibold text-[var(--as-muted-fg)]\"\n style={{ fontSize: Math.max(8, Math.round(size / 2)) }}\n >\n {preset.charAt(0).toUpperCase()}\n </span>\n )}\n </span>\n )\n },\n)\n"]}
|
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
import { cn } from './chunk-RVVXVTH3.js';
|
|
2
|
+
import * as React from 'react';
|
|
3
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
4
|
+
|
|
5
|
+
var SwitchRow = React.forwardRef(
|
|
6
|
+
function SwitchRow2({
|
|
7
|
+
label,
|
|
8
|
+
checked,
|
|
9
|
+
onCheckedChange,
|
|
10
|
+
currentValue,
|
|
11
|
+
disabled = false,
|
|
12
|
+
className,
|
|
13
|
+
onClick,
|
|
14
|
+
...props
|
|
15
|
+
}, ref) {
|
|
16
|
+
return /* @__PURE__ */ jsxs(
|
|
17
|
+
"button",
|
|
18
|
+
{
|
|
19
|
+
ref,
|
|
20
|
+
type: "button",
|
|
21
|
+
role: "switch",
|
|
22
|
+
"aria-checked": checked,
|
|
23
|
+
disabled,
|
|
24
|
+
"data-as": "switch-row",
|
|
25
|
+
"data-state": checked ? "checked" : "unchecked",
|
|
26
|
+
onClick: (event) => {
|
|
27
|
+
onClick?.(event);
|
|
28
|
+
if (event.defaultPrevented) return;
|
|
29
|
+
onCheckedChange(!checked);
|
|
30
|
+
},
|
|
31
|
+
className: cn(
|
|
32
|
+
"flex w-full cursor-pointer items-center justify-between gap-3 rounded-[var(--as-radius)] border border-[var(--as-border)] bg-[var(--as-surface)] px-3 py-2 text-left text-sm text-[var(--as-fg)] transition-colors hover:bg-[var(--as-muted)] focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)] disabled:pointer-events-none disabled:opacity-50",
|
|
33
|
+
className
|
|
34
|
+
),
|
|
35
|
+
...props,
|
|
36
|
+
children: [
|
|
37
|
+
/* @__PURE__ */ jsxs("span", { className: "flex min-w-0 flex-col gap-0.5", children: [
|
|
38
|
+
/* @__PURE__ */ jsx("span", { className: "truncate font-medium", children: label }),
|
|
39
|
+
currentValue != null && currentValue !== "" ? /* @__PURE__ */ jsx("span", { className: "truncate text-xs text-[var(--as-muted-fg)]", children: currentValue }) : null
|
|
40
|
+
] }),
|
|
41
|
+
/* @__PURE__ */ jsx(
|
|
42
|
+
"span",
|
|
43
|
+
{
|
|
44
|
+
"aria-hidden": "true",
|
|
45
|
+
className: cn(
|
|
46
|
+
"relative h-5 w-9 shrink-0 rounded-full transition-colors duration-150",
|
|
47
|
+
checked ? "bg-[var(--as-primary)]" : "bg-[var(--as-border)]"
|
|
48
|
+
),
|
|
49
|
+
children: /* @__PURE__ */ jsx(
|
|
50
|
+
"span",
|
|
51
|
+
{
|
|
52
|
+
className: cn(
|
|
53
|
+
"absolute top-0.5 h-4 w-4 rounded-full bg-[var(--as-surface-raised)] shadow transition-all duration-150",
|
|
54
|
+
checked ? "left-[1.125rem]" : "left-0.5"
|
|
55
|
+
)
|
|
56
|
+
}
|
|
57
|
+
)
|
|
58
|
+
}
|
|
59
|
+
)
|
|
60
|
+
]
|
|
61
|
+
}
|
|
62
|
+
);
|
|
63
|
+
}
|
|
64
|
+
);
|
|
65
|
+
|
|
66
|
+
export { SwitchRow };
|
|
67
|
+
//# sourceMappingURL=chunk-FQXVZVA5.js.map
|
|
68
|
+
//# sourceMappingURL=chunk-FQXVZVA5.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/components/switch-row/SwitchRow.tsx"],"names":["SwitchRow"],"mappings":";;;;AAmBO,IAAM,SAAA,GAAkB,KAAA,CAAA,UAAA;AAAA,EAC7B,SAASA,UAAAA,CACP;AAAA,IACE,KAAA;AAAA,IACA,OAAA;AAAA,IACA,eAAA;AAAA,IACA,YAAA;AAAA,IACA,QAAA,GAAW,KAAA;AAAA,IACX,SAAA;AAAA,IACA,OAAA;AAAA,IACA,GAAG;AAAA,KAEL,GAAA,EACA;AACA,IAAA,uBACE,IAAA;AAAA,MAAC,QAAA;AAAA,MAAA;AAAA,QACC,GAAA;AAAA,QACA,IAAA,EAAK,QAAA;AAAA,QACL,IAAA,EAAK,QAAA;AAAA,QACL,cAAA,EAAc,OAAA;AAAA,QACd,QAAA;AAAA,QACA,SAAA,EAAQ,YAAA;AAAA,QACR,YAAA,EAAY,UAAU,SAAA,GAAY,WAAA;AAAA,QAClC,OAAA,EAAS,CAAC,KAAA,KAAU;AAClB,UAAA,OAAA,GAAU,KAAK,CAAA;AACf,UAAA,IAAI,MAAM,gBAAA,EAAkB;AAC5B,UAAA,eAAA,CAAgB,CAAC,OAAO,CAAA;AAAA,QAC1B,CAAA;AAAA,QACA,SAAA,EAAW,EAAA;AAAA,UACT,oYAAA;AAAA,UACA;AAAA,SACF;AAAA,QACC,GAAG,KAAA;AAAA,QAEJ,QAAA,EAAA;AAAA,0BAAA,IAAA,CAAC,MAAA,EAAA,EAAK,WAAU,+BAAA,EACd,QAAA,EAAA;AAAA,4BAAA,GAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,sBAAA,EAAwB,QAAA,EAAA,KAAA,EAAM,CAAA;AAAA,YAC7C,YAAA,IAAgB,QAAQ,YAAA,KAAiB,EAAA,uBACvC,MAAA,EAAA,EAAK,SAAA,EAAU,4CAAA,EACb,QAAA,EAAA,YAAA,EACH,CAAA,GACE;AAAA,WAAA,EACN,CAAA;AAAA,0BACA,GAAA;AAAA,YAAC,MAAA;AAAA,YAAA;AAAA,cACC,aAAA,EAAY,MAAA;AAAA,cACZ,SAAA,EAAW,EAAA;AAAA,gBACT,uEAAA;AAAA,gBACA,UAAU,wBAAA,GAA2B;AAAA,eACvC;AAAA,cAEA,QAAA,kBAAA,GAAA;AAAA,gBAAC,MAAA;AAAA,gBAAA;AAAA,kBACC,SAAA,EAAW,EAAA;AAAA,oBACT,wGAAA;AAAA,oBACA,UAAU,iBAAA,GAAoB;AAAA;AAChC;AAAA;AACF;AAAA;AACF;AAAA;AAAA,KACF;AAAA,EAEJ;AACF","file":"chunk-FQXVZVA5.js","sourcesContent":["import * as React from 'react'\nimport { cn } from '../../lib/utils'\n\nexport interface SwitchRowProps\n extends Omit<React.ComponentProps<'button'>, 'onChange'> {\n /** Visible row label — doubles as the switch's accessible name. */\n label: React.ReactNode\n /** Controlled on/off state. */\n checked: boolean\n /** Controlled toggle. */\n onCheckedChange: (checked: boolean) => void\n /** Sub-line under the label — apps pass the current value (\"now: gpt-5\"). */\n currentValue?: React.ReactNode\n disabled?: boolean\n}\n\n/** Labeled `role=\"switch\"` row with an animated knob — the standalone\n * settings toggle the family's setup surfaces (desktop/study/health)\n * previously hand-rolled. */\nexport const SwitchRow = React.forwardRef<HTMLButtonElement, SwitchRowProps>(\n function SwitchRow(\n {\n label,\n checked,\n onCheckedChange,\n currentValue,\n disabled = false,\n className,\n onClick,\n ...props\n },\n ref,\n ) {\n return (\n <button\n ref={ref}\n type=\"button\"\n role=\"switch\"\n aria-checked={checked}\n disabled={disabled}\n data-as=\"switch-row\"\n data-state={checked ? 'checked' : 'unchecked'}\n onClick={(event) => {\n onClick?.(event)\n if (event.defaultPrevented) return\n onCheckedChange(!checked)\n }}\n className={cn(\n 'flex w-full cursor-pointer items-center justify-between gap-3 rounded-[var(--as-radius)] border border-[var(--as-border)] bg-[var(--as-surface)] px-3 py-2 text-left text-sm text-[var(--as-fg)] transition-colors hover:bg-[var(--as-muted)] focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)] disabled:pointer-events-none disabled:opacity-50',\n className,\n )}\n {...props}\n >\n <span className=\"flex min-w-0 flex-col gap-0.5\">\n <span className=\"truncate font-medium\">{label}</span>\n {currentValue != null && currentValue !== '' ? (\n <span className=\"truncate text-xs text-[var(--as-muted-fg)]\">\n {currentValue}\n </span>\n ) : null}\n </span>\n <span\n aria-hidden=\"true\"\n className={cn(\n 'relative h-5 w-9 shrink-0 rounded-full transition-colors duration-150',\n checked ? 'bg-[var(--as-primary)]' : 'bg-[var(--as-border)]',\n )}\n >\n <span\n className={cn(\n 'absolute top-0.5 h-4 w-4 rounded-full bg-[var(--as-surface-raised)] shadow transition-all duration-150',\n checked ? 'left-[1.125rem]' : 'left-0.5',\n )}\n />\n </span>\n </button>\n )\n },\n)\n"]}
|
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
import { SwitchRow } from './chunk-FQXVZVA5.js';
|
|
2
|
+
import { cn } from './chunk-RVVXVTH3.js';
|
|
3
|
+
import * as React from 'react';
|
|
4
|
+
import { Scale, Database, Volume2, Mic, Wrench, Eye, Type, Check } from 'lucide-react';
|
|
5
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
6
|
+
|
|
7
|
+
var DEFAULT_CAP_ICONS = {
|
|
8
|
+
text: Type,
|
|
9
|
+
vision: Eye,
|
|
10
|
+
tools: Wrench,
|
|
11
|
+
stt: Mic,
|
|
12
|
+
tts: Volume2,
|
|
13
|
+
embeddings: Database,
|
|
14
|
+
decision: Scale
|
|
15
|
+
};
|
|
16
|
+
var SetupReview = React.forwardRef(
|
|
17
|
+
function SetupReview2({
|
|
18
|
+
models,
|
|
19
|
+
slots,
|
|
20
|
+
onOptionsChange,
|
|
21
|
+
capIcons,
|
|
22
|
+
modelsLabel = "Models to save",
|
|
23
|
+
footnote = "Existing assignments and models are never removed.",
|
|
24
|
+
className,
|
|
25
|
+
...props
|
|
26
|
+
}, ref) {
|
|
27
|
+
const icons = { ...DEFAULT_CAP_ICONS, ...capIcons };
|
|
28
|
+
const body = (curatedIds, slotOverrides = {}) => ({
|
|
29
|
+
curatedIds,
|
|
30
|
+
bindChat: slotOverrides.bindChat ?? slots.some((slot) => slot.optionsKey === "bindChat" && slot.bind),
|
|
31
|
+
bindVision: slotOverrides.bindVision ?? slots.some((slot) => slot.optionsKey === "bindVision" && slot.bind),
|
|
32
|
+
bindStt: slotOverrides.bindStt ?? slots.some((slot) => slot.optionsKey === "bindStt" && slot.bind),
|
|
33
|
+
bindDecision: slotOverrides.bindDecision ?? slots.some((slot) => slot.optionsKey === "bindDecision" && slot.bind)
|
|
34
|
+
});
|
|
35
|
+
const toggleModel = (id) => {
|
|
36
|
+
const next = models.filter(
|
|
37
|
+
(model) => model.selected !== (model.id === id)
|
|
38
|
+
);
|
|
39
|
+
onOptionsChange(body(next.map((model) => model.id)));
|
|
40
|
+
};
|
|
41
|
+
const toggleSlot = (slot) => {
|
|
42
|
+
onOptionsChange(
|
|
43
|
+
body(
|
|
44
|
+
models.filter((model) => model.selected).map((model) => model.id),
|
|
45
|
+
{ [slot.optionsKey]: !slot.bind }
|
|
46
|
+
)
|
|
47
|
+
);
|
|
48
|
+
};
|
|
49
|
+
return /* @__PURE__ */ jsxs(
|
|
50
|
+
"div",
|
|
51
|
+
{
|
|
52
|
+
ref,
|
|
53
|
+
"data-as": "setup-review",
|
|
54
|
+
className: cn("flex w-full flex-col gap-4", className),
|
|
55
|
+
...props,
|
|
56
|
+
children: [
|
|
57
|
+
models.length > 0 ? /* @__PURE__ */ jsx(
|
|
58
|
+
"div",
|
|
59
|
+
{
|
|
60
|
+
role: "group",
|
|
61
|
+
"aria-label": modelsLabel,
|
|
62
|
+
className: "grid grid-cols-1 gap-2 sm:grid-cols-2",
|
|
63
|
+
children: models.map((model) => {
|
|
64
|
+
const selected = model.selected;
|
|
65
|
+
const caps = model.caps ?? [];
|
|
66
|
+
return /* @__PURE__ */ jsxs(
|
|
67
|
+
"button",
|
|
68
|
+
{
|
|
69
|
+
type: "button",
|
|
70
|
+
"aria-pressed": selected,
|
|
71
|
+
"data-model-id": model.id,
|
|
72
|
+
onClick: () => toggleModel(model.id),
|
|
73
|
+
className: cn(
|
|
74
|
+
"flex cursor-pointer items-center justify-between gap-2 rounded-[var(--as-radius)] border px-3 py-2 text-left text-sm text-[var(--as-fg)] transition-colors focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)]",
|
|
75
|
+
selected ? "border-[var(--as-focus-ring)] bg-[var(--as-muted)]" : "border-[var(--as-border)] opacity-70 hover:opacity-100"
|
|
76
|
+
),
|
|
77
|
+
children: [
|
|
78
|
+
/* @__PURE__ */ jsxs("span", { className: "flex min-w-0 flex-col gap-1", children: [
|
|
79
|
+
/* @__PURE__ */ jsx("span", { className: "truncate font-medium", children: model.name }),
|
|
80
|
+
caps.length > 0 ? /* @__PURE__ */ jsx("span", { className: "flex items-center gap-2 text-xs text-[var(--as-muted-fg)]", children: caps.map((cap) => {
|
|
81
|
+
const Icon = icons[cap];
|
|
82
|
+
return Icon ? /* @__PURE__ */ jsx(Icon, { className: "size-3.5", "aria-hidden": true }, cap) : null;
|
|
83
|
+
}) }) : null
|
|
84
|
+
] }),
|
|
85
|
+
selected ? /* @__PURE__ */ jsx(Check, { className: "size-4 shrink-0", "aria-hidden": true }) : null
|
|
86
|
+
]
|
|
87
|
+
},
|
|
88
|
+
model.id
|
|
89
|
+
);
|
|
90
|
+
})
|
|
91
|
+
}
|
|
92
|
+
) : null,
|
|
93
|
+
slots.length > 0 ? /* @__PURE__ */ jsx("div", { className: "flex flex-col gap-2", children: slots.map((slot) => /* @__PURE__ */ jsx(
|
|
94
|
+
SwitchRow,
|
|
95
|
+
{
|
|
96
|
+
label: slot.label,
|
|
97
|
+
checked: slot.bind,
|
|
98
|
+
currentValue: slot.currentValue,
|
|
99
|
+
onCheckedChange: () => toggleSlot(slot)
|
|
100
|
+
},
|
|
101
|
+
slot.id
|
|
102
|
+
)) }) : null,
|
|
103
|
+
/* @__PURE__ */ jsx("p", { className: "text-xs text-[var(--as-muted-fg)]", children: footnote })
|
|
104
|
+
]
|
|
105
|
+
}
|
|
106
|
+
);
|
|
107
|
+
}
|
|
108
|
+
);
|
|
109
|
+
|
|
110
|
+
export { SetupReview };
|
|
111
|
+
//# sourceMappingURL=chunk-FY3NCPFO.js.map
|
|
112
|
+
//# sourceMappingURL=chunk-FY3NCPFO.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/components/setup-review/SetupReview.tsx"],"names":["SetupReview"],"mappings":"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","file":"chunk-FY3NCPFO.js","sourcesContent":["import * as React from 'react'\nimport {\n Check,\n Database,\n Eye,\n Mic,\n Scale,\n Type,\n Volume2,\n Wrench,\n type LucideIcon,\n} from 'lucide-react'\nimport { cn } from '../../lib/utils'\nimport { SwitchRow } from '../switch-row/SwitchRow'\n\n/** One curated model card (capability icons render from `caps`). */\nexport interface SetupReviewModel {\n id: string\n name: string\n caps?: string[]\n selected: boolean\n}\n\n/** The five-bind option keys of the §15 options body (camelCase — desktop\n * IPC; Python apps convert to snake_case app-side). */\nexport type SetupReviewOptionsKey =\n | 'bindChat'\n | 'bindVision'\n | 'bindStt'\n | 'bindDecision'\n\n/** One gap-fill switch. Pass one slot per `optionsKey` — chat presets show\n * text/vision/stt slots, decision-only presets show the decision slot only;\n * the current value of every slot the bind would fill rides `currentValue`. */\nexport interface SetupReviewSlot {\n id: string\n label: string\n bind: boolean\n currentValue?: string\n optionsKey: SetupReviewOptionsKey\n}\n\n/** The options body a setup run carries (plan 26 D14) — `curatedIds` in the\n * order the cards are given, one bind flag per capability group. */\nexport interface SetupReviewOptions {\n curatedIds: string[]\n bindChat: boolean\n bindVision: boolean\n bindStt: boolean\n bindDecision: boolean\n}\n\nconst DEFAULT_CAP_ICONS: Record<string, LucideIcon> = {\n text: Type,\n vision: Eye,\n tools: Wrench,\n stt: Mic,\n tts: Volume2,\n embeddings: Database,\n decision: Scale,\n}\n\nexport interface SetupReviewProps extends React.ComponentProps<'div'> {\n models: SetupReviewModel[]\n slots: SetupReviewSlot[]\n /** Emits the full options body on every card/switch edit — controlled:\n * feed the changed state back through `models`/`slots`. */\n onOptionsChange: (options: SetupReviewOptions) => void\n /** Per-capability icon override (capability string → icon). */\n capIcons?: Partial<Record<string, LucideIcon>>\n modelsLabel?: string\n footnote?: string\n}\n\n/** Editable pre-flight review (plan 26 §6): model-select cards with\n * capability icons plus gap-fill switch rows with `now:` sub-lines and the\n * never-removes footnote. Emits the five-bind options body\n * `{curatedIds, bindChat, bindVision, bindStt, bindDecision}` — append\n * semantics mean nothing existing is ever removed. */\nexport const SetupReview = React.forwardRef<HTMLDivElement, SetupReviewProps>(\n function SetupReview(\n {\n models,\n slots,\n onOptionsChange,\n capIcons,\n modelsLabel = 'Models to save',\n footnote = 'Existing assignments and models are never removed.',\n className,\n ...props\n },\n ref,\n ) {\n const icons = { ...DEFAULT_CAP_ICONS, ...capIcons }\n const body = (\n curatedIds: string[],\n slotOverrides: Partial<Record<SetupReviewOptionsKey, boolean>> = {},\n ): SetupReviewOptions => ({\n curatedIds,\n bindChat: slotOverrides.bindChat ?? slots.some((slot) => slot.optionsKey === 'bindChat' && slot.bind),\n bindVision: slotOverrides.bindVision ?? slots.some((slot) => slot.optionsKey === 'bindVision' && slot.bind),\n bindStt: slotOverrides.bindStt ?? slots.some((slot) => slot.optionsKey === 'bindStt' && slot.bind),\n bindDecision: slotOverrides.bindDecision ?? slots.some((slot) => slot.optionsKey === 'bindDecision' && slot.bind),\n })\n\n const toggleModel = (id: string): void => {\n const next = models.filter(\n (model) => model.selected !== (model.id === id),\n )\n onOptionsChange(body(next.map((model) => model.id)))\n }\n\n const toggleSlot = (slot: SetupReviewSlot): void => {\n onOptionsChange(\n body(\n models.filter((model) => model.selected).map((model) => model.id),\n { [slot.optionsKey]: !slot.bind },\n ),\n )\n }\n\n return (\n <div\n ref={ref}\n data-as=\"setup-review\"\n className={cn('flex w-full flex-col gap-4', className)}\n {...props}\n >\n {models.length > 0 ? (\n <div\n role=\"group\"\n aria-label={modelsLabel}\n className=\"grid grid-cols-1 gap-2 sm:grid-cols-2\"\n >\n {models.map((model) => {\n const selected = model.selected\n const caps = model.caps ?? []\n return (\n <button\n key={model.id}\n type=\"button\"\n aria-pressed={selected}\n data-model-id={model.id}\n onClick={() => toggleModel(model.id)}\n className={cn(\n 'flex cursor-pointer items-center justify-between gap-2 rounded-[var(--as-radius)] border px-3 py-2 text-left text-sm text-[var(--as-fg)] transition-colors focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-[var(--as-focus-ring)]',\n selected\n ? 'border-[var(--as-focus-ring)] bg-[var(--as-muted)]'\n : 'border-[var(--as-border)] opacity-70 hover:opacity-100',\n )}\n >\n <span className=\"flex min-w-0 flex-col gap-1\">\n <span className=\"truncate font-medium\">{model.name}</span>\n {caps.length > 0 ? (\n <span className=\"flex items-center gap-2 text-xs text-[var(--as-muted-fg)]\">\n {caps.map((cap) => {\n const Icon = icons[cap]\n return Icon ? (\n <Icon key={cap} className=\"size-3.5\" aria-hidden />\n ) : null\n })}\n </span>\n ) : null}\n </span>\n {selected ? (\n <Check className=\"size-4 shrink-0\" aria-hidden />\n ) : null}\n </button>\n )\n })}\n </div>\n ) : null}\n\n {slots.length > 0 ? (\n <div className=\"flex flex-col gap-2\">\n {slots.map((slot) => (\n <SwitchRow\n key={slot.id}\n label={slot.label}\n checked={slot.bind}\n currentValue={slot.currentValue}\n onCheckedChange={() => toggleSlot(slot)}\n />\n ))}\n </div>\n ) : null}\n\n <p className=\"text-xs text-[var(--as-muted-fg)]\">{footnote}</p>\n </div>\n )\n },\n)\n"]}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/components/capability-chips/CapabilityChips.tsx"],"names":["CapabilityChips"],"mappings":";;;;;AAsBO,IAAM,eAAA,GAAwB,KAAA,CAAA,UAAA;AAAA,EACnC,SAASA,gBAAAA,CACP;AAAA,IACE,IAAA;AAAA,IACA,QAAA;AAAA,IACA,QAAA;AAAA,IACA,OAAA,GAAU,QAAA;AAAA,IACV,WAAA,GAAc,CAAA;AAAA,IACd,QAAA,GAAW,KAAA;AAAA,IACX,SAAA;AAAA,IACA;AAAA,KAEF,GAAA,EACA;AACA,IAAA,MAAM,WAAA,GAAc,OAAA,KAAY,QAAA,IAAY,OAAA,CAAQ,QAAQ,CAAA;AAC5D,IAAA,MAAM,MAAA,GAAS,CAAC,KAAA,KACd,WAAA,IAAe,CAAC,QAAA,IAAY,QAAA,CAAS,QAAA,CAAS,KAAK,CAAA,IAAK,QAAA,CAAS,MAAA,IAAU,WAAA;AAE7E,IAAA,uBACE,GAAA;AAAA,MAAC,KAAA;AAAA,MAAA;AAAA,QACC,GAAA;AAAA,QACA,SAAA,EAAQ,kBAAA;AAAA,QACR,cAAA,EAAc,OAAA;AAAA,QACd,IAAA,EAAM,cAAc,OAAA,GAAU,MAAA;AAAA,QAC9B,YAAA,EAAY,cAAc,SAAA,GAAY,MAAA;AAAA,QACtC,SAAA,EAAW,EAAA,CAAG,qCAAA,EAAuC,SAAS,CAAA;AAAA,QAE7D,QAAA,EAAA,IAAA,CAAK,GAAA,CAAI,CAAC,GAAA,KAAQ;AACjB,UAAA,MAAM,EAAA,GAAK,QAAA,CAAS,QAAA,CAAS,GAAA,CAAI,KAAK,CAAA;AACtC,UAAA,MAAM,OAAO,GAAA,CAAI,IAAA;AACjB,UAAA,IAAI,CAAC,WAAA,EAAa;AAChB,YAAA,uBACE,IAAA;AAAA,cAAC,MAAA;AAAA,cAAA;AAAA,gBAEC,eAAa,GAAA,CAAI,KAAA;AAAA,gBACjB,eAAa,EAAA,IAAM,MAAA;AAAA,gBACnB,KAAA,EAAO,CAAA,EAAG,GAAA,CAAI,KAAK,CAAA,WAAA,CAAA;AAAA,gBACnB,SAAA,EAAW,EAAA;AAAA,kBACT,8HAAA;AAAA,kBACA,KACI,oDAAA,GACA;AAAA,iBACN;AAAA,gBAEC,QAAA,EAAA;AAAA,kBAAA,IAAA,uBAAQ,IAAA,EAAA,EAAK,SAAA,EAAU,UAAA,EAAW,aAAA,EAAW,MAAC,CAAA,GAAK,IAAA;AAAA,kBACnD,GAAA,CAAI;AAAA;AAAA,eAAA;AAAA,cAZA,GAAA,CAAI;AAAA,aAaX;AAAA,UAEJ;AACA,UAAA,uBACE,IAAA;AAAA,YAAC,QAAA;AAAA,YAAA;AAAA,cAEC,IAAA,EAAK,QAAA;AAAA,cACL,eAAa,GAAA,CAAI,KAAA;AAAA,cACjB,cAAA,EAAc,EAAA;AAAA,cACd,QAAA,EAAU,QAAA,IAAY,MAAA,CAAO,GAAA,CAAI,KAAK,CAAA;AAAA,cACtC,OAAA,EAAS,MAAM,QAAA,GAAW,GAAA,CAAI,KAAK,CAAA;AAAA,cACnC,SAAA,EAAW,EAAA;AAAA,gBACT,oJAAA;AAAA,gBACA,qGAAA;AAAA,gBACA,kDAAA;AAAA,gBACA,KACI,8GAAA,GACA;AAAA,eACN;AAAA,cAEC,QAAA,EAAA;AAAA,gBAAA,IAAA,uBAAQ,IAAA,EAAA,EAAK,SAAA,EAAU,UAAA,EAAW,aAAA,EAAW,MAAC,CAAA,GAAK,IAAA;AAAA,gBACnD,GAAA,CAAI,KAAA;AAAA,gBACJ,qBAAK,GAAA,CAAC,KAAA,EAAA,EAAM,WAAU,QAAA,EAAS,aAAA,EAAW,MAAC,CAAA,GAAK;AAAA;AAAA,aAAA;AAAA,YAjB5C,GAAA,CAAI;AAAA,WAkBX;AAAA,QAEJ,CAAC;AAAA;AAAA,KACH;AAAA,EAEJ;AACF","file":"chunk-
|
|
1
|
+
{"version":3,"sources":["../src/components/capability-chips/CapabilityChips.tsx"],"names":["CapabilityChips"],"mappings":";;;;;AAsBO,IAAM,eAAA,GAAwB,KAAA,CAAA,UAAA;AAAA,EACnC,SAASA,gBAAAA,CACP;AAAA,IACE,IAAA;AAAA,IACA,QAAA;AAAA,IACA,QAAA;AAAA,IACA,OAAA,GAAU,QAAA;AAAA,IACV,WAAA,GAAc,CAAA;AAAA,IACd,QAAA,GAAW,KAAA;AAAA,IACX,SAAA;AAAA,IACA;AAAA,KAEF,GAAA,EACA;AACA,IAAA,MAAM,WAAA,GAAc,OAAA,KAAY,QAAA,IAAY,OAAA,CAAQ,QAAQ,CAAA;AAC5D,IAAA,MAAM,MAAA,GAAS,CAAC,KAAA,KACd,WAAA,IAAe,CAAC,QAAA,IAAY,QAAA,CAAS,QAAA,CAAS,KAAK,CAAA,IAAK,QAAA,CAAS,MAAA,IAAU,WAAA;AAE7E,IAAA,uBACE,GAAA;AAAA,MAAC,KAAA;AAAA,MAAA;AAAA,QACC,GAAA;AAAA,QACA,SAAA,EAAQ,kBAAA;AAAA,QACR,cAAA,EAAc,OAAA;AAAA,QACd,IAAA,EAAM,cAAc,OAAA,GAAU,MAAA;AAAA,QAC9B,YAAA,EAAY,cAAc,SAAA,GAAY,MAAA;AAAA,QACtC,SAAA,EAAW,EAAA,CAAG,qCAAA,EAAuC,SAAS,CAAA;AAAA,QAE7D,QAAA,EAAA,IAAA,CAAK,GAAA,CAAI,CAAC,GAAA,KAAQ;AACjB,UAAA,MAAM,EAAA,GAAK,QAAA,CAAS,QAAA,CAAS,GAAA,CAAI,KAAK,CAAA;AACtC,UAAA,MAAM,OAAO,GAAA,CAAI,IAAA;AACjB,UAAA,IAAI,CAAC,WAAA,EAAa;AAChB,YAAA,uBACE,IAAA;AAAA,cAAC,MAAA;AAAA,cAAA;AAAA,gBAEC,eAAa,GAAA,CAAI,KAAA;AAAA,gBACjB,eAAa,EAAA,IAAM,MAAA;AAAA,gBACnB,KAAA,EAAO,CAAA,EAAG,GAAA,CAAI,KAAK,CAAA,WAAA,CAAA;AAAA,gBACnB,SAAA,EAAW,EAAA;AAAA,kBACT,8HAAA;AAAA,kBACA,KACI,oDAAA,GACA;AAAA,iBACN;AAAA,gBAEC,QAAA,EAAA;AAAA,kBAAA,IAAA,uBAAQ,IAAA,EAAA,EAAK,SAAA,EAAU,UAAA,EAAW,aAAA,EAAW,MAAC,CAAA,GAAK,IAAA;AAAA,kBACnD,GAAA,CAAI;AAAA;AAAA,eAAA;AAAA,cAZA,GAAA,CAAI;AAAA,aAaX;AAAA,UAEJ;AACA,UAAA,uBACE,IAAA;AAAA,YAAC,QAAA;AAAA,YAAA;AAAA,cAEC,IAAA,EAAK,QAAA;AAAA,cACL,eAAa,GAAA,CAAI,KAAA;AAAA,cACjB,cAAA,EAAc,EAAA;AAAA,cACd,QAAA,EAAU,QAAA,IAAY,MAAA,CAAO,GAAA,CAAI,KAAK,CAAA;AAAA,cACtC,OAAA,EAAS,MAAM,QAAA,GAAW,GAAA,CAAI,KAAK,CAAA;AAAA,cACnC,SAAA,EAAW,EAAA;AAAA,gBACT,oJAAA;AAAA,gBACA,qGAAA;AAAA,gBACA,kDAAA;AAAA,gBACA,KACI,8GAAA,GACA;AAAA,eACN;AAAA,cAEC,QAAA,EAAA;AAAA,gBAAA,IAAA,uBAAQ,IAAA,EAAA,EAAK,SAAA,EAAU,UAAA,EAAW,aAAA,EAAW,MAAC,CAAA,GAAK,IAAA;AAAA,gBACnD,GAAA,CAAI,KAAA;AAAA,gBACJ,qBAAK,GAAA,CAAC,KAAA,EAAA,EAAM,WAAU,QAAA,EAAS,aAAA,EAAW,MAAC,CAAA,GAAK;AAAA;AAAA,aAAA;AAAA,YAjB5C,GAAA,CAAI;AAAA,WAkBX;AAAA,QAEJ,CAAC;AAAA;AAAA,KACH;AAAA,EAEJ;AACF","file":"chunk-H5KOC7Z5.js","sourcesContent":["import * as React from 'react'\nimport { Check } from 'lucide-react'\nimport type { LucideIcon } from 'lucide-react'\nimport { cn } from '../../lib/utils'\n\nexport interface CapabilityDescriptor {\n value: string\n label: string\n icon?: LucideIcon\n}\n\nexport interface CapabilityChipsProps {\n caps: CapabilityDescriptor[]\n selected: string[]\n onToggle?: (value: string) => void\n variant?: 'toggle' | 'badge'\n minSelected?: number\n disabled?: boolean\n ariaLabel?: string\n className?: string\n}\n\nexport const CapabilityChips = React.forwardRef<HTMLDivElement, CapabilityChipsProps>(\n function CapabilityChips(\n {\n caps,\n selected,\n onToggle,\n variant = 'toggle',\n minSelected = 0,\n disabled = false,\n ariaLabel,\n className,\n },\n ref,\n ) {\n const interactive = variant === 'toggle' && Boolean(onToggle)\n const locked = (value: string) =>\n interactive && !disabled && selected.includes(value) && selected.length <= minSelected\n\n return (\n <div\n ref={ref}\n data-as=\"capability-chips\"\n data-variant={variant}\n role={interactive ? 'group' : undefined}\n aria-label={interactive ? ariaLabel : undefined}\n className={cn('flex flex-wrap items-center gap-1.5', className)}\n >\n {caps.map((cap) => {\n const on = selected.includes(cap.value)\n const Icon = cap.icon\n if (!interactive) {\n return (\n <span\n key={cap.value}\n data-as-cap={cap.value}\n data-active={on || undefined}\n title={`${cap.label} capability`}\n className={cn(\n 'inline-flex items-center gap-1 rounded-[var(--as-radius-sm)] px-1.5 py-0.5 text-[10px] font-semibold uppercase tracking-wide',\n on\n ? 'bg-[var(--as-primary)]/10 text-[var(--as-primary)]'\n : 'bg-[var(--as-muted)] text-[var(--as-muted-fg)]',\n )}\n >\n {Icon ? <Icon className=\"size-2.5\" aria-hidden /> : null}\n {cap.label}\n </span>\n )\n }\n return (\n <button\n key={cap.value}\n type=\"button\"\n data-as-cap={cap.value}\n aria-pressed={on}\n disabled={disabled || locked(cap.value)}\n onClick={() => onToggle?.(cap.value)}\n className={cn(\n 'flex cursor-pointer items-center gap-1.5 rounded-[var(--as-radius)] border px-3 py-2 text-xs font-semibold uppercase tracking-wider transition-all',\n 'focus-visible:outline-2 focus-visible:outline-offset-1 focus-visible:outline-[var(--as-focus-ring)]',\n 'disabled:pointer-events-none disabled:opacity-60',\n on\n ? 'border-[var(--as-primary)]/30 bg-[var(--as-primary)]/10 text-[var(--as-primary)] shadow-[var(--as-shadow-1)]'\n : 'border-[var(--as-border)] bg-[var(--as-surface)] text-[var(--as-muted-fg)] hover:border-[var(--as-muted-fg)]/40',\n )}\n >\n {Icon ? <Icon className=\"size-3.5\" aria-hidden /> : null}\n {cap.label}\n {on ? <Check className=\"size-3\" aria-hidden /> : null}\n </button>\n )\n })}\n </div>\n )\n },\n)\n"]}
|