AstrBot 4.6.1__py3-none-any.whl → 4.7.1__py3-none-any.whl

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 (37) hide show
  1. astrbot/core/agent/mcp_client.py +3 -3
  2. astrbot/core/agent/runners/base.py +7 -4
  3. astrbot/core/agent/runners/coze/coze_agent_runner.py +367 -0
  4. astrbot/core/agent/runners/dashscope/dashscope_agent_runner.py +403 -0
  5. astrbot/core/agent/runners/dify/dify_agent_runner.py +336 -0
  6. astrbot/core/{utils → agent/runners/dify}/dify_api_client.py +51 -13
  7. astrbot/core/agent/runners/tool_loop_agent_runner.py +0 -6
  8. astrbot/core/config/default.py +141 -26
  9. astrbot/core/config/i18n_utils.py +110 -0
  10. astrbot/core/core_lifecycle.py +11 -13
  11. astrbot/core/db/po.py +1 -1
  12. astrbot/core/db/sqlite.py +2 -2
  13. astrbot/core/pipeline/process_stage/method/agent_request.py +48 -0
  14. astrbot/core/pipeline/process_stage/method/{llm_request.py → agent_sub_stages/internal.py} +13 -34
  15. astrbot/core/pipeline/process_stage/method/agent_sub_stages/third_party.py +202 -0
  16. astrbot/core/pipeline/process_stage/method/star_request.py +1 -1
  17. astrbot/core/pipeline/process_stage/stage.py +8 -5
  18. astrbot/core/pipeline/result_decorate/stage.py +15 -5
  19. astrbot/core/provider/manager.py +43 -41
  20. astrbot/core/star/session_llm_manager.py +0 -107
  21. astrbot/core/star/session_plugin_manager.py +0 -81
  22. astrbot/core/umop_config_router.py +19 -0
  23. astrbot/core/utils/migra_helper.py +73 -0
  24. astrbot/core/utils/shared_preferences.py +1 -28
  25. astrbot/dashboard/routes/chat.py +13 -1
  26. astrbot/dashboard/routes/config.py +20 -16
  27. astrbot/dashboard/routes/knowledge_base.py +0 -156
  28. astrbot/dashboard/routes/session_management.py +311 -606
  29. {astrbot-4.6.1.dist-info → astrbot-4.7.1.dist-info}/METADATA +1 -1
  30. {astrbot-4.6.1.dist-info → astrbot-4.7.1.dist-info}/RECORD +34 -30
  31. {astrbot-4.6.1.dist-info → astrbot-4.7.1.dist-info}/WHEEL +1 -1
  32. astrbot/core/provider/sources/coze_source.py +0 -650
  33. astrbot/core/provider/sources/dashscope_source.py +0 -207
  34. astrbot/core/provider/sources/dify_source.py +0 -285
  35. /astrbot/core/{provider/sources → agent/runners/coze}/coze_api_client.py +0 -0
  36. {astrbot-4.6.1.dist-info → astrbot-4.7.1.dist-info}/entry_points.txt +0 -0
  37. {astrbot-4.6.1.dist-info → astrbot-4.7.1.dist-info}/licenses/LICENSE +0 -0
@@ -4,7 +4,7 @@ import os
4
4
 
5
5
  from astrbot.core.utils.astrbot_path import get_astrbot_data_path
6
6
 
7
- VERSION = "4.6.1"
7
+ VERSION = "4.7.1"
8
8
  DB_PATH = os.path.join(get_astrbot_data_path(), "data_v4.db")
9
9
 
10
10
  # 默认配置
