@blueking/chat-x 0.0.48-beta.1 → 0.0.49-beta.2

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.
Files changed (52) hide show
  1. package/dist/ag-ui/types/constants.d.ts +1 -0
  2. package/dist/ag-ui/types/file.d.ts +23 -0
  3. package/dist/ag-ui/types/index.d.ts +1 -0
  4. package/dist/ag-ui/types/messages.d.ts +2 -0
  5. package/dist/components/chat-message/assistant-message/assistant-message.vue.d.ts +12 -1
  6. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-file-card.vue.d.ts +12 -0
  7. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/artifact-preview-host.vue.d.ts +7 -0
  8. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/preview-strategy.d.ts +9 -0
  9. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/renderers/html-preview.vue.d.ts +6 -0
  10. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/renderers/markdown-preview.vue.d.ts +6 -0
  11. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/renderers/txt-preview.vue.d.ts +6 -0
  12. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/renderers/url-iframe-preview.vue.d.ts +6 -0
  13. package/dist/components/chat-message/assistant-message/message-artifacts/artifact-preview/use-artifact-preview-loader.d.ts +23 -0
  14. package/dist/components/chat-message/assistant-message/message-artifacts/file-artifact-panel.vue.d.ts +12 -0
  15. package/dist/components/chat-message/assistant-message/message-artifacts/file-icon.d.ts +29 -0
  16. package/dist/components/chat-message/assistant-message/message-artifacts/message-artifacts.vue.d.ts +9 -0
  17. package/dist/components/chat-message/interrupt-message/user-question/use-user-question.d.ts +7 -2
  18. package/dist/components/chat-message/user-message/user-message.vue.d.ts +14 -2
  19. package/dist/composables/index.d.ts +1 -0
  20. package/dist/composables/use-artifact-preview.d.ts +56 -0
  21. package/dist/composables/use-custom-tab.d.ts +2 -0
  22. package/dist/composables/use-message-group.d.ts +433 -0
  23. package/dist/icons/file.d.ts +24 -0
  24. package/dist/icons/index.d.ts +1 -0
  25. package/dist/index.css +1 -1
  26. package/dist/index.js +2217 -1689
  27. package/dist/index.js.map +1 -1
  28. package/dist/lang/lang.d.ts +8 -1
  29. package/dist/mcp/generated/docs/activity-message.md +122 -97
  30. package/dist/mcp/generated/docs/assistant-message.md +125 -62
  31. package/dist/mcp/generated/docs/chat-container.md +97 -18
  32. package/dist/mcp/generated/docs/chat-input.md +2 -10
  33. package/dist/mcp/generated/docs/constants.md +3 -1
  34. package/dist/mcp/generated/docs/content-render.md +2 -10
  35. package/dist/mcp/generated/docs/file-artifact-panel.md +275 -0
  36. package/dist/mcp/generated/docs/info-message.md +29 -12
  37. package/dist/mcp/generated/docs/interrupt.md +1 -0
  38. package/dist/mcp/generated/docs/loading-message.md +36 -17
  39. package/dist/mcp/generated/docs/message-container.md +4 -21
  40. package/dist/mcp/generated/docs/message-render.md +47 -59
  41. package/dist/mcp/generated/docs/messages.md +5 -0
  42. package/dist/mcp/generated/docs/reasoning-message.md +17 -20
  43. package/dist/mcp/generated/docs/tool-message.md +61 -45
  44. package/dist/mcp/generated/docs/toolcall-render.md +8 -8
  45. package/dist/mcp/generated/docs/use-artifact-preview.md +232 -0
  46. package/dist/mcp/generated/docs/use-custom-tab.md +18 -5
  47. package/dist/mcp/generated/docs/use-message-group.md +29 -0
  48. package/dist/mcp/generated/docs/user-message.md +185 -121
  49. package/dist/mcp/generated/docs/user-question-card.md +6 -3
  50. package/dist/mcp/generated/index.json +83 -13
  51. package/dist/mcp/index.js +0 -0
  52. package/package.json +20 -21
@@ -13,15 +13,16 @@
13
13
  <!-- FULL DOC -->
14
14
 
15
15
  # MessageRender 消息渲染器
16
+
16
17
  ## 源码事实
17
18
 
18
19
  - **源码位置**:`src/components/chat-message/message-render/message-render.vue`
