From e2122f22b89bd186a5458943af16275fe2fa973e Mon Sep 17 00:00:00 2001 From: Brooklyn Nicholson Date: Sat, 25 Jul 2026 20:37:09 -0500 Subject: [PATCH] fix(desktop): stop the model picker overriding the configured effort Selecting a model applied 'preset.effort ?? medium', so a user running agent.reasoning_effort: high was silently downgraded to medium on every model switch and every new chat that inherited the pick. The Thinking toggle and the effort radio group defaulted to the same literal. Resolve all of them from the profile default instead, falling back to DEFAULT_REASONING_EFFORT only when config has not loaded. --- .../src/app/shell/model-edit-submenu.tsx | 27 ++++++++++++------- .../src/app/shell/model-menu-panel.tsx | 6 +++-- 2 files changed, 21 insertions(+), 12 deletions(-) diff --git a/apps/desktop/src/app/shell/model-edit-submenu.tsx b/apps/desktop/src/app/shell/model-edit-submenu.tsx index 742ed304b65b..ab141d71744b 100644 --- a/apps/desktop/src/app/shell/model-edit-submenu.tsx +++ b/apps/desktop/src/app/shell/model-edit-submenu.tsx @@ -16,7 +16,13 @@ import { useI18n } from '@/i18n' import { normalize } from '@/lib/text' import { setModelPreset } from '@/store/model-presets' import { notifyError } from '@/store/notifications' -import { markComposerSelectionManual, setCurrentFastMode, setCurrentReasoningEffort } from '@/store/session' +import { + $defaultReasoningEffort, + DEFAULT_REASONING_EFFORT, + markComposerSelectionManual, + setCurrentFastMode, + setCurrentReasoningEffort +} from '@/store/session' import { sessionTileDelegate } from '@/store/session-states' // Hermes' real reasoning levels (see VALID_REASONING_EFFORTS); `none` is owned @@ -111,8 +117,9 @@ export function ModelEditSubmenu({ const activeSessionId = useStore(view.$runtimeId) const touchesPrimary = view.kind === 'primary' - const effortValue = normalizeEffort(effort) - const thinkingOn = isThinkingEnabled(effort) + const defaultEffort = useStore($defaultReasoningEffort) || DEFAULT_REASONING_EFFORT + const effortValue = normalizeEffort(effort, defaultEffort) + const thinkingOn = isThinkingEnabled(effort, defaultEffort) // Editing always records the model's global preset (keyed by provider::model, // not per-surface — a tile edit re-applies to that model everywhere); the @@ -224,7 +231,7 @@ export function ModelEditSubmenu({ void patchReasoning(checked ? effortValue || 'medium' : 'none')} + onCheckedChange={checked => void patchReasoning(checked ? effortValue || defaultEffort : 'none')} size="xs" /> @@ -259,18 +266,18 @@ export function ModelEditSubmenu({ ) } -function isThinkingEnabled(effort: string): boolean { - // Empty = Hermes default (medium) = on; only an explicit "none" is off. - return normalize(effort || 'medium') !== 'none' +function isThinkingEnabled(effort: string, fallback: string): boolean { + // Empty = the profile default = on; only an explicit "none" is off. + return normalize(effort || fallback) !== 'none' } -function normalizeEffort(effort: string): string { - const value = normalize(effort || 'medium') +function normalizeEffort(effort: string, fallback: string): string { + const value = normalize(effort || fallback) // Thinking off → no effort selected in the radio group. if (value === 'none') { return '' } - return EFFORT_OPTIONS.some(option => option.value === value) ? value : 'medium' + return EFFORT_OPTIONS.some(option => option.value === value) ? value : DEFAULT_REASONING_EFFORT } diff --git a/apps/desktop/src/app/shell/model-menu-panel.tsx b/apps/desktop/src/app/shell/model-menu-panel.tsx index 9c3c60e5cdaf..6affa652c84e 100644 --- a/apps/desktop/src/app/shell/model-menu-panel.tsx +++ b/apps/desktop/src/app/shell/model-menu-panel.tsx @@ -39,6 +39,7 @@ import { setModelVisibilityOpen } from '@/store/model-visibility' import { $collapsedProviders, toggleCollapsedProvider } from '@/store/provider-collapse' +import { $defaultReasoningEffort, DEFAULT_REASONING_EFFORT } from '@/store/session' import type { ModelOptionProvider, ModelOptionsResponse } from '@/types/hermes' import { ModelEditSubmenu, resolveFastControl } from './model-edit-submenu' @@ -84,6 +85,7 @@ export function ModelMenuPanel({ gateway, onSelectModel, profile = 'default', re const currentProvider = useStore(view.$provider) const currentReasoningEffort = useStore(view.$reasoningEffort) const modelPresets = useStore($modelPresets) + const defaultEffort = useStore($defaultReasoningEffort) || DEFAULT_REASONING_EFFORT const visibleModels = useStore($visibleModels) const collapsedProviders = useStore($collapsedProviders) @@ -181,7 +183,7 @@ export function ModelMenuPanel({ gateway, onSelectModel, profile = 'default', re await applyModelPreset( { - effort: (caps?.reasoning ?? true) ? (preset.effort ?? 'medium') : undefined, + effort: (caps?.reasoning ?? true) ? (preset.effort ?? defaultEffort) : undefined, fast: (caps?.fast ?? false) ? (preset.fast ?? false) : undefined }, { @@ -300,7 +302,7 @@ export function ModelMenuPanel({ gateway, onSelectModel, profile = 'default', re const meta = [ fastControl.kind !== 'none' && fastControl.on ? copy.fast : null, - (caps?.reasoning ?? true) ? reasoningEffortLabel(effEffort) || copy.medium : null + (caps?.reasoning ?? true) ? reasoningEffortLabel(effEffort || defaultEffort) : null ] .filter(Boolean) .join(' ')