diff --git a/src/lib/components/chat/Messages/ResponseMessage/TaskList.svelte b/src/lib/components/chat/Messages/ResponseMessage/TaskList.svelte index b8541a3ffa..79a9f42d5d 100644 --- a/src/lib/components/chat/Messages/ResponseMessage/TaskList.svelte +++ b/src/lib/components/chat/Messages/ResponseMessage/TaskList.svelte @@ -18,7 +18,7 @@ {#if tasks.length > 0 && hasActive}
@@ -26,7 +26,10 @@
- {completedCount} {$i18n.t('out of')} {totalCount} {$i18n.t('tasks completed')} + {completedCount} + {$i18n.t('out of')} + {totalCount} + {$i18n.t('tasks completed')}
@@ -50,19 +53,43 @@
{#if task.status === 'completed'} - + {:else if task.status === 'in_progress'} - + {:else if task.status === 'cancelled'} - + {:else} - + {/if} diff --git a/src/lib/components/chat/ModelSelector/ModelItem.svelte b/src/lib/components/chat/ModelSelector/ModelItem.svelte index b5a29ffe96..cd5fe453c3 100644 --- a/src/lib/components/chat/ModelSelector/ModelItem.svelte +++ b/src/lib/components/chat/ModelSelector/ModelItem.svelte @@ -26,6 +26,7 @@ export let unloadModelHandler: (modelValue: string) => void = () => {}; export let pinModelHandler: (modelId: string) => void = () => {}; + export let deleteModelHandler: (model: any) => void = () => {}; export let onClick: () => void = () => {}; @@ -255,6 +256,7 @@ bind:show={showMenu} model={item.model} {pinModelHandler} + {deleteModelHandler} copyLinkHandler={() => { copyLinkHandler(item.model); }} diff --git a/src/lib/components/chat/ModelSelector/ModelItemMenu.svelte b/src/lib/components/chat/ModelSelector/ModelItemMenu.svelte index 65d90bf2a3..d0f46b2624 100644 --- a/src/lib/components/chat/ModelSelector/ModelItemMenu.svelte +++ b/src/lib/components/chat/ModelSelector/ModelItemMenu.svelte @@ -18,6 +18,7 @@ export let pinModelHandler: (modelId: string) => void = () => {}; export let copyLinkHandler: Function = () => {}; + export let deleteModelHandler: Function = () => {}; export let onClose: Function = () => {}; @@ -66,6 +67,37 @@
{$i18n.t('Edit')}
+ {#if $user?.role === 'admin' && model?.owned_by === 'ollama'} + + {/if} +
{/if} diff --git a/src/lib/components/chat/ModelSelector/Selector.svelte b/src/lib/components/chat/ModelSelector/Selector.svelte index 1a7a3dfc97..3d316562d5 100644 --- a/src/lib/components/chat/ModelSelector/Selector.svelte +++ b/src/lib/components/chat/ModelSelector/Selector.svelte @@ -8,6 +8,7 @@ dayjs.extend(relativeTime); import Spinner from '$lib/components/common/Spinner.svelte'; + import ConfirmDialog from '$lib/components/common/ConfirmDialog.svelte'; import { flyAndScale } from '$lib/utils/transitions'; import { createEventDispatcher, onMount, getContext, tick } from 'svelte'; @@ -375,6 +376,41 @@ } }; + let showDeleteConfirm = false; + let deleteModelTarget: any = null; + + const deleteModelHandler = async (model: any) => { + deleteModelTarget = model; + showDeleteConfirm = true; + }; + + const confirmDeleteModel = async () => { + const model = deleteModelTarget; + if (!model) return; + + const res = await deleteModel(localStorage.token, model.id).catch((error) => { + toast.error($i18n.t('Error deleting model: {{error}}', { error })); + }); + + if (res) { + toast.success($i18n.t('Model {{modelName}} deleted successfully', { modelName: model.name ?? model.id })); + + // If the deleted model was selected, clear the selection + if (value === model.id) { + value = ''; + } + + models.set( + await getModels( + localStorage.token, + $config?.features?.enable_direct_connections && ($settings?.directConnections ?? null) + ) + ); + } + + deleteModelTarget = null; + }; + const ITEM_HEIGHT = 42; const OVERSCAN = 10; @@ -388,6 +424,15 @@ ); + { + confirmDeleteModel(); + }} +/> + { @@ -646,6 +691,7 @@ {value} {pinModelHandler} {unloadModelHandler} + {deleteModelHandler} onClick={() => { value = item.value; selectedModelIdx = index;