@blueking/chat-x 0.0.47-beta.3 → 0.0.48-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/chat-input/chat-input.vue.d.ts +15 -2
- package/dist/components/chat-input/input-attachment/input-attachment.vue.d.ts +4 -2
- package/dist/components/chat-input/model-selector/capabilities.d.ts +3 -0
- package/dist/components/chat-input/model-selector/index.d.ts +3 -0
- package/dist/components/chat-input/model-selector/model-selector-panel.vue.d.ts +26 -0
- package/dist/components/chat-input/model-selector/model-selector-trigger.vue.d.ts +14 -0
- package/dist/components/chat-input/model-selector/model-selector.vue.d.ts +39 -0
- package/dist/components/chat-input/model-selector/types.d.ts +61 -0
- package/dist/components/chat-input/model-selector/use-model-selector.d.ts +17 -0
- package/dist/components/chat-message/message-container/message-container.vue.d.ts +2 -0
- package/dist/components/index.d.ts +3 -1
- package/dist/icons/input.d.ts +7 -0
- package/dist/index.css +1 -1
- package/dist/index.js +2147 -1853
- package/dist/index.js.map +1 -1
- package/dist/lang/lang.d.ts +5 -1
- package/dist/mcp/generated/docs/ai-prompt-list.md +6 -3
- package/dist/mcp/generated/docs/ai-skill-list.md +75 -0
- package/dist/mcp/generated/docs/ai-slash-input.md +17 -3
- package/dist/mcp/generated/docs/chat-container.md +189 -74
- package/dist/mcp/generated/docs/chat-input.md +79 -5
- package/dist/mcp/generated/docs/input-attachment.md +1 -0
- package/dist/mcp/generated/docs/message-container.md +47 -0
- package/dist/mcp/generated/docs/message-tools.md +5 -1
- package/dist/mcp/generated/docs/model-selector.md +157 -0
- package/dist/mcp/generated/docs/tool-btn.md +33 -4
- package/dist/mcp/generated/index.json +75 -9
- package/dist/mcp/index.js +0 -0
- package/dist/types/tool.d.ts +6 -2
- package/package.json +21 -20
|
@@ -8,6 +8,7 @@
|
|
|
8
8
|
- **shortcut-btn** — 已选快捷指令以单按钮形式展示并可关闭
|
|
9
9
|
- **shortcut-render** — 快捷指令含 components 时由外层唤起表单渲染
|
|
10
10
|
- **chat-container** — 顶层聊天布局中作为输入区子组件
|
|
11
|
+
- **model-selector** — 传入 models 后在发送按钮左侧默认展示模型选择器
|
|
11
12
|
- **cite-content** — 消息引用区展示选中的上下文片段
|
|
12
13
|
|
|
13
14
|
---
|
|
@@ -38,6 +39,7 @@ ai-chat-input-container
|
|
|
38
39
|
├── FileUploadBtn(仅当 supportUpload 为 true 时显示,在 slot#attachment 外部)
|
|
39
40
|
├── 分隔线(仅当 supportUpload 为 true 且有快捷指令时显示)
|
|
40
41
|
├── slot#attachment(默认:ShortcutBtns 或已选 ShortcutBtn + 关闭图标)
|
|
42
|
+
├── slot#before-send(默认:传入 models 时渲染 ModelSelector)
|
|
41
43
|
└── slot#send-icon(默认:发送/停止图标,仅替换图标,按钮容器保留)
|
|
42
44
|
```
|
|
43
45
|
|
|
@@ -183,9 +185,24 @@ const handleSendMessage = async (
|
|
|
183
185
|
|
|
184
186
|
**渲染效果**(顶部引用区,点击右侧 × 关闭引用)
|
|
185
187
|
|
|
186
|
-
##
|
|
188
|
+
## Skill 列表(`/` 触发)
|
|
187
189
|
|
|
188
|
-
通过 `
|
|
190
|
+
通过 `skills` 传入 Skill 列表,用户在编辑器中输入 `/` 唤出 [AiSkillList](/components/input/ai-skill-list) 菜单,支持按名称/编码模糊搜索,选择后以 Skill 标签嵌入编辑器。无 icon 或 icon 加载失败时展示首字母 fallback。已插入的 Skill 不会再出现在下拉菜单中(自动去重)。
|
|
191
|
+
|
|
192
|
+
```vue
|
|
193
|
+
<script setup lang="ts">
|
|
194
|
+
import type { ISkillListItem } from '@blueking/chat-x';
|
|
195
|
+
|
|
196
|
+
const skills: ISkillListItem[] = [
|
|
197
|
+
{ skill_code: 'translate', skill_name: '翻译', description: '翻译文本', icon: '' },
|
|
198
|
+
{ skill_code: 'summarize', skill_name: '总结', description: '总结内容', icon: 'https://example.com/icon.png' },
|
|
199
|
+
];
|
|
200
|
+
</script>
|
|
201
|
+
```
|
|
202
|
+
|
|
203
|
+
## Prompt 模板(`\` 触发)
|
|
204
|
+
|
|
205
|
+
通过 `prompts` 传入字符串数组,用户在编辑器中输入 `\` 唤出 Prompt 菜单,支持模糊搜索,选择后自动填入编辑器:
|
|
189
206
|
|
|
190
207
|
```vue
|
|
191
208
|
<script setup lang="ts">
|
|
@@ -483,6 +500,57 @@ const handleSendMessage = async (
|
|
|
483
500
|
|
|
484
501
|
**渲染效果**(顶部自定义模型信息与中断提示)
|
|
485
502
|
|
|
503
|
+
## 模型选择
|
|
504
|
+
|
|
505
|
+
传入 `models` 后,会在发送按钮左侧展示 [ModelSelector](/components/input/model-selector)。选中值(模型的 `llm_name`)通过 `v-model:selected-model` 双向绑定,`@model-change` 可获取完整模型对象。能力标签由组件依据 `property` 自动派生。
|
|
506
|
+
|
|
507
|
+
```vue
|
|
508
|
+
<template>
|
|
509
|
+
<ChatInput
|
|
510
|
+
v-model="inputValue"
|
|
511
|
+
v-model:selected-model="selectedModel"
|
|
512
|
+
:message-status="messageStatus"
|
|
513
|
+
:models="models"
|
|
514
|
+
:on-send-message="handleSendMessage"
|
|
515
|
+
@model-change="handleModelChange"
|
|
516
|
+
/>
|
|
517
|
+
</template>
|
|
518
|
+
|
|
519
|
+
<script setup lang="ts">
|
|
520
|
+
import { ref } from 'vue';
|
|
521
|
+
import { ChatInput, MessageStatus, type IModelOption, type TagSchema } from '@blueking/chat-x';
|
|
522
|
+
|
|
523
|
+
const inputValue = ref('');
|
|
524
|
+
// 选中值为 llm_name
|
|
525
|
+
const selectedModel = ref('GPT-4');
|
|
526
|
+
const messageStatus = ref(MessageStatus.Complete);
|
|
527
|
+
const models: IModelOption[] = [
|
|
528
|
+
{ id: 1, llm_name: 'GPT-4', property: { support_thinking: true } },
|
|
529
|
+
{ id: 2, llm_name: 'Claude 3', property: {} },
|
|
530
|
+
];
|
|
531
|
+
|
|
532
|
+
const handleSendMessage = async (content: string, docSchema: TagSchema) => {
|
|
533
|
+
/* 发送时可读取 selectedModel.value */
|
|
534
|
+
};
|
|
535
|
+
|
|
536
|
+
const handleModelChange = (model: IModelOption) => {
|
|
537
|
+
console.log('切换模型:', model);
|
|
538
|
+
};
|
|
539
|
+
</script>
|
|
540
|
+
```
|
|
541
|
+
|
|
542
|
+
也可通过 `#model-selector` 插槽完全自定义选择器,插槽参数为 `{ models, selectedModel }`:
|
|
543
|
+
|
|
544
|
+
```vue
|
|
545
|
+
<template>
|
|
546
|
+
<ChatInput v-model="inputValue" :models="models">
|
|
547
|
+
<template #model-selector="{ models, selectedModel }">
|
|
548
|
+
<span>当前:{{ selectedModel || '未选择' }}(共 {{ models.length }} 个)</span>
|
|
549
|
+
</template>
|
|
550
|
+
</ChatInput>
|
|
551
|
+
</template>
|
|
552
|
+
```
|
|
553
|
+
|
|
486
554
|
## Expose(模板引用)
|
|
487
555
|
|
|
488
556
|
通过 `ref` 获取组件实例后可调用以下方法:
|
|
@@ -517,11 +585,14 @@ const handleSendMessage = async (
|
|
|
517
585
|
| 属性名 | 类型 | 默认值 | 必填 | 说明 |
|
|
518
586
|
| ------------------ | -------------------------------------------------------------------------- | -------- | ---- | ------------------------------------------------------- |
|
|
519
587
|
| modelValue | `string \| TagSchema` | - | ✅ | 编辑器的值,支持 `v-model` |
|
|
588
|
+
| selectedModel | `string` | - | - | 当前选中模型的 `llm_name`,支持 `v-model:selected-model` |
|
|
520
589
|
| messageStatus | `MessageStatus` | - | - | 消息状态,控制按钮;输入为空时内部强制 `disabled` |
|
|
521
590
|
| cite | `string` | `''` | - | 引用内容,支持 `v-model:cite`,不为空时显示引用区 |
|
|
522
|
-
|
|
|
591
|
+
| skills | `ISkillListItem[]` | `[]` | - | Skill 列表,输入 `/` 触发,选中后插入 Skill 标签 |
|
|
592
|
+
| prompts | `string[]` | `[]` | - | Prompt 模板列表,输入 `\` 触发 |
|
|
523
593
|
| resources | `IAiSlashMenuItem[]` | `[]` | - | 资源列表,输入 `@` 触发,按 `type` 分组展示 |
|
|
524
594
|
| shortcuts | `Shortcut[]` | - | - | 快捷指令列表,显示在底部工具栏 |
|
|
595
|
+
| models | `IModelOption[]` | - | - | 可选模型列表,传入后在发送按钮左侧展示模型选择器 |
|
|
525
596
|
| shortcutId | `string` | - | - | 当前选中的快捷指令 ID,匹配时列表收起为已选样式 |
|
|
526
597
|
| placeholder | `string` | 见默认值 | - | 编辑器占位符,支持多行 |
|
|
527
598
|
| inputMaxHeight | `number` | `200` | - | 框体最大高度(px),有文件时自动加上文件预览区高度 |
|
|
@@ -536,8 +607,9 @@ const handleSendMessage = async (
|
|
|
536
607
|
### 默认占位符
|
|
537
608
|
|
|
538
609
|
```
|
|
539
|
-
输入 "/"唤出
|
|
540
|
-
输入"
|
|
610
|
+
输入 "/" 唤出 Skill
|
|
611
|
+
输入 "\" 唤出 Prompt
|
|
612
|
+
输入 "@" 唤出 工具和 MCP
|
|
541
613
|
通过 Shift + Enter 进行换行输入
|
|
542
614
|
```
|
|
543
615
|
|
|
@@ -546,6 +618,7 @@ const handleSendMessage = async (
|
|
|
546
618
|
| 事件名 | 参数 | 触发时机 |
|
|
547
619
|
| ----------------- | ------------------------------------------------------------------------ | --------------------------------------------------------- |
|
|
548
620
|
| update:modelValue | `(value: string \| TagSchema, selectedResourceList: IAiSlashMenuItem[])` | 编辑器值变化时触发;第二个参数为当前已选中的 `@` 资源列表 |
|
|
621
|
+
| modelChange | `(model: IModelOption)` | 用户切换模型时触发 |
|
|
549
622
|
| selectShortcut | `(shortcut: Shortcut)` | 点击底部快捷指令按钮 |
|
|
550
623
|
| deleteShortcut | - | 点击已选快捷指令旁的关闭按钮 |
|
|
551
624
|
|
|
@@ -558,6 +631,7 @@ const handleSendMessage = async (
|
|
|
558
631
|
| input-header | - | 框体内顶部,替换引用区(`CiteContent`) |
|
|
559
632
|
| files | `{ files: Partial<UploadFile>[] }` | 文件预览区 |
|
|
560
633
|
| attachment | - | 底部快捷指令区,`FileUploadBtn` 在其左侧,不受此 slot 影响 |
|
|
634
|
+
| model-selector | `{ models: IModelOption[]; selectedModel: string \| undefined }` | 发送按钮左侧模型选择区,默认渲染 ModelSelector |
|
|
561
635
|
| send-icon | - | 发送按钮内图标,按钮的点击逻辑和样式仍由组件控制 |
|
|
562
636
|
|
|
563
637
|
### Expose
|
|
@@ -301,6 +301,51 @@ AI 回复状态为 `error` 时,消息以错误样式展示:
|
|
|
301
301
|
|
|
302
302
|
连续多轮问答,组件按角色自动分组,每个 AI 组独立显示工具栏:
|
|
303
303
|
|
|
304
|
+
## 自定义消息工具栏
|
|
305
|
+
|
|
306
|
+
`messageTools`(左侧)与 `updateTools`(右侧反馈区)用于在**内置工具的基础上做增量定制**,无需重写整份列表。二者分别与内置 `CONST_MESSAGE_TOOLS`、`CONST_UPDATE_TOOLS` 按 `id` 合并,规则如下:
|
|
307
|
+
|
|
308
|
+
- **覆盖**:`id` 命中内置项时,做字段级浅合并(仅覆盖传入的字段,其余保留),不新增条目
|
|
309
|
+
- **追加**:`id` 为内置列表中不存在的新值时,追加到该组末尾(如自定义「保存」「收藏」按钮)
|
|
310
|
+
- **隐藏**:传入 `{ id: 'xxx', hidden: true }` 可移除对应内置项(如隐藏「分享」)
|
|
311
|
+
- **自定义图标**:通过 `icon`(组件/VNode)为自定义按钮提供图标,优先级高于内置 `ToolIconsMap`
|
|
312
|
+
- 不传 `messageTools` / `updateTools` 时,各自使用内置默认列表
|
|
313
|
+
|
|
314
|
+
```vue
|
|
315
|
+
<template>
|
|
316
|
+
<MessageContainer
|
|
317
|
+
:messages="messages"
|
|
318
|
+
:message-groups="messageGroups"
|
|
319
|
+
message-status="complete"
|
|
320
|
+
:message-tools="customMessageTools"
|
|
321
|
+
:update-tools="customUpdateTools"
|
|
322
|
+
:on-agent-action="handleAgentAction"
|
|
323
|
+
@stop-streaming="handleStopStreaming"
|
|
324
|
+
/>
|
|
325
|
+
</template>
|
|
326
|
+
|
|
327
|
+
<script setup lang="ts">
|
|
328
|
+
import { MessageContainer, DownloadIcon, type IToolBtn, type Message } from '@blueking/chat-x';
|
|
329
|
+
|
|
330
|
+
const customMessageTools: IToolBtn[] = [
|
|
331
|
+
{ id: 'save', name: '保存', description: '保存该回答', icon: DownloadIcon }, // 追加新按钮
|
|
332
|
+
{ id: 'copy', description: '复制全文' }, // 覆盖内置 copy 的 description
|
|
333
|
+
{ id: 'share', hidden: true }, // 隐藏内置「分享」
|
|
334
|
+
];
|
|
335
|
+
const customUpdateTools: IToolBtn[] = [
|
|
336
|
+
{ id: 'collect', name: '收藏', description: '收藏到我的空间', icon: DownloadIcon },
|
|
337
|
+
];
|
|
338
|
+
|
|
339
|
+
const handleAgentAction = async (tool: IToolBtn, messages: Message[]) => {
|
|
340
|
+
if (tool.id === 'save') {
|
|
341
|
+
// 处理保存
|
|
342
|
+
}
|
|
343
|
+
};
|
|
344
|
+
</script>
|
|
345
|
+
```
|
|
346
|
+
|
|
347
|
+
> **合并优先级**:`RenderMode.Test` 下仍会额外过滤掉「分享」按钮(即便合并后存在);即测试模式对 `share` 的过滤在自定义合并之后生效。
|
|
348
|
+
|
|
304
349
|
## 工具栏状态控制
|
|
305
350
|
|
|
306
351
|
通过 `messageToolsStatus` 控制消息工具栏的显示状态。常见用法:流式输出期间禁用工具栏:
|
|
@@ -501,6 +546,8 @@ AI 回复状态为 `error` 时,消息以错误样式展示:
|
|
|
501
546
|
| messages | `Message[]` | — | **必填**,消息列表 |
|
|
502
547
|
| messageGroups | `MessageGroup[]` | — | 预计算的消息分组;传入时跳过内部分组逻辑,由 `ChatContainer` 通过 `useMessageGroup` 提供 |
|
|
503
548
|
| messageStatus | `MessageStatus` | — | 当前整体消息状态,控制底部「停止生成」按钮显示;`ChatContainer` 会结合末尾 Loading 占位推导 `fetching` 等再传入 |
|
|
549
|
+
| messageTools | `IToolBtn[]` | — | AI 消息左侧工具(复制/引用等)的自定义配置;按 `id` 与内置 `CONST_MESSAGE_TOOLS` 合并(覆盖同 id、追加新 id、`hidden` 过滤),详见「自定义消息工具栏」 |
|
|
550
|
+
| updateTools | `IToolBtn[]` | — | AI 消息右侧反馈工具(点赞/踩/删除等)的自定义配置;按 `id` 与内置 `CONST_UPDATE_TOOLS` 合并,规则同上 |
|
|
504
551
|
| messageToolsStatus | `MessageToolsStatus` | — | 工具栏状态,透传给 `MessageTools` 和 `MessageRender` |
|
|
505
552
|
| messageToolsTippyOptions | `AITippyProps` | — | 透传给 `MessageTools` 和 `MessageRender`(进而透传给 `UserMessage` 的工具栏)的 Tippy 配置,用于自定义 tooltip 挂载点、位置等(如 `appendTo`、`placement`、`zIndex`) |
|
|
506
553
|
| enableSelection | `boolean` | `false` | 是否启用多选模式 |
|
|
@@ -361,11 +361,15 @@ const CONST_UPDATE_TOOLS = [
|
|
|
361
361
|
|
|
362
362
|
```typescript
|
|
363
363
|
import { MessageToolsStatus, type IToolBtn } from '@blueking/chat-x';
|
|
364
|
+
import type { Component, VNode } from 'vue';
|
|
364
365
|
|
|
365
366
|
interface IToolBtn {
|
|
366
|
-
id?:
|
|
367
|
+
id?: (string & {}) | ToolIcons; // 工具唯一标识;命中 ToolIconsMap 显示内置图标,否则显示 name 文本;支持业务自定义字符串
|
|
367
368
|
name?: string; // 工具名称,无对应图标时显示;也用作 tooltip fallback
|
|
368
369
|
description?: string; // tooltip 文本
|
|
370
|
+
icon?: Component | VNode; // 自定义图标(组件/VNode),优先级高于内置 ToolIconsMap[id]
|
|
371
|
+
hidden?: boolean; // 按 id 合并时隐藏该按钮(仅在 MessageContainer/ChatContainer 合并语义下生效)
|
|
372
|
+
triggerSelection?: boolean; // 标记点击后进入多选态(复用 share 选择流程),确认走 confirmShare
|
|
369
373
|
}
|
|
370
374
|
|
|
371
375
|
enum MessageToolsStatus {
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
<!-- AI SUMMARY -->
|
|
2
|
+
## 快速了解
|
|
3
|
+
|
|
4
|
+
聊天输入区的模型下拉选择器,支持搜索过滤、能力标签与键盘导航。 源码位置:src/components/chat-input/model-selector/model-selector.vue。
|
|
5
|
+
|
|
6
|
+
### 关联组件
|
|
7
|
+
- **chat-input** — 传入 models 后在发送按钮左侧默认渲染
|
|
8
|
+
- **input-attachment** — 通过 before-send 插槽与发送按钮成组布局
|
|
9
|
+
|
|
10
|
+
---
|
|
11
|
+
<!-- FULL DOC -->
|
|
12
|
+
|
|
13
|
+
# ModelSelector 模型选择器
|
|
14
|
+
|
|
15
|
+
## 源码事实
|
|
16
|
+
|
|
17
|
+
- **源码位置**:`src/components/chat-input/model-selector/model-selector.vue`
|
|
18
|
+
- **能力域**:输入交互
|
|
19
|
+
- **能力说明**:基于 Tippy 下拉的模型选择器,包含触发器、搜索面板与能力标签展示;数据过滤逻辑由 `useModelSelector` composable 承担。
|
|
20
|
+
|
|
21
|
+
> **能力域**:输入交互
|
|
22
|
+
|
|
23
|
+
可在 [ChatInput](/components/input/chat-input) 传入 `models` 后自动出现在发送按钮左侧,也可单独使用。
|
|
24
|
+
|
|
25
|
+
## 组件结构
|
|
26
|
+
|
|
27
|
+
```
|
|
28
|
+
ModelSelector(Tippy 容器,theme: ai-model-selector)
|
|
29
|
+
├── ModelSelectorTrigger(触发器:图标 + 名称 + 箭头)
|
|
30
|
+
└── ModelSelectorPanel(下拉面板)
|
|
31
|
+
├── 搜索框(展开后自动聚焦)
|
|
32
|
+
└── 模型列表(支持键盘导航、选中态、禁用态、能力标签)
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
## 基础用法
|
|
36
|
+
|
|
37
|
+
选中值为模型的 `llm_name`;能力标签由组件依据 `property`(`support_thinking` / `support_thinking_quick` / `support_vision`)自动派生,无需调用方传入。
|
|
38
|
+
|
|
39
|
+
```vue
|
|
40
|
+
<template>
|
|
41
|
+
<ModelSelector
|
|
42
|
+
v-model="selectedModel"
|
|
43
|
+
:models="models"
|
|
44
|
+
@change="handleModelChange"
|
|
45
|
+
/>
|
|
46
|
+
</template>
|
|
47
|
+
|
|
48
|
+
<script setup lang="ts">
|
|
49
|
+
import { ref } from 'vue';
|
|
50
|
+
import { ModelSelector, type IModelOption } from '@blueking/chat-x';
|
|
51
|
+
|
|
52
|
+
// 选中值为 llm_name
|
|
53
|
+
const selectedModel = ref('DeepSeek-V4-Pro-Online-32k');
|
|
54
|
+
const models: IModelOption[] = [
|
|
55
|
+
{
|
|
56
|
+
id: 119,
|
|
57
|
+
llm_code: 'DeepSeek-V4-Pro-Online-32k',
|
|
58
|
+
llm_name: 'DeepSeek-V4-Pro-Online-32k',
|
|
59
|
+
llm_type: 'chat.completion',
|
|
60
|
+
space_auth_mode: 'APPLY',
|
|
61
|
+
user_auth_mode: 'PUBLIC',
|
|
62
|
+
max_token_size: 4096,
|
|
63
|
+
icon: 'https://example.com/deepseek.png',
|
|
64
|
+
description: 'DeepSeek-V4-Pro 旗舰版本,支持超长上下文与复杂任务处理',
|
|
65
|
+
base_model: 'deepseek',
|
|
66
|
+
tag_names: [],
|
|
67
|
+
// support_thinking → 深度思考、support_vision → 图生文
|
|
68
|
+
property: { support_thinking: true, support_vision: true, max_model_len: 32000 },
|
|
69
|
+
},
|
|
70
|
+
];
|
|
71
|
+
|
|
72
|
+
const handleModelChange = (model: IModelOption) => {
|
|
73
|
+
console.log('选中模型:', model);
|
|
74
|
+
};
|
|
75
|
+
</script>
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
## API
|
|
79
|
+
|
|
80
|
+
### Props
|
|
81
|
+
|
|
82
|
+
| 属性名 | 类型 | 默认值 | 说明 |
|
|
83
|
+
| ----------------- | -------------------------------------------------------------------------- | ---------------- | -------------------------------------- |
|
|
84
|
+
| disabled | `boolean` | `false` | 是否禁用整个选择器 |
|
|
85
|
+
| models | `IModelOption[]` | `[]` | 可选模型列表 |
|
|
86
|
+
| placeholder | `string` | `选择模型` | trigger 无选中时的占位文案 |
|
|
87
|
+
| searchPlaceholder | `string` | `搜索模型关键字` | 搜索框占位文案 |
|
|
88
|
+
| tippyOptions | `Partial<Omit<TippyOptions, 'getReferenceClientRect' \| 'triggerTarget'>>` | — | 透传给 Tippy 的额外配置 |
|
|
89
|
+
|
|
90
|
+
### v-model
|
|
91
|
+
|
|
92
|
+
| 属性名 | 类型 | 说明 |
|
|
93
|
+
| ------ | -------- | ----------------------------- |
|
|
94
|
+
| — | `string` | 当前选中模型的 `llm_name` 值 |
|
|
95
|
+
|
|
96
|
+
### Events
|
|
97
|
+
|
|
98
|
+
| 事件名 | 参数 | 说明 |
|
|
99
|
+
| ------ | ----------------------- | -------------------- |
|
|
100
|
+
| change | `(model: IModelOption)` | 用户选中模型时触发 |
|
|
101
|
+
|
|
102
|
+
## 类型定义
|
|
103
|
+
|
|
104
|
+
```typescript
|
|
105
|
+
import type { IModelCapability, IModelOption, IModelProperty, ModelCapabilityTheme } from '@blueking/chat-x';
|
|
106
|
+
|
|
107
|
+
type ModelCapabilityTheme = 'default' | 'primary' | 'success' | 'warning';
|
|
108
|
+
|
|
109
|
+
// 能力标签由组件依据 property 派生(文案走内置 i18n)
|
|
110
|
+
interface IModelCapability {
|
|
111
|
+
theme?: ModelCapabilityTheme;
|
|
112
|
+
text: string;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
// 模型能力属性,决定派生出的能力标签
|
|
116
|
+
interface IModelProperty {
|
|
117
|
+
agent_type?: string;
|
|
118
|
+
default?: boolean;
|
|
119
|
+
is_self_host?: boolean;
|
|
120
|
+
max_model_len?: number;
|
|
121
|
+
support_summary?: boolean;
|
|
122
|
+
support_thinking?: boolean; // → 深度思考
|
|
123
|
+
support_thinking_quick?: boolean; // → 快速思考
|
|
124
|
+
support_tools?: boolean;
|
|
125
|
+
support_vision?: boolean; // → 图生文
|
|
126
|
+
support_window?: boolean;
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// 模型选项,贴合后端模型接口结构
|
|
130
|
+
interface IModelOption {
|
|
131
|
+
base_model?: string;
|
|
132
|
+
description?: string; // 选项 hover 的 title 提示
|
|
133
|
+
disabled?: boolean; // 前端扩展字段,禁用项不可选中
|
|
134
|
+
icon?: string;
|
|
135
|
+
id: number;
|
|
136
|
+
llm_code: string;
|
|
137
|
+
llm_name: string; // 展示名,同时作为选中值
|
|
138
|
+
llm_type: string;
|
|
139
|
+
max_token_size: number;
|
|
140
|
+
property: IModelProperty;
|
|
141
|
+
space_auth_mode: string;
|
|
142
|
+
tag_names?: string[];
|
|
143
|
+
user_auth_mode: string;
|
|
144
|
+
}
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
## 注意事项
|
|
148
|
+
|
|
149
|
+
1. `models` 为空或 `disabled` 为 `true` 时,下拉不会展开。
|
|
150
|
+
2. 选中值为模型的 `llm_name`;能力标签由组件依据 `property` 的 `support_thinking` / `support_thinking_quick` / `support_vision` 派生,文案走内置 i18n。
|
|
151
|
+
3. `description` 会作为选项 hover 的 `title` 提示展示。
|
|
152
|
+
4. 展开面板后会自动聚焦搜索框;列表支持键盘上下选择与 Enter 确认(复用 `useMenuKeydown`)。
|
|
153
|
+
|
|
154
|
+
## 关联组件
|
|
155
|
+
|
|
156
|
+
- [ChatInput](/components/input/chat-input):传入 `models` 后默认在发送按钮左侧渲染本组件,也可通过 `#model-selector` 插槽完全自定义。
|
|
157
|
+
- [ChatContainer](/components/setup/chat-container):透传 `models` 与 `v-model:selected-model`,并向上 emit `modelChange`。
|
|
@@ -30,8 +30,9 @@ div.ai-tool-btn(v-tippy,flex,min-width: 20px,height: 20px,border-radiu
|
|
|
30
30
|
disabled=true → .is-disabled(color: #979ba5; cursor: not-allowed)
|
|
31
31
|
:not(.is-disabled):hover → color: #4d4f56; background: #eaebf0
|
|
32
32
|
│
|
|
33
|
-
└── <slot
|
|
34
|
-
├── [
|
|
33
|
+
└── <slot>(默认内容,可完全自定义;优先级最高)
|
|
34
|
+
├── [icon] → <component :is="icon" />(自定义图标组件/VNode,优先级高于内置图标)
|
|
35
|
+
├── [id && id in ToolIconsMap] → <component :is="ToolIconsMap[id]" />(内置 SVG 图标)
|
|
35
36
|
└── [其他] → <div>{{ name }}</div>(文本回退,XSS 安全)
|
|
36
37
|
|
|
37
38
|
Tippy:content=description, theme='ai-chat-box', disabled=true 时 onShow 返回 false 不显示
|
|
@@ -195,6 +196,28 @@ click 事件:disabled=true 时被 JS 拦截,不触发 emit
|
|
|
195
196
|
|
|
196
197
|
`id` 不在 `ToolIconsMap` 时渲染 `name` 文本,适用于自定义扩展场景:
|
|
197
198
|
|
|
199
|
+
## 自定义图标(icon 属性)
|
|
200
|
+
|
|
201
|
+
当内置 `ToolIconsMap` 未覆盖所需图标时,可通过 `icon` 传入自定义图标组件或 VNode(如业务新增的「保存」按钮)。`icon` 的渲染优先级高于内置图标,因此即便 `id` 命中内置图标,也会以 `icon` 为准。
|
|
202
|
+
|
|
203
|
+
```vue
|
|
204
|
+
<template>
|
|
205
|
+
<ToolBtn
|
|
206
|
+
id="save"
|
|
207
|
+
name="保存"
|
|
208
|
+
description="保存该回答"
|
|
209
|
+
:icon="DownloadIcon"
|
|
210
|
+
@click="handleClick"
|
|
211
|
+
/>
|
|
212
|
+
</template>
|
|
213
|
+
|
|
214
|
+
<script setup lang="ts">
|
|
215
|
+
import { ToolBtn, DownloadIcon } from '@blueking/chat-x';
|
|
216
|
+
</script>
|
|
217
|
+
```
|
|
218
|
+
|
|
219
|
+
> 优先级从高到低:默认插槽 `>` `icon` 属性 `>` 内置 `ToolIconsMap[id]` `>` `name` 文本回退。
|
|
220
|
+
|
|
198
221
|
## 自定义插槽内容
|
|
199
222
|
|
|
200
223
|
通过默认插槽可完全替换内置图标/文本,适用于预置 `ToolIconsMap` 未覆盖的图标场景(如侧栏全屏按钮):
|
|
@@ -225,9 +248,10 @@ click 事件:disabled=true 时被 JS 拦截,不触发 emit
|
|
|
225
248
|
|
|
226
249
|
| 属性名 | 类型 | 必填 | 默认值 | 说明 |
|
|
227
250
|
| ------------ | -------------------------------------------------------------------------- | ---- | ------ | ------------------------------------------------------------------------------------------------------------------ |
|
|
228
|
-
| id | `
|
|
251
|
+
| id | `(string & {}) \| ToolIcons` | 否 | — | 按钮标识;命中 `ToolIconsMap` 时渲染对应 SVG 图标,否则渲染 `name` 文本;支持业务自定义任意字符串(如 `save`) |
|
|
229
252
|
| name | `string` | 否 | — | 按钮名称;`id` 无对应图标时作为文本内容渲染 |
|
|
230
253
|
| description | `string` | 否 | — | Tippy tooltip 内容;`disabled=true` 时不显示 tooltip |
|
|
254
|
+
| icon | `Component \| VNode` | 否 | — | 自定义图标组件或 VNode;优先级高于内置 `ToolIconsMap[id]`,低于默认插槽 |
|
|
231
255
|
| active | `boolean` | 否 | — | 激活态;`true` 时追加 `.is-active`(字色由 `id` 决定:`like`/`activeLike` 为蓝色 `#3a84ff`,其他为红色 `#E71818`) |
|
|
232
256
|
| disabled | `boolean` | 否 | — | 禁用态;`true` 时追加 `.is-disabled`,阻止 click 事件,隐藏 tooltip |
|
|
233
257
|
| tippyOptions | `Partial<Omit<TippyOptions, 'getReferenceClientRect' \| 'triggerTarget'>>` | 否 | — | 自定义 Tippy 配置,与内部默认配置合并;可用于控制 `content`、`appendTo`、`placement` 等 |
|
|
@@ -247,11 +271,16 @@ click 事件:disabled=true 时被 JS 拦截,不触发 emit
|
|
|
247
271
|
## 类型定义
|
|
248
272
|
|
|
249
273
|
```typescript
|
|
274
|
+
import type { Component, VNode } from 'vue';
|
|
275
|
+
|
|
250
276
|
// 来自 @blueking/chat-x 导出
|
|
251
277
|
interface IToolBtn {
|
|
252
|
-
id?:
|
|
278
|
+
id?: (string & {}) | ToolIcons; // 内置 ID 保留自动补全,同时允许业务自定义任意字符串(如 'save')
|
|
253
279
|
name?: string;
|
|
254
280
|
description?: string;
|
|
281
|
+
icon?: Component | VNode; // 自定义图标,优先级高于内置 ToolIconsMap
|
|
282
|
+
hidden?: boolean; // 按 id 合并时隐藏该按钮(如 { id: 'share', hidden: true } 移除内置项)
|
|
283
|
+
triggerSelection?: boolean; // 标记点击后进入多选态(复用 share 选择流程),确认走 confirmShare
|
|
255
284
|
}
|
|
256
285
|
|
|
257
286
|
// ToolBtn 完整 Props
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": "2.0.0",
|
|
3
|
-
"generatedAt": "2026-07-
|
|
3
|
+
"generatedAt": "2026-07-27T02:31:49.169Z",
|
|
4
4
|
"domains": {
|
|
5
5
|
"setup": {
|
|
6
6
|
"label": "对话搭建",
|
|
@@ -44,6 +44,7 @@
|
|
|
44
44
|
"components": [
|
|
45
45
|
"ai-prompt-list",
|
|
46
46
|
"ai-selection",
|
|
47
|
+
"ai-skill-list",
|
|
47
48
|
"ai-slash-editor",
|
|
48
49
|
"ai-slash-input",
|
|
49
50
|
"ai-slash-menu",
|
|
@@ -51,6 +52,7 @@
|
|
|
51
52
|
"file-upload-btn",
|
|
52
53
|
"input-attachment",
|
|
53
54
|
"input-info-alert",
|
|
55
|
+
"model-selector",
|
|
54
56
|
"selection-footer",
|
|
55
57
|
"shortcut-btn",
|
|
56
58
|
"shortcut-btns",
|
|
@@ -671,9 +673,14 @@
|
|
|
671
673
|
"name": "AiPromptList Prompt 列表",
|
|
672
674
|
"slug": "ai-prompt-list",
|
|
673
675
|
"kind": "component",
|
|
674
|
-
"description": "
|
|
675
|
-
"aiSummary": "
|
|
676
|
-
"relatedComponents": [
|
|
676
|
+
"description": "\\ Prompt 选择列表,供 AiSlashInput 插入模板文本。",
|
|
677
|
+
"aiSummary": "\\ Prompt 选择列表,供 AiSlashInput 插入模板文本。 源码位置:src/components/chat-input/ai-slash-input/ai-prompt-list/ai-prompt-list.vue。",
|
|
678
|
+
"relatedComponents": [
|
|
679
|
+
{
|
|
680
|
+
"slug": "ai-slash-input",
|
|
681
|
+
"relation": "输入 \\ 时由 AiSlashInput tippy 菜单渲染"
|
|
682
|
+
}
|
|
683
|
+
],
|
|
677
684
|
"docFile": "docs/ai-prompt-list.md",
|
|
678
685
|
"domain": "input"
|
|
679
686
|
},
|
|
@@ -696,6 +703,25 @@
|
|
|
696
703
|
"docFile": "docs/ai-selection.md",
|
|
697
704
|
"domain": "input"
|
|
698
705
|
},
|
|
706
|
+
{
|
|
707
|
+
"name": "AiSkillList Skill 列表",
|
|
708
|
+
"slug": "ai-skill-list",
|
|
709
|
+
"kind": "component",
|
|
710
|
+
"description": "/ Skill 选择列表,供 AiSlashInput 插入 Skill 标签。",
|
|
711
|
+
"aiSummary": "/ Skill 选择列表,供 AiSlashInput 插入 Skill 标签。 无 icon 或 icon 加载失败时展示 skill_name 首字母 fallback。 源码位置:src/components/chat-input/ai-slash-input/ai-skill-list/ai-skill-list.vue。",
|
|
712
|
+
"relatedComponents": [
|
|
713
|
+
{
|
|
714
|
+
"slug": "ai-slash-input",
|
|
715
|
+
"relation": "输入 / 时由 AiSlashInput tippy 菜单渲染"
|
|
716
|
+
},
|
|
717
|
+
{
|
|
718
|
+
"slug": "chat-input",
|
|
719
|
+
"relation": "经 ChatInput.skills 透传数据源"
|
|
720
|
+
}
|
|
721
|
+
],
|
|
722
|
+
"docFile": "docs/ai-skill-list.md",
|
|
723
|
+
"domain": "input"
|
|
724
|
+
},
|
|
699
725
|
{
|
|
700
726
|
"name": "AiSlashEditor 富文本编辑器",
|
|
701
727
|
"slug": "ai-slash-editor",
|
|
@@ -710,9 +736,22 @@
|
|
|
710
736
|
"name": "AiSlashInput 富文本命令输入",
|
|
711
737
|
"slug": "ai-slash-input",
|
|
712
738
|
"kind": "component",
|
|
713
|
-
"description": "ChatInput 内部富文本输入,支持 / Prompt 与 @ 资源标签。",
|
|
714
|
-
"aiSummary": "ChatInput 内部富文本输入,支持 / Prompt 与 @ 资源标签。 源码位置:src/components/chat-input/ai-slash-input/ai-slash-input.vue。",
|
|
715
|
-
"relatedComponents": [
|
|
739
|
+
"description": "ChatInput 内部富文本输入,支持 / Skill、\\ Prompt 与 @ 资源标签。",
|
|
740
|
+
"aiSummary": "ChatInput 内部富文本输入,支持 / Skill、\\ Prompt 与 @ 资源标签。 源码位置:src/components/chat-input/ai-slash-input/ai-slash-input.vue。",
|
|
741
|
+
"relatedComponents": [
|
|
742
|
+
{
|
|
743
|
+
"slug": "ai-skill-list",
|
|
744
|
+
"relation": "输入 / 时渲染 Skill 选择列表"
|
|
745
|
+
},
|
|
746
|
+
{
|
|
747
|
+
"slug": "ai-prompt-list",
|
|
748
|
+
"relation": "输入 \\ 时渲染 Prompt 选择列表"
|
|
749
|
+
},
|
|
750
|
+
{
|
|
751
|
+
"slug": "ai-slash-menu",
|
|
752
|
+
"relation": "输入 @ 时渲染资源选择菜单"
|
|
753
|
+
}
|
|
754
|
+
],
|
|
716
755
|
"docFile": "docs/ai-slash-input.md",
|
|
717
756
|
"domain": "input"
|
|
718
757
|
},
|
|
@@ -749,6 +788,10 @@
|
|
|
749
788
|
"slug": "chat-container",
|
|
750
789
|
"relation": "顶层聊天布局中作为输入区子组件"
|
|
751
790
|
},
|
|
791
|
+
{
|
|
792
|
+
"slug": "model-selector",
|
|
793
|
+
"relation": "传入 models 后在发送按钮左侧默认展示模型选择器"
|
|
794
|
+
},
|
|
752
795
|
{
|
|
753
796
|
"slug": "cite-content",
|
|
754
797
|
"relation": "消息引用区展示选中的上下文片段"
|
|
@@ -796,6 +839,25 @@
|
|
|
796
839
|
"docFile": "docs/input-info-alert.md",
|
|
797
840
|
"domain": "input"
|
|
798
841
|
},
|
|
842
|
+
{
|
|
843
|
+
"name": "ModelSelector 模型选择器",
|
|
844
|
+
"slug": "model-selector",
|
|
845
|
+
"kind": "component",
|
|
846
|
+
"description": "聊天输入区的模型下拉选择器,支持搜索过滤、能力标签与键盘导航。",
|
|
847
|
+
"aiSummary": "聊天输入区的模型下拉选择器,支持搜索过滤、能力标签与键盘导航。 源码位置:src/components/chat-input/model-selector/model-selector.vue。",
|
|
848
|
+
"relatedComponents": [
|
|
849
|
+
{
|
|
850
|
+
"slug": "chat-input",
|
|
851
|
+
"relation": "传入 models 后在发送按钮左侧默认渲染"
|
|
852
|
+
},
|
|
853
|
+
{
|
|
854
|
+
"slug": "input-attachment",
|
|
855
|
+
"relation": "通过 before-send 插槽与发送按钮成组布局"
|
|
856
|
+
}
|
|
857
|
+
],
|
|
858
|
+
"docFile": "docs/model-selector.md",
|
|
859
|
+
"domain": "input"
|
|
860
|
+
},
|
|
799
861
|
{
|
|
800
862
|
"name": "SelectionFooter 多选操作栏",
|
|
801
863
|
"slug": "selection-footer",
|
|
@@ -1393,8 +1455,8 @@
|
|
|
1393
1455
|
"name": "ChatContainer 聊天容器",
|
|
1394
1456
|
"slug": "chat-container",
|
|
1395
1457
|
"kind": "component",
|
|
1396
|
-
"description": "
|
|
1397
|
-
"aiSummary": "
|
|
1458
|
+
"description": "完整对话容器,组合消息列表、输入区、模型选择、快捷指令、执行摘要、分享选择和自定义 Tab。",
|
|
1459
|
+
"aiSummary": "完整对话容器,组合消息列表、输入区、模型选择、快捷指令、执行摘要、分享选择和自定义 Tab。 透传 models / selectedModel;支持 welcomeTitle 与 #welcome。 源码位置:src/components/chat-container/chat-container.vue。",
|
|
1398
1460
|
"relatedComponents": [
|
|
1399
1461
|
{
|
|
1400
1462
|
"slug": "message-container",
|
|
@@ -1404,6 +1466,10 @@
|
|
|
1404
1466
|
"slug": "chat-input",
|
|
1405
1467
|
"relation": "对话输入与快捷指令入口"
|
|
1406
1468
|
},
|
|
1469
|
+
{
|
|
1470
|
+
"slug": "model-selector",
|
|
1471
|
+
"relation": "透传 models / selectedModel,在输入区展示模型选择器"
|
|
1472
|
+
},
|
|
1407
1473
|
{
|
|
1408
1474
|
"slug": "shortcut-render",
|
|
1409
1475
|
"relation": "快捷指令表单浮层"
|
package/dist/mcp/index.js
CHANGED
|
File without changes
|
package/dist/types/tool.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { Component, VNode } from 'vue';
|
|
2
|
+
import type { ToolIcons } from '../icons/tools';
|
|
2
3
|
import type { TippyOptions } from 'vue-tippy';
|
|
3
4
|
export declare enum MessageToolsStatus {
|
|
4
5
|
Disabled = "disabled",// 禁用
|
|
@@ -7,6 +8,9 @@ export declare enum MessageToolsStatus {
|
|
|
7
8
|
export type AITippyProps = Partial<Pick<TippyOptions, 'appendTo' | 'placement' | 'zIndex'>>;
|
|
8
9
|
export interface IToolBtn {
|
|
9
10
|
description?: string;
|
|
10
|
-
|
|
11
|
+
hidden?: boolean;
|
|
12
|
+
icon?: Component | VNode;
|
|
13
|
+
id?: (string & {}) | ToolIcons;
|
|
11
14
|
name?: string;
|
|
15
|
+
triggerSelection?: boolean;
|
|
12
16
|
}
|