@@ -68,6 +68,10 @@ DEFAULT_CONFIG = {
68
68
  "dequeue_context_length": 1,
69
69
  "streaming_response": False,
70
70
  "show_tool_use_status": False,
71
+ "agent_runner_type": "local",
72
+ "dify_agent_runner_provider_id": "",
73
+ "coze_agent_runner_provider_id": "",
74
+ "dashscope_agent_runner_provider_id": "",
71
75
  "unsupported_streaming_strategy": "realtime_segmenting",
72
76
  "max_agent_step": 30,
73
77
  "tool_call_timeout": 60,
@@ -141,7 +145,16 @@ DEFAULT_CONFIG = {
141
145
  }
142
146
 
143
147
 
144
- # 配置项的中文描述、值类型
148
+ """
149
+ AstrBot v3 时代的配置元数据,目前仅承担以下功能:
150
+
151
+ 1. 保存配置时,配置项的类型验证
152
+ 2. WebUI 展示提供商和平台适配器模版
153
+
154
+ WebUI 的配置文件在 `CONFIG_METADATA_3` 中。
155
+
156
+ 未来将会逐步淘汰此配置元数据。
157
+ """
145
158
  CONFIG_METADATA_2 = {
146
159
  "platform_group": {
147
160
  "metadata": {
@@ -634,7 +647,7 @@ CONFIG_METADATA_2 = {
634
647
  },
635
648
  "words_count_threshold": {
636
649
  "type": "int",
637
- "hint": "超过这个字数的消息不会被分段回复。默认为 150",
650
+ "hint": "分段回复的字数上限。只有字数小于此值的消息才会被分段,超过此值的长消息将直接发送(不分段)。默认为 150",
638
651
  },
639
652
  "regex": {
640
653
  "type": "string",
@@ -1011,7 +1024,7 @@ CONFIG_METADATA_2 = {
1011
1024
  "id": "dify_app_default",
1012
1025
  "provider": "dify",
1013
1026
  "type": "dify",
1014
- "provider_type": "chat_completion",
1027
+ "provider_type": "agent_runner",
1015
1028
  "enable": True,
1016
1029
  "dify_api_type": "chat",
1017
1030
  "dify_api_key": "",
@@ -1025,20 +1038,20 @@ CONFIG_METADATA_2 = {
1025
1038
  "Coze": {
1026
1039
  "id": "coze",
1027
1040
  "provider": "coze",
1028
- "provider_type": "chat_completion",
1041
+ "provider_type": "agent_runner",
1029
1042
  "type": "coze",
1030
1043
  "enable": True,
1031
1044
  "coze_api_key": "",
1032
1045
  "bot_id": "",
1033
1046
  "coze_api_base": "https://api.coze.cn",
1034
1047
  "timeout": 60,
1035
- "auto_save_history": True,
1048
+ # "auto_save_history": True,
1036
1049
  },
1037
1050
  "阿里云百炼应用": {
1038
1051
  "id": "dashscope",
1039
1052
  "provider": "dashscope",
1040
1053
  "type": "dashscope",
1041
- "provider_type": "chat_completion",
1054
+ "provider_type": "agent_runner",
1042
1055
  "enable": True,
1043
1056
  "dashscope_app_type": "agent",
1044
1057
  "dashscope_api_key": "",
@@ -1087,7 +1100,7 @@ CONFIG_METADATA_2 = {
1087
1100
  "api_base": "",
1088
1101
  "model": "whisper-1",
1089
1102
  },
1090
- "Whisper(本地加载)": {
1103
+ "Whisper(Local)": {
1091
1104
  "hint": "启用前请 pip 安装 openai-whisper 库(N卡用户大约下载 2GB,主要是 torch 和 cuda,CPU 用户大约下载 1 GB),并且安装 ffmpeg。否则将无法正常转文字。",
1092
1105
  "provider": "openai",
1093
1106
  "type": "openai_whisper_selfhost",
@@ -1096,7 +1109,7 @@ CONFIG_METADATA_2 = {
1096
1109
  "id": "whisper_selfhost",
1097
1110
  "model": "tiny",
1098
1111
  },
1099
- "SenseVoice(本地加载)": {
1112
+ "SenseVoice(Local)": {
1100
1113
  "hint": "启用前请 pip 安装 funasr、funasr_onnx、torchaudio、torch、modelscope、jieba 库(默认使用CPU,大约下载 1 GB),并且安装 ffmpeg。否则将无法正常转文字。",
1101
1114
  "type": "sensevoice_stt_selfhost",
1102
1115
  "provider": "sensevoice",
@@ -1131,7 +1144,7 @@ CONFIG_METADATA_2 = {
1131
1144
  "pitch": "+0Hz",
1132
1145
  "timeout": 20,
1133
1146
  },
1134
- "GSV TTS(本地加载)": {
1147
+ "GSV TTS(Local)": {
1135
1148
  "id": "gsv_tts",
1136
1149
  "enable": False,
1137
1150
  "provider": "gpt_sovits",
@@ -1907,7 +1920,6 @@ CONFIG_METADATA_2 = {
1907
1920
  "enable": {
1908
1921
  "description": "启用",
1909
1922
  "type": "bool",
1910
- "hint": "是否启用。",
1911
1923
  },
1912
1924
  "key": {
1913
1925
  "description": "API Key",
@@ -2037,12 +2049,22 @@ CONFIG_METADATA_2 = {
2037
2049
  "unsupported_streaming_strategy": {
2038
2050
  "type": "string",
2039
2051
  },
2052
+ "agent_runner_type": {
2053
+ "type": "string",
2054
+ },
2055
+ "dify_agent_runner_provider_id": {
2056
+ "type": "string",
2057
+ },
2058
+ "coze_agent_runner_provider_id": {
2059
+ "type": "string",
2060
+ },
2061
+ "dashscope_agent_runner_provider_id": {
2062
+ "type": "string",
2063
+ },
2040
2064
  "max_agent_step": {
2041
- "description": "工具调用轮数上限",
2042
2065
  "type": "int",
2043
2066
  },
2044
2067
  "tool_call_timeout": {
2045
- "description": "工具调用超时时间(秒)",
2046
2068
  "type": "int",
2047
2069
  },
2048
2070
  },
@@ -2176,34 +2198,87 @@ CONFIG_METADATA_2 = {
2176
2198
  }
2177
2199
 
2178
2200
 
2201
+ """
2202
+ v4.7.0 之后,name, description, hint 等字段已经实现 i18n 国际化。国际化资源文件位于:
2203
+
2204
+ - dashboard/src/i18n/locales/en-US/features/config-metadata.json
2205
+ - dashboard/src/i18n/locales/zh-CN/features/config-metadata.json
2206
+
2207
+ 如果在此文件中添加了新的配置字段,请务必同步更新上述两个国际化资源文件。
2208
+ """
2179
2209
  CONFIG_METADATA_3 = {
2180
2210
  "ai_group": {
2181
2211
  "name": "AI 配置",
2182
2212
  "metadata": {
2183
- "ai": {
2184
- "description": "模型",
2213
+ "agent_runner": {
2214
+ "description": "Agent 执行方式",
2215
+ "hint": "选择 AI 对话的执行器,默认为 AstrBot 内置 Agent 执行器,可使用 AstrBot 内的知识库、人格、工具调用功能。如果不打算接入 Dify 或 Coze 等第三方 Agent 执行器,不需要修改此节。",
2185
2216
  "type": "object",
2186
2217
  "items": {
2187
2218
  "provider_settings.enable": {
2188
- "description": "启用大语言模型聊天",
2219
+ "description": "启用",
2189
2220
  "type": "bool",
2221
+ "hint": "AI 对话总开关",
2222
+ },
2223
+ "provider_settings.agent_runner_type": {
2224
+ "description": "执行器",
2225
+ "type": "string",
2226
+ "options": ["local", "dify", "coze", "dashscope"],
2227
+ "labels": ["内置 Agent", "Dify", "Coze", "阿里云百炼应用"],
2228
+ "condition": {
2229
+ "provider_settings.enable": True,
2230
+ },
2231
+ },
2232
+ "provider_settings.coze_agent_runner_provider_id": {
2233
+ "description": "Coze Agent 执行器提供商 ID",
2234
+ "type": "string",
2235
+ "_special": "select_agent_runner_provider:coze",
2236
+ "condition": {
2237
+ "provider_settings.agent_runner_type": "coze",
2238
+ "provider_settings.enable": True,
2239
+ },
2240
+ },
2241
+ "provider_settings.dify_agent_runner_provider_id": {
2242
+ "description": "Dify Agent 执行器提供商 ID",
2243
+ "type": "string",
2244
+ "_special": "select_agent_runner_provider:dify",
2245
+ "condition": {
2246
+ "provider_settings.agent_runner_type": "dify",
2247
+ "provider_settings.enable": True,
2248
+ },
2249
+ },
2250
+ "provider_settings.dashscope_agent_runner_provider_id": {
2251
+ "description": "阿里云百炼应用 Agent 执行器提供商 ID",
2252
+ "type": "string",
2253
+ "_special": "select_agent_runner_provider:dashscope",
2254
+ "condition": {
2255
+ "provider_settings.agent_runner_type": "dashscope",
2256
+ "provider_settings.enable": True,
2257
+ },
2190
2258
  },
2259
+ },
2260
+ },
2261
+ "ai": {
2262
+ "description": "模型",
2263
+ "hint": "当使用非内置 Agent 执行器时,默认聊天模型和默认图片转述模型可能会无效,但某些插件会依赖此配置项来调用 AI 能力。",
2264
+ "type": "object",
2265
+ "items": {
2191
2266
  "provider_settings.default_provider_id": {
2192
2267
  "description": "默认聊天模型",
2193
2268
  "type": "string",
2194
2269
  "_special": "select_provider",
2195
- "hint": "留空时使用第一个模型。",
2270
+ "hint": "留空时使用第一个模型",
2196
2271
  },
2197
2272
  "provider_settings.default_image_caption_provider_id": {
2198
2273
  "description": "默认图片转述模型",
2199
2274
  "type": "string",
2200
2275
  "_special": "select_provider",
2201
- "hint": "留空代表不使用。可用于不支持视觉模态的聊天模型。",
2276
+ "hint": "留空代表不使用,可用于非多模态模型",
2202
2277
  },
2203
2278
  "provider_stt_settings.enable": {
2204
2279
  "description": "启用语音转文本",
2205
2280
  "type": "bool",
2206
- "hint": "STT 总开关。",
2281
+ "hint": "STT 总开关",
2207
2282
  },
2208
2283
  "provider_stt_settings.provider_id": {
2209
2284
  "description": "默认语音转文本模型",
@@ -2217,12 +2292,11 @@ CONFIG_METADATA_3 = {
2217
2292
  "provider_tts_settings.enable": {
2218
2293
  "description": "启用文本转语音",
2219
2294
  "type": "bool",
2220
- "hint": "TTS 总开关。当关闭时,会话启用 TTS 也不会生效。",
2295
+ "hint": "TTS 总开关",
2221
2296
  },
2222
2297
  "provider_tts_settings.provider_id": {
2223
2298
  "description": "默认文本转语音模型",
2224
2299
  "type": "string",
2225
- "hint": "用户也可使用 /provider 单独选择会话的 TTS 模型。",
2226
2300
  "_special": "select_provider_tts",
2227
2301
  "condition": {
2228
2302
  "provider_tts_settings.enable": True,
@@ -2233,6 +2307,9 @@ CONFIG_METADATA_3 = {
2233
2307
  "type": "text",
2234
2308
  },
2235
2309
  },
2310
+ "condition": {
2311
+ "provider_settings.enable": True,
2312
+ },
2236
2313
  },
2237
2314
  "persona": {
2238
2315
  "description": "人格",
@@ -2244,6 +2321,10 @@ CONFIG_METADATA_3 = {
2244
2321
  "_special": "select_persona",
2245
2322
  },
2246
2323
  },
2324
+ "condition": {
2325
+ "provider_settings.agent_runner_type": "local",
2326
+ "provider_settings.enable": True,
2327
+ },
2247
2328
  },
2248
2329
  "knowledgebase": {
2249
2330
  "description": "知识库",
@@ -2272,6 +2353,10 @@ CONFIG_METADATA_3 = {
2272
2353
  "hint": "启用后,知识库检索将作为 LLM Tool,由模型自主决定何时调用知识库进行查询。需要模型支持函数调用能力。",
2273
2354
  },
2274
2355
  },
2356
+ "condition": {
2357
+ "provider_settings.agent_runner_type": "local",
2358
+ "provider_settings.enable": True,
2359
+ },
2275
2360
  },
2276
2361
  "websearch": {
2277
2362
  "description": "网页搜索",
@@ -2308,6 +2393,10 @@ CONFIG_METADATA_3 = {
2308
2393
  "type": "bool",
2309
2394
  },
2310
2395
  },
2396
+ "condition": {
2397
+ "provider_settings.agent_runner_type": "local",
2398
+ "provider_settings.enable": True,
2399
+ },
2311
2400
  },
2312
2401
  "others": {
2313
2402
  "description": "其他配置",
@@ -2316,34 +2405,51 @@ CONFIG_METADATA_3 = {
2316
2405
  "provider_settings.display_reasoning_text": {
2317
2406
  "description": "显示思考内容",
2318
2407
  "type": "bool",
2408
+ "condition": {
2409
+ "provider_settings.agent_runner_type": "local",
2410
+ },
2319
2411
  },
2320
2412
  "provider_settings.identifier": {
2321
2413
  "description": "用户识别",
2322
2414
  "type": "bool",
2415
+ "hint": "启用后,会在提示词前包含用户 ID 信息。",
2323
2416
  },
2324
2417
  "provider_settings.group_name_display": {
2325
2418
  "description": "显示群名称",
2326
2419
  "type": "bool",
2327
- "hint": "启用后,在支持的平台(aiocqhttp)上会在 prompt 中包含群名称信息。",
2420
+ "hint": "启用后,在支持的平台(OneBot v11)上会在提示词前包含群名称信息。",
2328
2421
  },
2329
2422
  "provider_settings.datetime_system_prompt": {
2330
2423
  "description": "现实世界时间感知",
2331
2424
  "type": "bool",
2425
+ "hint": "启用后,会在系统提示词中附带当前时间信息。",
2426
+ "condition": {
2427
+ "provider_settings.agent_runner_type": "local",
2428
+ },
2332
2429
  },
2333
2430
  "provider_settings.show_tool_use_status": {
2334
2431
  "description": "输出函数调用状态",
2335
2432
  "type": "bool",
2433
+ "condition": {
2434
+ "provider_settings.agent_runner_type": "local",
2435
+ },
2336
2436
  },
2337
2437
  "provider_settings.max_agent_step": {
2338
2438
  "description": "工具调用轮数上限",
2339
2439
  "type": "int",
2440
+ "condition": {
2441
+ "provider_settings.agent_runner_type": "local",
2442
+ },
2340
2443
  },
2341
2444
  "provider_settings.tool_call_timeout": {
2342
2445
  "description": "工具调用超时时间(秒)",
2343
2446
  "type": "int",
2447
+ "condition": {
2448
+ "provider_settings.agent_runner_type": "local",
2449
+ },
2344
2450
  },
2345
2451
  "provider_settings.streaming_response": {
2346
- "description": "流式回复",
2452
+ "description": "流式输出",
2347
2453
  "type": "bool",
2348
2454
  },
2349
2455
  "provider_settings.unsupported_streaming_strategy": {
@@ -2359,17 +2465,23 @@ CONFIG_METADATA_3 = {
2359
2465
  "provider_settings.max_context_length": {
2360
2466
  "description": "最多携带对话轮数",
2361
2467
  "type": "int",
2362
- "hint": "超出这个数量时丢弃最旧的部分,一轮聊天记为 1 条。-1 为不限制。",
2468
+ "hint": "超出这个数量时丢弃最旧的部分,一轮聊天记为 1 条,-1 为不限制",
2469
+ "condition": {
2470
+ "provider_settings.agent_runner_type": "local",
2471
+ },
2363
2472
  },
2364
2473
  "provider_settings.dequeue_context_length": {
2365
2474
  "description": "丢弃对话轮数",
2366
2475
  "type": "int",
2367
- "hint": "超出最多携带对话轮数时, 一次丢弃的聊天轮数。",
2476
+ "hint": "超出最多携带对话轮数时, 一次丢弃的聊天轮数",
2477
+ "condition": {
2478
+ "provider_settings.agent_runner_type": "local",
2479
+ },
2368
2480
  },
2369
2481
  "provider_settings.wake_prefix": {
2370
2482
  "description": "LLM 聊天额外唤醒前缀 ",
2371
2483
  "type": "string",
2372
- "hint": "如果唤醒前缀为 `/`, 额外聊天唤醒前缀为 `chat`,则需要 `/chat` 才会触发 LLM 请求。默认为空。",
2484
+ "hint": "如果唤醒前缀为 /, 额外聊天唤醒前缀为 chat,则需要 /chat 才会触发 LLM 请求",
2373
2485
  },
2374
2486
  "provider_settings.prompt_prefix": {
2375
2487
  "description": "用户提示词",
@@ -2381,6 +2493,9 @@ CONFIG_METADATA_3 = {
2381
2493
  "type": "bool",
2382
2494
  },
2383
2495
  },
2496
+ "condition": {
2497
+ "provider_settings.enable": True,
2498
+ },
2384
2499
  },
2385
2500
  },
2386
2501
  },
@@ -0,0 +1,110 @@
1
+ """
2
+ 配置元数据国际化工具
3
+
4
+ 提供配置元数据的国际化键转换功能
5
+ """
6
+
7
+ from typing import Any
8
+
9
+
10
+ class ConfigMetadataI18n:
11
+ """配置元数据国际化转换器"""
12
+
13
+ @staticmethod
14
+ def _get_i18n_key(group: str, section: str, field: str, attr: str) -> str:
15
+ """
16
+ 生成国际化键
17
+
18
+ Args:
19
+ group: 配置组,如 'ai_group', 'platform_group'
20
+ section: 配置节,如 'agent_runner', 'general'
21
+ field: 字段名,如 'enable', 'default_provider'
22
+ attr: 属性类型,如 'description', 'hint', 'labels'
23
+
24
+ Returns:
25
+ 国际化键,格式如: 'ai_group.agent_runner.enable.description'
26
+ """
27
+ if field:
28
+ return f"{group}.{section}.{field}.{attr}"
29
+ else:
30
+ return f"{group}.{section}.{attr}"
31
+
32
+ @staticmethod
33
+ def convert_to_i18n_keys(metadata: dict[str, Any]) -> dict[str, Any]:
34
+ """
35
+ 将配置元数据转换为使用国际化键
36
+
37
+ Args:
38
+ metadata: 原始配置元数据字典
39
+
40
+ Returns:
41
+ 使用国际化键的配置元数据字典
42
+ """
43
+ result = {}
44
+
45
+ for group_key, group_data in metadata.items():
46
+ group_result = {
47
+ "name": f"{group_key}.name",
48
+ "metadata": {},
49
+ }
50
+
51
+ for section_key, section_data in group_data.get("metadata", {}).items():
52
+ section_result = {
53
+ "description": f"{group_key}.{section_key}.description",
54
+ "type": section_data.get("type"),
55
+ }
56
+
57
+ # 复制其他属性
58
+ for key in ["items", "condition", "_special", "invisible"]:
59
+ if key in section_data:
60
+ section_result[key] = section_data[key]
61
+
62
+ # 处理 hint
63
+ if "hint" in section_data:
64
+ section_result["hint"] = f"{group_key}.{section_key}.hint"
65
+
66
+ # 处理 items 中的字段
67
+ if "items" in section_data and isinstance(section_data["items"], dict):
68
+ items_result = {}
69
+ for field_key, field_data in section_data["items"].items():
70
+ # 处理嵌套的点号字段名(如 provider_settings.enable)
71
+ field_name = field_key
72
+
73
+ field_result = {}
74
+
75
+ # 复制基本属性
76
+ for attr in [
77
+ "type",
78
+ "condition",
79
+ "_special",
80
+ "invisible",
81
+ "options",
82
+ ]:
83
+ if attr in field_data:
84
+ field_result[attr] = field_data[attr]
85
+
86
+ # 转换文本属性为国际化键
87
+ if "description" in field_data:
88
+ field_result["description"] = (
89
+ f"{group_key}.{section_key}.{field_name}.description"
90
+ )
91
+
92
+ if "hint" in field_data:
93
+ field_result["hint"] = (
94
+ f"{group_key}.{section_key}.{field_name}.hint"
95
+ )
96
+
97
+ if "labels" in field_data:
98
+ field_result["labels"] = (
99
+ f"{group_key}.{section_key}.{field_name}.labels"
100
+ )
101
+
102
+ items_result[field_key] = field_result
103
+
104
+ section_result["items"] = items_result
105
+
106
+ group_result["metadata"][section_key] = section_result
107
+
108
+ result[group_key] = group_result
109
+
110
+ return result
@@ -16,13 +16,12 @@ import time
16
16
  import traceback
17
17
  from asyncio import Queue
18
18
 
19
- from astrbot.core import LogBroker, logger, sp
19
+ from astrbot.api import logger, sp
20
+ from astrbot.core import LogBroker
20
21
  from astrbot.core.astrbot_config_mgr import AstrBotConfigManager
21
22
  from astrbot.core.config.default import VERSION
22
23
  from astrbot.core.conversation_mgr import ConversationManager
23
24
  from astrbot.core.db import BaseDatabase
24
- from astrbot.core.db.migration.migra_45_to_46 import migrate_45_to_46
25
- from astrbot.core.db.migration.migra_webchat_session import migrate_webchat_session
26
25
  from astrbot.core.knowledge_base.kb_mgr import KnowledgeBaseManager
27
26
  from astrbot.core.persona_mgr import PersonaManager
28
27
  from astrbot.core.pipeline.scheduler import PipelineContext, PipelineScheduler
@@ -34,6 +33,7 @@ from astrbot.core.star.context import Context
34
33
  from astrbot.core.star.star_handler import EventType, star_handlers_registry, star_map
35
34
  from astrbot.core.umop_config_router import UmopConfigRouter
36
35
  from astrbot.core.updator import AstrBotUpdator
36
+ from astrbot.core.utils.migra_helper import migra
37
37
 
38
38
  from . import astrbot_config, html_renderer
39
39
  from .event_bus import EventBus
@@ -97,18 +97,16 @@ class AstrBotCoreLifecycle:
97
97
  sp=sp,
98
98
  )
99
99
 
100
- # 4.5 to 4.6 migration for umop_config_router
100
+ # apply migration
101
101
  try:
102
- await migrate_45_to_46(self.astrbot_config_mgr, self.umop_config_router)
103
- except Exception as e:
104
- logger.error(f"Migration from version 4.5 to 4.6 failed: {e!s}")
105
- logger.error(traceback.format_exc())
106
-
107
- # migration for webchat session
108
- try:
109
- await migrate_webchat_session(self.db)
102
+ await migra(
103
+ self.db,
104
+ self.astrbot_config_mgr,
105
+ self.umop_config_router,
106
+ self.astrbot_config_mgr,
107
+ )
110
108
  except Exception as e:
111
- logger.error(f"Migration for webchat session failed: {e!s}")
109
+ logger.error(f"AstrBot migration failed: {e!s}")
112
110
  logger.error(traceback.format_exc())
113
111
 
114
112
  # 初始化事件队列
astrbot/core/db/po.py CHANGED
@@ -173,7 +173,7 @@ class PlatformSession(SQLModel, table=True):
173
173
  max_length=100,
174
174
  nullable=False,
175
175
  unique=True,
176
- default_factory=lambda: f"webchat_{uuid.uuid4()}",
176
+ default_factory=lambda: str(uuid.uuid4()),
177
177
  )
178
178
  platform_id: str = Field(default="webchat", nullable=False)
179
179
  """Platform identifier (e.g., 'webchat', 'qq', 'discord')"""
astrbot/core/db/sqlite.py CHANGED
@@ -794,7 +794,7 @@ class SQLiteDatabase(BaseDatabase):
794
794
 
795
795
  await session.execute(
796
796
  update(PlatformSession)
797
- .where(col(PlatformSession.session_id == session_id))
797
+ .where(col(PlatformSession.session_id) == session_id)
798
798
  .values(**values),
799
799
  )
800
800
 
@@ -805,6 +805,6 @@ class SQLiteDatabase(BaseDatabase):
805
805
  async with session.begin():
806
806
  await session.execute(
807
807
  delete(PlatformSession).where(
808
- col(PlatformSession.session_id == session_id),
808
+ col(PlatformSession.session_id) == session_id,
809
809
  ),
810
810
  )
@@ -0,0 +1,48 @@
1
+ from collections.abc import AsyncGenerator
2
+
3
+ from astrbot.core import logger
4
+ from astrbot.core.platform.astr_message_event import AstrMessageEvent
5
+ from astrbot.core.star.session_llm_manager import SessionServiceManager
6
+
7
+ from ...context import PipelineContext
8
+ from ..stage import Stage
9
+ from .agent_sub_stages.internal import InternalAgentSubStage
10
+ from .agent_sub_stages.third_party import ThirdPartyAgentSubStage
11
+
12
+
13
+ class AgentRequestSubStage(Stage):
14
+ async def initialize(self, ctx: PipelineContext) -> None:
15
+ self.ctx = ctx
16
+ self.config = ctx.astrbot_config
17
+
18
+ self.bot_wake_prefixs: list[str] = self.config["wake_prefix"]
19
+ self.prov_wake_prefix: str = self.config["provider_settings"]["wake_prefix"]
20
+ for bwp in self.bot_wake_prefixs:
21
+ if self.prov_wake_prefix.startswith(bwp):
22
+ logger.info(
23
+ f"识别 LLM 聊天额外唤醒前缀 {self.prov_wake_prefix} 以机器人唤醒前缀 {bwp} 开头,已自动去除。",
24
+ )
25
+ self.prov_wake_prefix = self.prov_wake_prefix[len(bwp) :]
26
+
27
+ agent_runner_type = self.config["provider_settings"]["agent_runner_type"]
28
+ if agent_runner_type == "local":
29
+ self.agent_sub_stage = InternalAgentSubStage()
30
+ else:
31
+ self.agent_sub_stage = ThirdPartyAgentSubStage()
32
+ await self.agent_sub_stage.initialize(ctx)
33
+
34
+ async def process(self, event: AstrMessageEvent) -> AsyncGenerator[None, None]:
35
+ if not self.ctx.astrbot_config["provider_settings"]["enable"]:
36
+ logger.debug(
37
+ "This pipeline does not enable AI capability, skip processing."
38
+ )
39
+ return
40
+
41
+ if not SessionServiceManager.should_process_llm_request(event):
42
+ logger.debug(
43
+ f"The session {event.unified_msg_origin} has disabled AI capability, skipping processing."
44
+ )
45
+ return
46
+
47
+ async for resp in self.agent_sub_stage.process(event, self.prov_wake_prefix):
48
+ yield resp