19
20
  - **能力域**:消息系统
20
- - **能力说明**:按 message.role 分发到用户、助手、工具、推理、活动、中断等消息组件。
21
+ - **能力说明**:按 `message.role` 分发到用户、助手、工具、推理、活动、中断等消息组件。
21
22
 
22
- > **能力域**:消息系统
23
+ > **导出说明**:`MessageRender` **已**从 `@blueking/chat-x` 包入口导出,消费方可直接 import。下文 `MessageRenderComp` 为文档站相对路径 demo,与包入口行为一致。
23
24
 
24
- 统一的消息渲染入口,通过 `message.role` 字段自动派发到对应的子组件。整个渲染过程由一个 `computed` 属性完成,无额外状态。
25
+ 统一的消息渲染入口,通过 `message.role` 派发到对应子组件;由单个 `computed` 完成,无额外状态。
25
26
 
26
27
  ## 渲染架构
27
28
 
@@ -151,7 +152,7 @@ MessageRender
151
152
 
152
153
  ### 流式输出(streaming)
153
154
 
154
- `status: 'streaming'` 时,`AssistantMessage` 内部展示打字光标,内容可实时追加:
155
+ `status: 'streaming'` 时,默认回退的 `ContentRender` / `MarkdownContent` 会按流式规则补全未闭合语法;内容由外部逐步追加:
155
156
 
156
157
  ```vue
157
158
  <script setup lang="ts">
@@ -202,65 +203,74 @@ MessageRender
202
203
 
203
204
  ## 自定义内容渲染(default slot)
204
205
 
205
- `default` slot **仅对 `role: 'assistant'` 生效**,用于替换默认的 `ContentRender`。未提供 slot 时回退渲染 `<ContentRender :content="message.content" :status="message.status" />`。
206
+ `default` slot **仅对 `role: 'assistant'` 生效**,用于替换默认的 `ContentRender`。
207
+
208
+ 未提供 slot 时,内部回退为:
209
+
210
+ ```ts
211
+ h(ContentRender, { content: message.content || '', status: message.status }, /* codeHeader */)
212
+ ```
213
+
214
+ 自定义 slot 时,运行时参数来自 `AssistantMessage` 的 `v-bind`,**仅保证 `{ content }`**。需要 `status` 时请从外层 `message.status` 读取(不要依赖 slot 内的 `status`)。
206
215
 
207
216
  ```vue
208
217
  <template>
209
- <MessageRender
210
- :message="message"
211
- :on-action="handleAction"
212
- >
213
- <template #default="{ content, status }">
214
- <!-- 完全接管内容区域渲染 -->
218
+ <MessageRender :message="message">
219
+ <template #default="{ content }">
215
220
  <MyMarkdownRenderer
216
221
  :content="content"
217
- :streaming="status === 'streaming'"
222
+ :streaming="message.status === 'streaming'"
218
223
  />
219
224
  </template>
220
225
  </MessageRender>
221
226
  </template>
222
227
  ```
223
228
 
224
- slot 参数类型与 `AssistantMessage` 的 slot 保持一致(`Partial<AssistantMessage>`),主要使用:
225
-
226
- | 参数 | 类型 | 说明 |
227
- | --------- | --------------- | ------------ |
228
- | `content` | `string` | 消息内容 |
229
- | `status` | `MessageStatus` | 当前消息状态 |
229
+ | 参数 | 类型 | 说明 |
230
+ | --------- | -------- | ---------------------------- |
231
+ | `content` | `string` | 消息内容(运行时保证) |
230
232
 
231
- ## 与 MessageContainer 配合
233
+ ## 与 MessageContainer / ChatContainer 配合
232
234
 
233
- `MessageContainer` 的 `default` slot 中使用,可替换默认的 `MessageRender` 渲染逻辑:
235
+ 自定义 `ChatContainer` 的 `#message` 时,插槽参数只有 `message` / `messageToolsStatus` / `onInterruptResume`。用户消息工具相关回调需由外层自行绑定透传,否则删除/编辑/复制/引用会失效(AI 消息工具栏在 `MessageContainer` 内渲染,不受 `#message` 影响):
234
236
 
