diff --git a/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigation.svelte b/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigation.svelte index 156229dc5b..7bd062b7ca 100644 --- a/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigation.svelte +++ b/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigation.svelte @@ -391,6 +391,7 @@ bind:searchQuery class="px-2" isExpandedMode={innerWidth > 768 ? uiStore.isSidebarExpanded : true} + onDiscoverModelsClick={() => (modelsHubOpen = true)} onNewChat={() => { if (deviceStore.isMobile) { scheduleMobileCollapse(); @@ -404,7 +405,6 @@ isSearchModeActive = false; searchQuery = ''; }} - onDiscoverModelsClick={() => (modelsHubOpen = true)} onSettingsClick={() => (settingsDialogOpen = true)} /> diff --git a/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigationActions.svelte b/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigationActions.svelte index d33ac57e97..2a6228423a 100644 --- a/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigationActions.svelte +++ b/tools/ui/src/lib/components/app/navigation/SidebarNavigation/SidebarNavigationActions.svelte @@ -34,8 +34,8 @@ class: className, isExpandedMode = false, isSearchModeActive = $bindable(false), - onNewChat, onDiscoverModelsClick, + onNewChat, onSearchClick, onSearchDeactivated, onSettingsClick, diff --git a/tools/ui/src/lib/enums/ui.enums.ts b/tools/ui/src/lib/enums/ui.enums.ts index 2d70478cc3..036dacee18 100644 --- a/tools/ui/src/lib/enums/ui.enums.ts +++ b/tools/ui/src/lib/enums/ui.enums.ts @@ -23,8 +23,8 @@ export enum ScrollCarouselVariant { * Sidebar icon strip actions handled directly by the sidebar. */ export enum SidebarAction { - NEW_CHAT = 'new-chat', DISCOVER_MODELS = 'discover-models', + NEW_CHAT = 'new-chat', SETTINGS = 'settings' } diff --git a/tools/ui/src/lib/hooks/use-model-params-fallback.svelte.ts b/tools/ui/src/lib/hooks/use-model-params-fallback.svelte.ts index 7d79fc9239..d8dc75badc 100644 --- a/tools/ui/src/lib/hooks/use-model-params-fallback.svelte.ts +++ b/tools/ui/src/lib/hooks/use-model-params-fallback.svelte.ts @@ -38,6 +38,7 @@ export function useModelParamsFallback(opts: UseModelParamsFallbackOptions) { return normalized.includes(MODEL_ID.ORG_SEPARATOR) ? normalized : null; }); + let fetchedParams = $state(null); $effect(() => { diff --git a/tools/ui/src/lib/services/models.service.ts b/tools/ui/src/lib/services/models.service.ts index 3157d9145b..b2637bcde3 100644 --- a/tools/ui/src/lib/services/models.service.ts +++ b/tools/ui/src/lib/services/models.service.ts @@ -29,23 +29,6 @@ const SIDECAR_TOKENS: readonly string[] = [ export class ModelsService { private static readonly SSE_RECONNECT_MS = 1000; - /** - * True when a router entry id is a sidecar-only entry, e.g. `org/model:Q4_0-mtp` - * or `org/model:mmproj`. Such entries mark a downloaded sidecar file, not a - * loadable model, so the selector skips them. - */ - static isSidecarEntry(modelId: string): boolean { - const idx = modelId.indexOf(MODEL_ID.QUANTIZATION_SEPARATOR); - - if (idx === MODEL_ID.NOT_FOUND) return false; - - const tag = modelId.slice(idx + 1).toLowerCase(); - const dash = tag.lastIndexOf(MODEL_ID.SEGMENT_SEPARATOR); - const token = dash === -1 ? tag : tag.slice(dash + 1); - - return SIDECAR_TOKENS.includes(token); - } - /** * Build the `:` string expected by POST /models from a parsed * filename quant + optional sidecar type. Used by the model download @@ -121,6 +104,16 @@ export class ModelsService { return model.status.value === ServerModelStatus.LOADED; } + /** + * Check if a model is currently loading. + * + * @param model - Model data entry from the API response + * @returns True if the model status is LOADING + */ + static isModelLoading(model: ApiModelDataEntry): boolean { + return model.status.value === ServerModelStatus.LOADING; + } + /** * * @@ -130,13 +123,20 @@ export class ModelsService { */ /** - * Check if a model is currently loading. - * - * @param model - Model data entry from the API response - * @returns True if the model status is LOADING + * True when a router entry id is a sidecar-only entry, e.g. `org/model:Q4_0-mtp` + * or `org/model:mmproj`. Such entries mark a downloaded sidecar file, not a + * loadable model, so the selector skips them. */ - static isModelLoading(model: ApiModelDataEntry): boolean { - return model.status.value === ServerModelStatus.LOADING; + static isSidecarEntry(modelId: string): boolean { + const idx = modelId.indexOf(MODEL_ID.QUANTIZATION_SEPARATOR); + + if (idx === MODEL_ID.NOT_FOUND) return false; + + const tag = modelId.slice(idx + 1).toLowerCase(); + const dash = tag.lastIndexOf(MODEL_ID.SEGMENT_SEPARATOR); + const token = dash === -1 ? tag : tag.slice(dash + 1); + + return SIDECAR_TOKENS.includes(token); } /**