@@ -1,10 +1,11 @@
|
||||
<script setup lang="ts">
|
||||
import { NButton, NDataTable, NInput, NSelect, NTooltip, useDialog, type DataTableColumns } from 'naive-ui'
|
||||
import { NButton, NDataTable, NInput, NSelect, NTooltip, type DataTableColumns } from 'naive-ui'
|
||||
import { computed, h, reactive, ref } from 'vue'
|
||||
|
||||
import { createAiChannel, deleteAiChannel, probeAiChannel, updateAiChannel } from '@/api/aigateway'
|
||||
import { listCachedRegions } from '@/api/configs'
|
||||
import AiChannelModelsModal from '@/components/ai/AiChannelModelsModal.vue'
|
||||
import ConfirmPop from '@/components/ConfirmPop.vue'
|
||||
import GroupChips from '@/components/ai/GroupChips.vue'
|
||||
import PanelHeader from '@/components/PanelHeader.vue'
|
||||
import AppInputNumber from '@/components/AppInputNumber.vue'
|
||||
@@ -25,7 +26,6 @@ const emit = defineEmits<{ changed: [] }>()
|
||||
const groupHints = computed(() => [...new Set(props.channels.map((c) => c.group).filter(Boolean))])
|
||||
|
||||
const toast = useToast()
|
||||
const dialog = useDialog()
|
||||
const scope = useScopeStore()
|
||||
/** 名称列:渠道名关联租户,悬停出统一租户卡(别名/名称/主区域/前往租户);
|
||||
* 名称本身不承载跳转,单元格内截断 */
|
||||
@@ -135,28 +135,31 @@ function openModels(ch: AiChannel) {
|
||||
showModels.value = true
|
||||
}
|
||||
|
||||
/** 正在切换启用状态的渠道 id 集合,按行 loading 防连点 */
|
||||
const toggling = ref(new Set<number>())
|
||||
|
||||
async function toggle(ch: AiChannel) {
|
||||
if (toggling.value.has(ch.id)) return
|
||||
toggling.value.add(ch.id)
|
||||
try {
|
||||
await updateAiChannel(ch.id, { enabled: !ch.enabled })
|
||||
toast.success(ch.enabled ? '已停用' : '已启用')
|
||||
emit('changed')
|
||||
} catch (e) {
|
||||
toast.error(e instanceof Error ? e.message : '操作失败')
|
||||
} finally {
|
||||
toggling.value.delete(ch.id)
|
||||
}
|
||||
}
|
||||
|
||||
function confirmRemove(ch: AiChannel) {
|
||||
dialog.warning({
|
||||
title: '删除渠道',
|
||||
content: `删除渠道「${ch.name}」及其模型缓存?`,
|
||||
positiveText: '删除',
|
||||
negativeText: '取消',
|
||||
onPositiveClick: async () => {
|
||||
await deleteAiChannel(ch.id)
|
||||
toast.success('已删除')
|
||||
emit('changed')
|
||||
},
|
||||
})
|
||||
async function doRemove(ch: AiChannel) {
|
||||
try {
|
||||
await deleteAiChannel(ch.id)
|
||||
toast.success('已删除')
|
||||
emit('changed')
|
||||
} catch (e) {
|
||||
toast.error(e instanceof Error ? e.message : '删除失败')
|
||||
}
|
||||
}
|
||||
|
||||
function probeCell(r: AiChannel) {
|
||||
@@ -204,9 +207,18 @@ const columns = computed<DataTableColumns<AiChannel>>(() => [
|
||||
render: (r) => h('div', { class: 'flex items-center gap-0.5' }, [
|
||||
h(NButton, { size: 'tiny', quaternary: true, type: 'primary', loading: probing.value.has(r.id), onClick: () => doProbe(r.id) }, { default: () => '探测' }),
|
||||
h(NButton, { size: 'tiny', quaternary: true, type: 'primary', onClick: () => openModels(r) }, { default: () => '模型列表' }),
|
||||
h(NButton, { size: 'tiny', quaternary: true, onClick: () => toggle(r) }, { default: () => (r.enabled ? '停用' : '启用') }),
|
||||
h(NButton, { size: 'tiny', quaternary: true, loading: toggling.value.has(r.id), onClick: () => toggle(r) }, { default: () => (r.enabled ? '停用' : '启用') }),
|
||||
h(NButton, { size: 'tiny', quaternary: true, type: 'primary', onClick: () => openEdit(r) }, { default: () => '编辑' }),
|
||||
h(NButton, { size: 'tiny', quaternary: true, type: 'error', onClick: () => confirmRemove(r) }, { default: () => '删除' }),
|
||||
h(
|
||||
ConfirmPop,
|
||||
{
|
||||
title: `删除渠道「${r.name}」?`,
|
||||
content: '渠道及其模型缓存将一并删除。',
|
||||
confirmText: '删除',
|
||||
onConfirm: () => doRemove(r),
|
||||
},
|
||||
{ trigger: () => h(NButton, { size: 'tiny', quaternary: true, type: 'error' }, { default: () => '删除' }) },
|
||||
),
|
||||
]),
|
||||
},
|
||||
])
|
||||
|
||||
Reference in New Issue
Block a user