235
237
  ```vue
236
238
  <template>
237
- <MessageContainer
239
+ <ChatContainer
238
240
  :messages="messages"
239
241
  :message-status="messageStatus"
240
242
  :on-agent-action="handleAgentAction"
241
243
  :on-user-action="handleUserAction"
242
- @stop-streaming="handleStopStreaming"
244
+ :common-tippy-options="commonTippyOptions"
243
245
  >
244
- <template #default="{ message, messageToolsStatus }">
245
- <!-- 自定义 MessageRender 的行为 -->
246
+ <template #message="{ message, messageToolsStatus, onInterruptResume }">
246
247
  <MessageRender
247
248
  :message="message"
248
249
  :message-tools-status="messageToolsStatus"
249
250
  :on-action="handleUserAction"
250
- :on-input-confirm="handleInputConfirm"
251
+ :on-input-confirm="(content, docSchema) => handleUserInputConfirm(message, content, docSchema)"
252
+ :on-shortcut-confirm="formModel => handleUserShortcutConfirm(message, formModel)"
253
+ :tippy-options="commonTippyOptions"
254
+ :on-interrupt-resume="onInterruptResume"
251
255
  >
252
256
  <template
253
257
  v-if="message.role === 'assistant'"
254
- #default="{ content, status }"
258
+ #default="{ content }"
255
259
  >
256
260
  <MyCustomContent
257
261
  :content="content"
258
- :status="status"
262
+ :status="message.status"
263
+ />
264
+ </template>
265
+ <template #codeHeader="{ language, token }">
266
+ <MyCodeActions
267
+ :language="language"
268
+ :token="token"
259
269
  />
260
270
  </template>
261
271
  </MessageRender>
262
272
  </template>
263
- </MessageContainer>
273
+ </ChatContainer>
264
274
  </template>
265
275
  ```
266
276
 
