import { useState } from "react"; import { deleteAiEndpoint, saveAiEndpoint } from "~/fns/ai-endpoints"; import { useAction } from "~/hooks/use-action"; import { Panel } from "~/ui/Panel"; import { Button } from "~/ui/Button"; import { SelectField, TextField } from "~/ui/Field"; import { ErrorBanner } from "~/ui/Callout"; type Kind = "provider" | "openai" | "cf-gateway"; export type AiEndpointSummaryView = { kind: Kind; provider: string | null; model: string; baseUrl: string | null; cfAccountId: string | null; cfGatewayId: string | null; }; export type AiEndpointTarget = | { scope: "repo"; owner: string; repo: string } | { scope: "account"; org: string | null }; const KIND_LABELS: Record = { provider: "Provider key (through this instance's AI Gateway)", openai: "OpenAI-compatible endpoint", "cf-gateway": "My Cloudflare AI Gateway", }; function describe(endpoint: AiEndpointSummaryView): string { if (endpoint.kind === "openai") return `${endpoint.model} at ${endpoint.baseUrl}`; if (endpoint.kind === "cf-gateway") return `${endpoint.provider}/${endpoint.model} via gateway ${endpoint.cfGatewayId}`; return `${endpoint.provider}/${endpoint.model}`; } /** Bring-your-own AI endpoint for an account or a repository. The saved key is never shown again. */ export function AiEndpointForm({ title, target, endpoint, providers, fallback, }: { title: string; target: AiEndpointTarget; endpoint: AiEndpointSummaryView | null; providers: readonly string[]; fallback: string; }) { const save = useAction(saveAiEndpoint); const remove = useAction(deleteAiEndpoint); const [kind, setKind] = useState(endpoint?.kind ?? "provider"); const [provider, setProvider] = useState(endpoint?.provider ?? providers[0] ?? "openai"); const [model, setModel] = useState(endpoint?.model ?? ""); const [baseUrl, setBaseUrl] = useState(endpoint?.baseUrl ?? ""); const [cfAccountId, setCfAccountId] = useState(endpoint?.cfAccountId ?? ""); const [cfGatewayId, setCfGatewayId] = useState(endpoint?.cfGatewayId ?? ""); const [apiKey, setApiKey] = useState(""); return (
{ event.preventDefault(); const saved = await save.run({ data: { target, kind, provider, model, baseUrl, cfAccountId, cfGatewayId, apiKey }, }); if (saved) setApiKey(""); }} >

{endpoint ? `Using ${describe(endpoint)}. Calls with your own endpoint are recorded but never count toward plan limits or prepaid credit.` : fallback}

({ value, label: KIND_LABELS[value] }))} onValueChange={(value) => setKind(value as Kind)} />
{kind !== "openai" && ( ({ value, label: value }))} onValueChange={(value) => setProvider(value)} /> )} {kind === "openai" && ( setBaseUrl(event.target.value)} /> )} {kind === "cf-gateway" && ( <> setCfAccountId(event.target.value)} /> setCfGatewayId(event.target.value)} /> )} setModel(event.target.value)} /> setApiKey(event.target.value)} />
{endpoint && ( )}
); }