diff --git a/app/[lang]/admin/page.tsx b/app/[lang]/admin/page.tsx index cf77222..af4a7ea 100644 --- a/app/[lang]/admin/page.tsx +++ b/app/[lang]/admin/page.tsx @@ -375,6 +375,11 @@ export default function AdminPage() { const [saveMessage, setSaveMessage] = useState("") const [justSaved, setJustSaved] = useState(false) const [activeGroup, setActiveGroup] = useState(SETTING_GROUPS[0].id) + // Toggleable groups (quota, observability): off by default, on when + // any of their fields is already configured + const [enabledGroups, setEnabledGroups] = useState>( + {}, + ) const mainRef = useRef(null) const dirtyCount = Object.keys(pending).length @@ -399,6 +404,20 @@ export default function AdminPage() { const map: SettingsMap = {} for (const s of data.settings) map[s.key] = s setSettings(map) + // Turn a toggleable group on when any of its fields is set + setEnabledGroups((prev) => { + const next = { ...prev } + for (const group of SETTING_GROUPS) { + if (!group.toggleable) continue + const configured = SETTINGS_REGISTRY.some( + (d) => + d.group === group.id && + map[d.key]?.source !== "default", + ) + if (configured) next[group.id] = true + } + return next + }) }, [], ) @@ -688,22 +707,46 @@ export default function AdminPage() { const defs = SETTINGS_REGISTRY.filter( (d) => d.group === group.id, ) + const groupOff = + group.toggleable && !enabledGroups[group.id] + const fieldsDisabled = !writable || !!groupOff return (
-

- {group.title} -

+
+

+ {group.title} +

+ {group.toggleable && ( + + setEnabledGroups((prev) => ({ + ...prev, + [group.id]: checked, + })) + } + /> + )} +

{group.description}

-
+
{group.id === "providers" ? [...providerSubgroups.entries()].map( ([name, subDefs]) => ( @@ -728,7 +771,7 @@ export default function AdminPage() { pending[def.key] } error={errors[def.key]} - disabled={!writable} + disabled={fieldsDisabled} onChange={(v) => handleChange(def.key, v) } diff --git a/lib/admin/settings-registry.ts b/lib/admin/settings-registry.ts index 75ef165..16fb95f 100644 --- a/lib/admin/settings-registry.ts +++ b/lib/admin/settings-registry.ts @@ -34,6 +34,9 @@ export interface SettingGroup { id: string title: string description: string + // Optional sections gated by an on/off switch in the panel; fields are + // grayed out until enabled. Starts on when any field is already set. + toggleable?: boolean } export const SETTING_GROUPS: SettingGroup[] = [ @@ -58,12 +61,6 @@ export const SETTING_GROUPS: SettingGroup[] = [ title: "Access Control", description: "Restrict who can use this deployment.", }, - { - id: "quota", - title: "Quota & Rate Limits", - description: - "Per-IP usage limits. Enforcement requires a DynamoDB table.", - }, { id: "features", title: "Features", @@ -73,6 +70,14 @@ export const SETTING_GROUPS: SettingGroup[] = [ id: "observability", title: "Observability", description: "Langfuse tracing for LLM calls.", + toggleable: true, + }, + { + id: "quota", + title: "Quota & Rate Limits", + description: + "Per-IP usage limits. Enforcement requires a DynamoDB table.", + toggleable: true, }, ]