@@ -280,11 +290,11 @@ slot 参数类型与 `AssistantMessage` 的 slot 保持一致(`Partial<Assista
280
290
 
281
291
  ### Slots
282
292
 
283
- | 插槽名 | 参数 | 说明 |
284
- | ---------------- | -------------------------------------------- | ------------------------------------------------------------------------------------------------------- |
285
- | answeredQuestion | `{ item, index, status }` | 自定义 UserQuestion 已回答回显,透传给 InterruptMessageRender → UserQuestionAnsweredCard 的 `#answer` |
286
- | codeHeader | `{ language: string; token: Token[] }` | 代码块头部自定义操作区域,透传给 ContentRender → MarkdownContent → CodeContent;**仅对 assistant 生效** |
287
- | default | `{ content: string, status: MessageStatus }` | 替换 AssistantMessage 的内容区域渲染;**仅对 `role: 'assistant'` 生效** |
293
+ | 插槽名 | 参数 | 说明 |
294
+ | ---------------- | -------------------------------------- | ------------------------------------------------------------------------------------------------------- |
295
+ | answeredQuestion | `{ item, index, status }` | 自定义 UserQuestion 已回答回显,透传给 InterruptMessageRender → UserQuestionAnsweredCard 的 `#answer` |
296
+ | codeHeader | `{ language: string; token: Token[] }` | 代码块头部自定义操作区域,透传给 ContentRender → MarkdownContent → CodeContent;**仅对 assistant 生效** |
297
+ | default | `{ content: string }` | 替换 AssistantMessage 内容区;**仅对 assistant 生效**;运行时仅保证 `content`(`status` 请读外层 message) |
288
298
 
289
299
  ## 消息类型映射
290
300
 
@@ -305,34 +315,12 @@ slot 参数类型与 `AssistantMessage` 的 slot 保持一致(`Partial<Assista
305
315
  ```typescript
306
316
  import { MessageRole, MessageStatus, MessageToolsStatus, type Message, type IToolBtn } from '@blueking/chat-x';
307
317
 
308
- // 消息角色
309
- enum MessageRole {
310
- User = 'user',
311
- Assistant = 'assistant',
312
- Info = 'info',
313
- Reasoning = 'reasoning',
314
- Tool = 'tool',
315
- Activity = 'activity',
316
- Loading = 'loading',
317
- }
318
-
319
- // 消息状态
320
- enum MessageStatus {
321
- Pending = 'pending',
322
- Streaming = 'streaming',
323
- Complete = 'complete',
324
- Error = 'error',
325
- Stop = 'stop',
326
- Disabled = 'disabled',
327
- }
328
-
329
- // 工具按钮状态(仅转发给 UserMessage)
330
- enum MessageToolsStatus {
331
- Disabled = 'disabled',
332
- Hidden = 'hidden',
333
- }
318
+ // MessageRole / MessageStatus 完整枚举见 ../../types/constants
319
+ // MessageToolsStatus:Disabled | Hidden(仅转发给 UserMessage)
334
320
  ```
335
321
 
322
+ > `MessageRole` / `MessageStatus` 完整取值见 [常量枚举](../../types/constants)。
323
+
336
324
  ## 关联组件
337
325
 
338
326
  - [MessageContainer](/components/setup/message-container) — 内部按组调用以渲染每条消息
@@ -144,6 +144,9 @@ enum MessageStatus {
144
144
  // 已完成
145
145
  Complete = 'complete',
146
146
 
147
+ // 已完成(与 Complete 同义,兼容协议/后端返回的 completed)
148
+ Completed = 'completed',
149
+
147
150
  // 已禁用
148
151
  Disabled = 'disabled',
149
152
 
@@ -170,6 +173,8 @@ enum MessageStatus {
170
173
  }
171
174
  ```
172
175
 
176
+ 完整取值与说明见 [常量枚举 · MessageStatus](./constants#messagestatus)。
177
+
173
178
  ## 具体消息类型
174
179
 
175
180
  ### UserMessage
@@ -12,13 +12,14 @@
12
12
  <!-- FULL DOC -->
13
13
 
14
14
  # ReasoningMessage 推理消息
15
+
15
16
  ## 源码事实
16
17
 
17
18
  - **源码位置**:`src/components/chat-message/reasoning-message/reasoning-message.vue`
18
19
  - **能力域**:消息系统
19
20
  - **能力说明**:渲染推理过程,覆盖加载、错误与 Markdown 内容展示。
20
21
 
21
- > **能力域**:消息系统
22
+ > **导出说明**:`ReasoningMessage` **未**从包入口导出(入口同名是 TS interface)。消费方经 `MessageRender` / `MessageContainer` 使用。下文 `ReasoningMessageComp` 为文档站内部示例。
22
23
 
23
24
  AI 思维链(Chain-of-Thought)推理过程展示组件。由**可点击标题栏**和**内容区域**组成,内容区支持 Markdown 渲染。`duration` 传入后自动折叠一次,用户可随时点击标题展开/收起。
24
25
 
@@ -44,17 +45,19 @@ AI 思维链(Chain-of-Thought)推理过程展示组件。由**可点击标
44
45
 
45
46
  ```vue
46
47
  <template>
47
- <ReasoningMessage
48
- :content="content"
49
- :status="status"
50
- />
48
+ <MessageRender :message="message" />
51
49
  </template>
52
50
 
53
51
  <script setup lang="ts">
54
- import { ReasoningMessage, MessageStatus } from '@blueking/chat-x';
55
-
56
- const status = MessageStatus.Complete;
57
- const content = ['让我分析一下这个问题...', '首先需要考虑以下几个方面...'];
52
+ import { MessageRender, MessageRole, MessageStatus } from '@blueking/chat-x';
53
+
54
+ const message = {
55
+ id: '1',
56
+ messageId: '1',
57
+ role: MessageRole.Reasoning,
58
+ status: MessageStatus.Complete,
59
+ content: ['让我分析一下这个问题...', '首先需要考虑以下几个方面...'],
60
+ };
58
61
  </script>
59
62
  ```
60
63
 
@@ -113,11 +116,12 @@ const { stop } = watch(
113
116
  通过 `v-model:collapsed` 从外部读取或设置折叠状态:
114
117
 
115
118
  ```vue
119
+ <!-- 文档站内部示例:组件本体支持 v-model:collapsed;消费方一般经 MessageRender 渲染 -->
116
120
  <template>
117
121
  <button @click="collapsed = !collapsed">
118
122
  {{ collapsed ? '展开推理' : '收起推理' }}
119
123
  </button>
120
- <ReasoningMessage
124
+ <ReasoningMessageComp
121
125
  v-model:collapsed="collapsed"
122
126
  :content="content"
123
127
  :status="status"
@@ -127,7 +131,7 @@ const { stop } = watch(
127
131
 
128
132
  <script setup lang="ts">
129
133
  import { ref } from 'vue';
130
- import { ReasoningMessage, MessageStatus } from '@blueking/chat-x';
134
+ import { MessageStatus } from '@blueking/chat-x';
131
135
 
132
136
  const collapsed = ref(false);
133
137
  const status = MessageStatus.Complete;
@@ -220,17 +224,10 @@ interface ReasoningMessage {
220
224
  duration?: number; // 推理耗时(毫秒)
221
225
  name?: string;
222
226
  }
223
-
224
- enum MessageStatus {
225
- Pending = 'pending',
226
- Streaming = 'streaming',
227
- Complete = 'complete',
228
- Success = 'success',
229
- Error = 'error',
230
- Stop = 'stop',
231
- }
232
227
  ```
233
228
 
229
+ > `MessageStatus` 完整取值见 [常量枚举](../../types/constants)。本组件完成态识别 `complete` / `success`(与标题文案表一致)。
230
+
234
231
  ## 关联组件
235
232
 
236
233
  - [MessageRender](/components/message/message-render) — reasoning 角色由其实例化
@@ -1,7 +1,7 @@
1
1
  <!-- AI SUMMARY -->
2
2
  ## 快速了解
3
3
 
4
- 渲染工具返回内容,JSON 场景交给 DescPanel 展示。 源码位置:src/components/chat-message/tool-message/tool-message.vue。
4
+ 渲染工具返回内容;DescPanel 解析 JSON key-value,嵌套值 JSON.stringify 后经 HighlightKeyword 展示。 源码位置:src/components/chat-message/tool-message/tool-message.vue。
5
5
 
6
6
  ### 关联组件
7
7
  - **assistant-message** — 结果常作为 assistant 消息中 toolCall.toolMessage 内联展示
@@ -12,51 +12,57 @@
12
12
  <!-- FULL DOC -->
13
13
 
14
14
  # ToolMessage 工具消息
15
+
15
16
  ## 源码事实
16
17
 
17
18
  - **源码位置**:`src/components/chat-message/tool-message/tool-message.vue`
18
19
  - **能力域**:消息系统
19
- - **能力说明**:渲染工具返回内容,JSON 场景交给 DescPanel 展示。
20
+ - **能力说明**:渲染工具返回内容,JSON 场景交给 DescPanel + HighlightKeyword 展示。
20
21
 
21
- > **能力域**:消息系统
22
+ > **导出说明**:`ToolMessage` **未**从包入口导出(入口同名是 TS interface)。消费方经 `MessageRender` / `ToolcallRender` 使用。下文 `ToolMessageComp` 为文档站内部示例。
22
23
 
23
- 工具(Function Call)执行结果展示组件。内部通过 `DescPanel` 渲染,标题固定为"返回内容",支持将 JSON 自动解析为 key-value 列表。
24
+ 工具执行结果展示组件。内部通过 `DescPanel` 渲染,标题固定为「返回内容」,可解析 JSON key-value 列表。
24
25
 
25
- > **通常不需要直接使用此组件**。`ToolcallRender` 在 `toolCall.toolMessage` 有值时会自动内联渲染;`MessageContainer` 处理 `role: 'tool'` 消息时也会通过 `MessageRender` 自动渲染。
26
+ > **通常不需要直接使用**。`ToolcallRender` 在 `toolCall.toolMessage` 有值时内联渲染;`role: 'tool'` 也可由 `MessageRender` 渲染。
26
27
 
27
28
  ## 渲染架构
28
29
 
29
30
  ```
30
31
  ToolMessage
31
- └── DescPanel(desc="content || (typeof error === 'string' ? error : undefined)",title="返回内容")
32
- ├── JSON.parse(desc) 成功且结果为 object/array
33
- │ └── key-value 列表(v-for 遍历)
34
- 值超长时截断 + overflow-tips tooltip
35
- └── 其他(parse 失败 / 结果为基本类型)
36
- └── 纯文本展示
32
+ └── DescPanel(desc = content || (typeof error === 'string' ? error : undefined),title="返回内容")
33
+ ├── JSON.parse 成功且结果为 object/array(排除 null)
34
+ │ └── key-value 列表
35
+ · key / value 均经 HighlightKeyword 展示
36
+ │ · 嵌套 object/array:JSON.stringify 后展示(无 overflow-tips)
37
+ └── 其他(parse 失败 / 标量)
38
+ └── HighlightKeyword 纯文本
37
39
  ```
38
40
 
39
41
  ## 基础用法
40
42
 
41
43
  ```vue
42
44
  <template>
43
- <ToolMessage
44
- :content="content"
45
- tool-call-id="call_1"
46
- :duration="850"
47
- />
45
+ <MessageRender :message="message" />
48
46
  </template>
49
47
 
50
48
  <script setup lang="ts">
51
- import { ToolMessage } from '@blueking/chat-x';
52
-
53
- const content = JSON.stringify({
54
- city: '北京',
55
- temperature: 22,
56
- weather: '晴',
57
- humidity: '45%',
58
- wind: '东北风 3 级',
59
- });
49
+ import { MessageRender, MessageRole, MessageStatus } from '@blueking/chat-x';
50
+
51
+ const message = {
52
+ id: 't1',
53
+ messageId: 't1',
54
+ role: MessageRole.Tool,
55
+ status: MessageStatus.Complete,
56
+ toolCallId: 'call_1',
57
+ duration: 850,
58
+ content: JSON.stringify({
59
+ city: '北京',
60
+ temperature: 22,
61
+ weather: '晴',
62
+ humidity: '45%',
63
+ wind: '东北风 3 级',
64
+ }),
65
+ };
60
66
  </script>
61
67
  ```
62
68
 
@@ -70,18 +76,22 @@ ToolMessage
70
76
 
71
77
  ```vue
72
78
  <template>
73
- <ToolMessage
74
- content=""
75
- :error="error"
76
- tool-call-id="call_3"
77
- :duration="5000"
78
- />
79
+ <MessageRender :message="message" />
79
80
  </template>
80
81
 
81
82
  <script setup lang="ts">
82
- import { ToolMessage } from '@blueking/chat-x';
83
-
84
- const error = 'Connection timeout: database server is unreachable (timeout: 5000ms)';
83
+ import { MessageRender, MessageRole, MessageStatus } from '@blueking/chat-x';
84
+
85
+ const message = {
86
+ id: 't3',
87
+ messageId: 't3',
88
+ role: MessageRole.Tool,
89
+ status: MessageStatus.Error,
90
+ toolCallId: 'call_3',
91
+ duration: 5000,
92
+ content: '',
93
+ error: 'Connection timeout: database server is unreachable (timeout: 5000ms)',
94
+ };
85
95
  </script>
86
96
  ```
87
97
 
@@ -98,25 +108,27 @@ ToolMessage
98
108
  | 解析失败(非法 JSON) | 捕获异常,返回原字符串 | 纯文本 |
99
109
  | `content` 和 `error` 均为空 | `''` → 解析失败 | 空内容区 |
100
110
 
101
- > **注意**:JSON 数组在 JavaScript 中 `typeof [] === 'object'` `true`,因此数组会以 `0:`、`1:`、`2:` 为键渲染为 key-value 列表,而**非**纯文本。
111
+ > **注意**:JSON 数组 `typeof [] === 'object'`,会以 `0:`、`1:`、`2:` 为键渲染为列表,而非整段纯文本。
102
112
 
103
- **嵌套对象值的处理**:当 value 本身是对象时,`{{ value }}` 会渲染为 `[object Object]`,但 hover 展示的 overflow-tips 会显示 `JSON.stringify(value)` 的完整字符串。
113
+ **嵌套对象 / 数组值**:`DescPanel` `JSON.stringify(value)` 转成字符串后交给 `HighlightKeyword`,**不再**使用 overflow-tips。
104
114
 
105
115
  ```typescript
106
- // ✅ 渲染为 key-value 列表
116
+ // key-value 列表
107
117
  const jsonObject = '{"city":"北京","temperature":22}';
108
118
 
109
- // ✅ 渲染为 index-keyed 列表(0: item1, 1: item2)
119
+ // index-keyed 列表(0: item1, 1: item2)
110
120
  const jsonArray = '["item1","item2","item3"]';
111
121
 
112
- // 渲染为纯文本(基本类型)
113
- const jsonNumber = '42';
114
- const jsonBool = 'true';
122
+ // 嵌套值 stringify 展示
123
+ const nested = '{"result":"success","data":{"city":"北京","meta":{"humidity":45}}}';
115
124
 
116
- // 渲染为纯文本(解析失败)
125
+ // 标量 / 非法 JSON → 纯文本
126
+ const jsonNumber = '42';
117
127
  const plainText = '查询成功,共返回 10 条记录。';
118
128
  ```
119
129
 
130
+ **嵌套 JSON 渲染效果**
131
+
120
132
  ## 与 ToolcallRender 的关系
121
133
 
122
134
  `ToolcallRender` 在详情面板展开时,若 `toolCall.toolMessage` 有值,会在底部内联渲染 `ToolMessage`:
@@ -186,8 +198,8 @@ const messages = [
186
198
 
187
199
  | 属性名 | 类型 | 说明 |
188
200
  | ---------- | ------------------ | ------------------------------------------------------------------------------- |
189
- | content | `string` | 工具执行返回内容;与 `error` 通过 `\|\|` 决定优先级,**truthy 时 error 被忽略** |
190
- | error | `string` | 工具执行错误信息;仅当 `content` 为 falsy `error``string` 类型时展示 |
201
+ | content | `string` | 工具执行返回内容;与 `error` 通过 `\|\|` 决定优先级,**truthy 时 error 被忽略** |
202
+ | error | `boolean \| string` | 类型上可为 boolean;**仅当为 `string` 且 contentfalsy 时**才会展示 |
191
203
  | toolCallId | `string` | 关联的工具调用 ID(透传,组件内不使用) |
192
204
  | duration | `number` | 工具执行耗时(毫秒,透传,组件内不使用) |
193
205
  | status | `MessageStatus` | 消息状态(透传,组件内不使用) |
@@ -210,11 +222,15 @@ interface ToolMessage {
210
222
  content: string;
211
223
  toolCallId: string; // 关联的 ToolCall.id
212
224
  duration: number; // 工具执行耗时(毫秒)
213
- error?: string; // 执行错误信息
225
+ error?: boolean | string; // 仅 string 会展示在 DescPanel
214
226
  name?: string;
215
227
  }
216
228
  ```
217
229
 
230
+ ### Events / Slots / Expose
231
+
232
+ 无。
233
+
218
234
  ## 关联组件
219
235
 
220
236
  - [AssistantMessage](/components/message/assistant-message) — toolCall.toolMessage 内联场景
@@ -78,14 +78,14 @@
78
78
 
79
79
  `status` prop 同时控制头部的 CSS class(`toolcall-status-{status}`)、背景/边框颜色、状态文案和 Loading 动画:
80
80
 
81
- | `status` | 状态文案 | 背景色 | 边框色 | Loading |
82
- | ----------------------- | -------- | ----------------- | --------- | ------- |
83
- | `pending` / `streaming` | 调用中 | `#fafbfd` | `#dcdee5` | ✓ |
84
- | `complete` / `success` | 调用成功 | `#ebfaf0` | `#a1e3ba` | - |
85
- | `error` | 调用失败 | `#fff0f0` | `#f8b4b4` | - |
86
- | 其他 / `undefined` | 调用中 | —(无匹配 class) | — | - |
87
-
88
- > **说明**:`statusTitle` `switch` 语句中 `default` 与 `case Pending` 共享同一返回值,`streaming` 和未知 status 均命中 `default` 分支,显示"调用中"。Loading 动画由 `v-if="status === 'pending' || status === 'streaming'"` 单独控制。
81
+ | `status` | 状态文案 | 背景色 | 边框色 | Loading |
82
+ | ------------------------------------- | -------- | ----------------- | --------- | ------- |
83
+ | `pending` / `streaming` | 调用中 | `#fafbfd` | `#dcdee5` | ✓ |
84
+ | `complete` / `completed` / `success` | 调用成功 | `#ebfaf0` | `#a1e3ba` | - |
85
+ | `error` | 调用失败 | `#fff0f0` | `#f8b4b4` | - |
86
+ | 其他 / `undefined` | 调用中 | —(无匹配 class) | — | - |
87
+
88
+ > **说明**:`statusTitle` `Completed`(`completed`)与 `Complete` / `Success` 一并视为成功;主题 `$toolcallStatusMap` 同步提供 `completed` 色值。`default` 与 `case Pending` 共享「调用中」文案,`streaming` 与未知 status 命中 `default`。Loading `v-if="status === 'pending' || status === 'streaming'"` 控制。
89
89
 
90
90
  **三种状态对比**
91
91