foliko 1.1.93 → 2.0.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/.claude/settings.local.json +2 -1
- package/CLAUDE.md +56 -30
- package/REFACTORING_PLAN.md +645 -0
- package/docs/architecture.md +131 -0
- package/docs/migration.md +57 -0
- package/docs/public-api.md +138 -0
- package/docs/usage.md +385 -0
- package/examples/ambient-example.js +20 -137
- package/examples/basic.js +21 -48
- package/examples/bootstrap.js +16 -74
- package/examples/mcp-example.js +6 -29
- package/examples/skill-example.js +6 -19
- package/examples/workflow.js +8 -56
- package/package.json +8 -4
- package/plugins/README.md +49 -0
- package/plugins/{ambient-agent → ambient}/EventWatcher.js +1 -1
- package/plugins/{ambient-agent → ambient}/ExplorerLoop.js +3 -3
- package/plugins/{ambient-agent → ambient}/GoalManager.js +2 -2
- package/plugins/ambient/README.md +14 -0
- package/plugins/{ambient-agent → ambient}/Reflector.js +1 -1
- package/plugins/{ambient-agent → ambient}/StateStore.js +1 -1
- package/plugins/{ambient-agent → ambient}/index.js +2 -2
- package/plugins/{ai-plugin.js → core/ai/index.js} +14 -30
- package/plugins/{audit-plugin.js → core/audit/index.js} +3 -30
- package/plugins/{coordinator-plugin.js → core/coordinator/index.js} +3 -35
- package/plugins/core/default/bootstrap.js +224 -0
- package/plugins/core/default/config.js +222 -0
- package/plugins/core/default/index.js +58 -0
- package/plugins/core/mcp/index.js +1 -0
- package/plugins/{python-plugin-loader.js → core/python-loader/index.js} +7 -187
- package/plugins/{rules-plugin.js → core/rules/index.js} +121 -64
- package/plugins/{scheduler-plugin.js → core/scheduler/index.js} +12 -114
- package/plugins/{session-plugin.js → core/session/index.js} +9 -73
- package/{src/capabilities/skill-manager.js → plugins/core/skill-manager/index.js} +64 -18
- package/plugins/{storage-plugin.js → core/storage/index.js} +5 -29
- package/plugins/{subagent-plugin.js → core/sub-agent/index.js} +10 -171
- package/plugins/{think-plugin.js → core/think/index.js} +24 -91
- package/{src/capabilities/workflow-engine.js → plugins/core/workflow/index.js} +87 -85
- package/plugins/default-plugins.js +6 -720
- package/plugins/{data-splitter-plugin.js → executors/data-splitter/index.js} +9 -83
- package/plugins/{extension-executor-plugin.js → executors/extension/index.js} +13 -97
- package/plugins/{python-executor-plugin.js → executors/python/index.js} +6 -31
- package/plugins/{shell-executor-plugin.js → executors/shell/index.js} +2 -5
- package/plugins/install/README.md +9 -0
- package/plugins/{install-plugin.js → install/index.js} +3 -3
- package/plugins/{file-system-plugin.js → io/file-system/index.js} +34 -236
- package/plugins/{web-plugin.js → io/web/index.js} +11 -113
- package/plugins/memory/README.md +13 -0
- package/plugins/{memory-plugin.js → memory/index.js} +4 -18
- package/plugins/messaging/email/README.md +19 -0
- package/plugins/{email → messaging/email}/index.js +3 -3
- package/plugins/{feishu-plugin.js → messaging/feishu/index.js} +4 -4
- package/plugins/{qq-plugin.js → messaging/qq/index.js} +6 -17
- package/plugins/{telegram-plugin.js → messaging/telegram/index.js} +4 -4
- package/plugins/{weixin-plugin.js → messaging/weixin/index.js} +16 -16
- package/plugins/{plugin-manager-plugin.js → plugin-manager/index.js} +36 -180
- package/plugins/{tools-plugin.js → tools/index.js} +68 -116
- package/plugins/trading/README.md +15 -0
- package/plugins/{gate-trading.js → trading/index.js} +8 -8
- package/{examples → sandbox}/test-concurrent-chat.js +2 -2
- package/{examples → sandbox}/test-long-chat.js +2 -2
- package/{examples → sandbox}/test-session-chat.js +2 -2
- package/{examples → sandbox}/test-web-plugin.js +1 -1
- package/{examples → sandbox}/test-weixin-feishu.js +2 -2
- package/src/agent/base.js +56 -0
- package/src/{core/agent-chat.js → agent/chat.js} +11 -11
- package/src/{core/coordinator-manager.js → agent/coordinator.js} +3 -3
- package/src/agent/index.js +111 -0
- package/src/agent/main.js +337 -0
- package/src/agent/prompt.js +78 -0
- package/src/agent/sub.js +198 -0
- package/src/agent/worker.js +104 -0
- package/{cli/bin/foliko.js → src/cli/bin.js} +1 -1
- package/{cli/src → src/cli}/commands/chat.js +25 -21
- package/{cli/src → src/cli}/index.js +1 -0
- package/{cli/src → src/cli}/ui/chat-ui-old.js +40 -178
- package/{cli/src → src/cli}/ui/chat-ui.js +3 -3
- package/{cli/src → src/cli}/ui/components/footer-bar.js +1 -1
- package/src/common/errors.js +402 -0
- package/src/{utils → common}/logger.js +33 -0
- package/src/{utils/chat-queue.js → common/queue.js} +2 -2
- package/src/config/plugin-config.js +50 -0
- package/src/context/agent.js +32 -0
- package/src/context/compaction-prompts.js +170 -0
- package/src/context/compaction-utils.js +191 -0
- package/src/context/compressor.js +413 -0
- package/src/context/index.js +9 -0
- package/src/{core/context-manager.js → context/manager.js} +1 -1
- package/src/context/request.js +50 -0
- package/src/context/session.js +33 -0
- package/src/context/storage.js +30 -0
- package/src/executors/mcp-client.js +153 -0
- package/src/executors/mcp-desc.js +236 -0
- package/src/executors/mcp-executor.js +91 -956
- package/src/{core → framework}/command-registry.js +1 -1
- package/src/framework/framework.js +300 -0
- package/src/framework/index.js +18 -0
- package/src/framework/lifecycle.js +203 -0
- package/src/framework/loader.js +78 -0
- package/src/framework/registry.js +86 -0
- package/src/{core/ui-extension-context.js → framework/ui-extension.js} +1 -1
- package/src/index.js +130 -15
- package/src/llm/index.js +26 -0
- package/src/llm/provider.js +212 -0
- package/src/llm/registry.js +11 -0
- package/src/{core/token-counter.js → llm/tokens.js} +4 -37
- package/src/{core/plugin-base.js → plugin/base.js} +10 -136
- package/src/plugin/index.js +14 -0
- package/src/plugin/loader.js +101 -0
- package/src/plugin/manager.js +484 -0
- package/src/{core → session}/branch-summary-auto.js +2 -2
- package/src/{core/chat-session.js → session/chat.js} +2 -2
- package/src/session/index.js +7 -0
- package/src/{core/session-manager.js → session/session.js} +2 -2
- package/src/session/ttl.js +92 -0
- package/src/{core/jsonl-storage.js → storage/jsonl.js} +1 -1
- package/src/tool/executor.js +85 -0
- package/src/tool/index.js +15 -0
- package/src/tool/registry.js +143 -0
- package/src/{core/tool-router.js → tool/router.js} +17 -124
- package/src/tool/schema.js +108 -0
- package/src/utils/data-splitter.js +1 -1
- package/src/utils/download.js +1 -1
- package/src/utils/index.js +6 -6
- package/src/utils/message-validator.js +1 -1
- package/tests/core/context-storage.test.js +46 -0
- package/tests/core/llm.test.js +54 -0
- package/tests/core/plugin.test.js +42 -0
- package/tests/core/tool.test.js +60 -0
- package/tests/setup.js +10 -0
- package/tests/smoke.test.js +58 -0
- package/vitest.config.js +9 -0
- package/cli/src/daemon.js +0 -149
- package/docs/CONTEXT_DESIGN.md +0 -1596
- package/docs/ai-sdk-optimization.md +0 -655
- package/docs/features.md +0 -120
- package/docs/qq-bot.md +0 -976
- package/docs/quick-reference.md +0 -160
- package/docs/user-manual.md +0 -1391
- package/images/geometric_shapes.jpg +0 -0
- package/images/sunset_mountain_lake.jpg +0 -0
- package/skills/poster-guide/SKILL.md +0 -792
- package/src/capabilities/index.js +0 -11
- package/src/core/agent.js +0 -808
- package/src/core/context-compressor.js +0 -959
- package/src/core/enhanced-context-compressor.js +0 -210
- package/src/core/framework.js +0 -1422
- package/src/core/index.js +0 -30
- package/src/core/plugin-manager.js +0 -961
- package/src/core/provider-registry.js +0 -159
- package/src/core/provider.js +0 -156
- package/src/core/request-context.js +0 -98
- package/src/core/subagent.js +0 -442
- package/src/core/system-prompt-builder.js +0 -120
- package/src/core/tool-executor.js +0 -202
- package/src/core/tool-registry.js +0 -517
- package/src/core/worker-agent.js +0 -192
- package/src/executors/executor-base.js +0 -58
- package/src/utils/error-boundary.js +0 -363
- package/src/utils/error.js +0 -374
- package/system.md +0 -1645
- package/website_v2/README.md +0 -57
- package/website_v2/SPEC.md +0 -1
- package/website_v2/docs/api.html +0 -128
- package/website_v2/docs/configuration.html +0 -147
- package/website_v2/docs/plugin-development.html +0 -129
- package/website_v2/docs/project-structure.html +0 -89
- package/website_v2/docs/skill-development.html +0 -85
- package/website_v2/index.html +0 -489
- package/website_v2/scripts/main.js +0 -93
- package/website_v2/styles/animations.css +0 -8
- package/website_v2/styles/docs.css +0 -83
- package/website_v2/styles/main.css +0 -417
- package/xhs_auth.json +0 -268
- package//346/265/267/346/212/245/346/217/222/344/273/266.md +0 -621
- /package/plugins/{ambient-agent → ambient}/constants.js +0 -0
- /package/plugins/{email → messaging/email}/constants.js +0 -0
- /package/plugins/{email → messaging/email}/handlers.js +0 -0
- /package/plugins/{email → messaging/email}/monitor.js +0 -0
- /package/plugins/{email → messaging/email}/parser.js +0 -0
- /package/plugins/{email → messaging/email}/reply.js +0 -0
- /package/plugins/{email → messaging/email}/utils.js +0 -0
- /package/{examples → sandbox}/test-chat.js +0 -0
- /package/{examples → sandbox}/test-mcp.js +0 -0
- /package/{examples → sandbox}/test-reload.js +0 -0
- /package/{examples → sandbox}/test-telegram.js +0 -0
- /package/{examples → sandbox}/test-tg-bot.js +0 -0
- /package/{examples → sandbox}/test-tg-simple.js +0 -0
- /package/{examples → sandbox}/test-tg.js +0 -0
- /package/{examples → sandbox}/test-think.js +0 -0
- /package/src/{core/sub-agent-config.js → agent/sub-config.js} +0 -0
- /package/{cli/src → src/cli}/commands/daemon.js +0 -0
- /package/{cli/src → src/cli}/commands/list.js +0 -0
- /package/{cli/src → src/cli}/commands/plugin.js +0 -0
- /package/{cli/src → src/cli}/ui/components/agent-mention-provider.js +0 -0
- /package/{cli/src → src/cli}/ui/components/chained-autocomplete-provider.js +0 -0
- /package/{cli/src → src/cli}/ui/components/message-bubble.js +0 -0
- /package/{cli/src → src/cli}/ui/components/status-bar.js +0 -0
- /package/{cli/src → src/cli}/utils/ansi.js +0 -0
- /package/{cli/src → src/cli}/utils/config.js +0 -0
- /package/{cli/src → src/cli}/utils/markdown.js +0 -0
- /package/{cli/src → src/cli}/utils/plugin-config.js +0 -0
- /package/{cli/src → src/cli}/utils/render-diff.js +0 -0
- /package/src/{utils/circuit-breaker.js → common/circuit.js} +0 -0
- /package/src/{core → common}/constants.js +0 -0
- /package/src/{utils/edit-diff.js → common/diff.js} +0 -0
- /package/src/{utils/event-emitter.js → common/events.js} +0 -0
- /package/src/{utils → common}/id.js +0 -0
- /package/src/{utils → common}/retry.js +0 -0
- /package/src/{core/notification-manager.js → notification/manager.js} +0 -0
- /package/src/{core/session-entry.js → session/entry.js} +0 -0
- /package/src/{core/storage-manager.js → storage/manager.js} +0 -0
|
@@ -3,9 +3,9 @@
|
|
|
3
3
|
* 支持 HTTP 服务、路由注册、Webhook(自动生成 /webhook/{id} 链接)
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
const { Plugin } = require('
|
|
7
|
-
const { logger } = require('
|
|
8
|
-
const { runInSandbox } = require('
|
|
6
|
+
const { Plugin } = require('../../../src/plugin/base')
|
|
7
|
+
const { logger } = require('../../../src/common/logger')
|
|
8
|
+
const { runInSandbox } = require('../../../src/utils/sandbox')
|
|
9
9
|
const log = logger.child('Web')
|
|
10
10
|
const { z } = require('zod')
|
|
11
11
|
const { serve } = require('@hono/node-server')
|
|
@@ -13,9 +13,6 @@ const { Hono } = require('hono')
|
|
|
13
13
|
const fs = require('fs')
|
|
14
14
|
const path = require('path')
|
|
15
15
|
|
|
16
|
-
// ============================================================================
|
|
17
|
-
// WebStore - 持久化 Web 配置到 .foliko/data/web/
|
|
18
|
-
// ============================================================================
|
|
19
16
|
class WebStore {
|
|
20
17
|
constructor(persistencePath) {
|
|
21
18
|
this._persistencePath = persistencePath
|
|
@@ -61,43 +58,34 @@ class WebPlugin extends Plugin {
|
|
|
61
58
|
this.description = 'Web 服务插件,支持 HTTP 服务、路由注册、Webhook'
|
|
62
59
|
this.priority = 50
|
|
63
60
|
|
|
64
|
-
this.system = true
|
|
61
|
+
this.system = true
|
|
65
62
|
|
|
66
|
-
// 服务器配置
|
|
67
63
|
this._port = process.env.WEB_PORT || 3000
|
|
68
64
|
this._host = process.env.WEB_HOST || '127.0.0.1'
|
|
69
|
-
this._baseUrl = process.env.WEB_BASE_URL || null
|
|
65
|
+
this._baseUrl = process.env.WEB_BASE_URL || null
|
|
70
66
|
|
|
71
|
-
// 运行时状态
|
|
72
67
|
this._server = null
|
|
73
68
|
this._app = null
|
|
74
69
|
this._framework = null
|
|
75
70
|
|
|
76
71
|
this.tools = {}
|
|
77
72
|
|
|
78
|
-
|
|
79
|
-
this.
|
|
80
|
-
this.
|
|
81
|
-
this._statics = [] // 静态文件夹列表
|
|
73
|
+
this._routes = []
|
|
74
|
+
this._webhooks = new Map()
|
|
75
|
+
this._statics = []
|
|
82
76
|
|
|
83
|
-
// 持久化存储
|
|
84
77
|
this._webStore = null
|
|
85
78
|
this._persistencePath = config.persistencePath || '.foliko/data/web'
|
|
86
79
|
}
|
|
87
80
|
|
|
88
|
-
// ==================== 生命周期 ====================
|
|
89
|
-
|
|
90
81
|
install(framework) {
|
|
91
82
|
this._framework = framework
|
|
92
83
|
this._registerTools()
|
|
93
84
|
|
|
94
|
-
// 初始化持久化存储
|
|
95
85
|
this._webStore = new WebStore(this._persistencePath)
|
|
96
86
|
|
|
97
|
-
// 加载已保存的配置
|
|
98
87
|
this._loadPersistedConfig()
|
|
99
88
|
|
|
100
|
-
// 将 WEB_BASE_URL 注入到 framework 的元数据,供所有 agent 使用
|
|
101
89
|
if (this._baseUrl && framework._mainAgent) {
|
|
102
90
|
framework._mainAgent.setMetadata('WEB_BASE_URL', this._baseUrl)
|
|
103
91
|
}
|
|
@@ -112,28 +100,20 @@ class WebPlugin extends Plugin {
|
|
|
112
100
|
reload(framework) {
|
|
113
101
|
this._framework = framework
|
|
114
102
|
|
|
115
|
-
// 重新初始化存储并加载配置
|
|
116
103
|
this._webStore = new WebStore(this._persistencePath)
|
|
117
104
|
this._loadPersistedConfig()
|
|
118
105
|
|
|
119
|
-
// 重新注入 WEB_BASE_URL
|
|
120
106
|
if (this._baseUrl && framework._mainAgent) {
|
|
121
107
|
framework._mainAgent.setMetadata('WEB_BASE_URL', this._baseUrl)
|
|
122
108
|
}
|
|
123
109
|
}
|
|
124
110
|
|
|
125
|
-
/**
|
|
126
|
-
* 加载持久化的配置并恢复路由/webhook/静态资源
|
|
127
|
-
*/
|
|
128
111
|
_loadPersistedConfig() {
|
|
129
112
|
if (!this._webStore) return
|
|
130
113
|
|
|
131
114
|
const config = this._webStore.loadConfig()
|
|
132
115
|
if (!config) return
|
|
133
116
|
|
|
134
|
-
// log.info(` 加载 Web 配置...`)
|
|
135
|
-
|
|
136
|
-
// 恢复前先清空,避免 install -> reload 重复加载导致数据翻倍
|
|
137
117
|
this._routes = []
|
|
138
118
|
this._webhooks = new Map()
|
|
139
119
|
this._statics = []
|
|
@@ -142,7 +122,6 @@ class WebPlugin extends Plugin {
|
|
|
142
122
|
let hasWebhooks = false
|
|
143
123
|
let hasStatics = false
|
|
144
124
|
|
|
145
|
-
// 恢复路由
|
|
146
125
|
if (config.routes && Array.isArray(config.routes)) {
|
|
147
126
|
for (const route of config.routes) {
|
|
148
127
|
if (route.method && route.path && route.handler) {
|
|
@@ -153,12 +132,10 @@ class WebPlugin extends Plugin {
|
|
|
153
132
|
description: route.description || ''
|
|
154
133
|
})
|
|
155
134
|
hasRoutes = true
|
|
156
|
-
// log.info(` 恢复路由: ${route.method} ${route.path}`)
|
|
157
135
|
}
|
|
158
136
|
}
|
|
159
137
|
}
|
|
160
138
|
|
|
161
|
-
// 恢复 Webhooks
|
|
162
139
|
if (config.webhooks && Array.isArray(config.webhooks)) {
|
|
163
140
|
for (const webhook of config.webhooks) {
|
|
164
141
|
if (webhook.id && webhook.path) {
|
|
@@ -169,12 +146,10 @@ class WebPlugin extends Plugin {
|
|
|
169
146
|
awaitResponse: webhook.awaitResponse || false
|
|
170
147
|
})
|
|
171
148
|
hasWebhooks = true
|
|
172
|
-
// log.info(` 恢复 Webhook: ${webhook.path}`)
|
|
173
149
|
}
|
|
174
150
|
}
|
|
175
151
|
}
|
|
176
152
|
|
|
177
|
-
// 恢复静态资源
|
|
178
153
|
if (config.statics && Array.isArray(config.statics)) {
|
|
179
154
|
for (const staticItem of config.statics) {
|
|
180
155
|
if (staticItem.urlPath && staticItem.folder) {
|
|
@@ -184,23 +159,17 @@ class WebPlugin extends Plugin {
|
|
|
184
159
|
options: staticItem.options || { dotfiles: 'ignore', index: 'index.html' }
|
|
185
160
|
})
|
|
186
161
|
hasStatics = true
|
|
187
|
-
// log.info(` 恢复静态资源: ${staticItem.urlPath} -> ${staticItem.folder}`)
|
|
188
162
|
}
|
|
189
163
|
}
|
|
190
164
|
}
|
|
191
165
|
|
|
192
|
-
// 如果有恢复的路由/webhook/静态资源,自动启动服务器
|
|
193
166
|
if ((hasRoutes || hasWebhooks || hasStatics) && !this._server) {
|
|
194
|
-
// log.info(` 恢复的 Web 配置需要启动服务器...`)
|
|
195
167
|
this._startServer().catch(err => {
|
|
196
168
|
log.error(` 自动启动服务器失败:`, err.message)
|
|
197
169
|
})
|
|
198
170
|
}
|
|
199
171
|
}
|
|
200
172
|
|
|
201
|
-
/**
|
|
202
|
-
* 保存当前配置到持久化存储
|
|
203
|
-
*/
|
|
204
173
|
_saveConfig() {
|
|
205
174
|
if (!this._webStore) return
|
|
206
175
|
|
|
@@ -232,10 +201,7 @@ class WebPlugin extends Plugin {
|
|
|
232
201
|
this._framework = null
|
|
233
202
|
}
|
|
234
203
|
|
|
235
|
-
// ==================== 工具注册 ====================
|
|
236
|
-
|
|
237
204
|
_registerTools() {
|
|
238
|
-
// 启动 Web 服务
|
|
239
205
|
this.tools.web_start = {
|
|
240
206
|
name: 'web_start',
|
|
241
207
|
description: '启动 Web 服务',
|
|
@@ -246,7 +212,6 @@ class WebPlugin extends Plugin {
|
|
|
246
212
|
execute: async (args) => this._startServer(args.port, args.host)
|
|
247
213
|
}
|
|
248
214
|
|
|
249
|
-
// 停止 Web 服务
|
|
250
215
|
this.tools.web_stop = {
|
|
251
216
|
name: 'web_stop',
|
|
252
217
|
description: '停止 Web 服务',
|
|
@@ -254,7 +219,6 @@ class WebPlugin extends Plugin {
|
|
|
254
219
|
execute: async () => this._stopServer()
|
|
255
220
|
}
|
|
256
221
|
|
|
257
|
-
// 注册 HTTP 路由
|
|
258
222
|
this.tools.web_register_route = {
|
|
259
223
|
name: 'web_register_route',
|
|
260
224
|
description: '注册 HTTP 路由',
|
|
@@ -272,7 +236,6 @@ class WebPlugin extends Plugin {
|
|
|
272
236
|
execute: async (args) => this._registerRoute(args.method, args.path, args.handler, args.description)
|
|
273
237
|
}
|
|
274
238
|
|
|
275
|
-
// 注册 Webhook(自动生成 /webhook/{id} 链接)
|
|
276
239
|
this.tools.web_register_webhook = {
|
|
277
240
|
name: 'web_register_webhook',
|
|
278
241
|
description: '注册 Webhook,接收的数据会交给 LLM 处理。自动生成唯一 URL',
|
|
@@ -283,7 +246,6 @@ class WebPlugin extends Plugin {
|
|
|
283
246
|
execute: async (args) => this._registerWebhook(args.prompt, args.awaitResponse)
|
|
284
247
|
}
|
|
285
248
|
|
|
286
|
-
// 注册静态资源
|
|
287
249
|
this.tools.web_register_static = {
|
|
288
250
|
name: 'web_register_static',
|
|
289
251
|
description: '注册静态资源文件夹',
|
|
@@ -298,7 +260,6 @@ class WebPlugin extends Plugin {
|
|
|
298
260
|
execute: async (args) => this._registerStatic(args.urlPath, args.folder, args.options)
|
|
299
261
|
}
|
|
300
262
|
|
|
301
|
-
// 列出所有路由
|
|
302
263
|
this.tools.web_list_routes = {
|
|
303
264
|
name: 'web_list_routes',
|
|
304
265
|
description: '列出所有已注册的路由和 Webhook',
|
|
@@ -306,7 +267,6 @@ class WebPlugin extends Plugin {
|
|
|
306
267
|
execute: async () => this._listRoutes()
|
|
307
268
|
}
|
|
308
269
|
|
|
309
|
-
// 删除路由
|
|
310
270
|
this.tools.web_delete_route = {
|
|
311
271
|
name: 'web_delete_route',
|
|
312
272
|
description: '删除已注册的 HTTP 路由',
|
|
@@ -317,7 +277,6 @@ class WebPlugin extends Plugin {
|
|
|
317
277
|
execute: async (args) => this._deleteRoute(args.method, args.path)
|
|
318
278
|
}
|
|
319
279
|
|
|
320
|
-
// 删除 Webhook
|
|
321
280
|
this.tools.web_delete_webhook = {
|
|
322
281
|
name: 'web_delete_webhook',
|
|
323
282
|
description: '删除已注册的 Webhook',
|
|
@@ -327,7 +286,6 @@ class WebPlugin extends Plugin {
|
|
|
327
286
|
execute: async (args) => this._deleteWebhook(args.id)
|
|
328
287
|
}
|
|
329
288
|
|
|
330
|
-
// 删除静态资源
|
|
331
289
|
this.tools.web_delete_static = {
|
|
332
290
|
name: 'web_delete_static',
|
|
333
291
|
description: '删除已注册的静态资源文件夹',
|
|
@@ -337,7 +295,6 @@ class WebPlugin extends Plugin {
|
|
|
337
295
|
execute: async (args) => this._deleteStatic(args.urlPath)
|
|
338
296
|
}
|
|
339
297
|
|
|
340
|
-
// 发送 HTTP 请求
|
|
341
298
|
this.tools.web_request = {
|
|
342
299
|
name: 'web_request',
|
|
343
300
|
description: '发送 HTTP 请求',
|
|
@@ -351,8 +308,6 @@ class WebPlugin extends Plugin {
|
|
|
351
308
|
}
|
|
352
309
|
}
|
|
353
310
|
|
|
354
|
-
// ==================== 服务器控制 ====================
|
|
355
|
-
|
|
356
311
|
async _startServer(port, host) {
|
|
357
312
|
if (this._server) {
|
|
358
313
|
return { success: true, message: 'Server already running', port: this._port }
|
|
@@ -371,14 +326,11 @@ class WebPlugin extends Plugin {
|
|
|
371
326
|
hostname: this._host
|
|
372
327
|
})
|
|
373
328
|
const serverUrl = this._getUrl()
|
|
374
|
-
// log.info(` Server started on ${serverUrl}`)
|
|
375
329
|
return {
|
|
376
330
|
success: true,
|
|
377
331
|
message: `Server started on ${serverUrl}`,
|
|
378
|
-
// port: this._port,
|
|
379
|
-
// host: this._host,
|
|
380
332
|
host: serverUrl,
|
|
381
|
-
url:serverUrl,
|
|
333
|
+
url: serverUrl,
|
|
382
334
|
}
|
|
383
335
|
} catch (err) {
|
|
384
336
|
this._server = null
|
|
@@ -397,17 +349,13 @@ class WebPlugin extends Plugin {
|
|
|
397
349
|
this._server.close()
|
|
398
350
|
this._server = null
|
|
399
351
|
this._app = null
|
|
400
|
-
// log.info(' Server stopped')
|
|
401
352
|
return { success: true, message: 'Server stopped' }
|
|
402
353
|
}
|
|
403
354
|
|
|
404
|
-
// ==================== 中间件 ====================
|
|
405
|
-
|
|
406
355
|
_setupMiddleware() {
|
|
407
356
|
this._app.use('*', async (c) => {
|
|
408
357
|
const pathname = c.req.path
|
|
409
358
|
|
|
410
|
-
// CORS 预检
|
|
411
359
|
if (c.req.method === 'OPTIONS') {
|
|
412
360
|
return c.text('', 200, {
|
|
413
361
|
'Access-Control-Allow-Origin': '*',
|
|
@@ -416,7 +364,6 @@ class WebPlugin extends Plugin {
|
|
|
416
364
|
})
|
|
417
365
|
}
|
|
418
366
|
|
|
419
|
-
// 1. 静态文件
|
|
420
367
|
const staticResult = this._serveStatic(pathname)
|
|
421
368
|
if (staticResult) {
|
|
422
369
|
if (staticResult.type === 'file') {
|
|
@@ -435,7 +382,6 @@ class WebPlugin extends Plugin {
|
|
|
435
382
|
}
|
|
436
383
|
}
|
|
437
384
|
|
|
438
|
-
// 2. Webhook(仅接受 POST)
|
|
439
385
|
const webhook = this._webhooks.get(pathname)
|
|
440
386
|
if (webhook) {
|
|
441
387
|
if (c.req.method !== 'POST') {
|
|
@@ -445,20 +391,16 @@ class WebPlugin extends Plugin {
|
|
|
445
391
|
return c.json(result)
|
|
446
392
|
}
|
|
447
393
|
|
|
448
|
-
// 3. 路由(支持参数)
|
|
449
394
|
for (const route of this._routes) {
|
|
450
395
|
if (route.method === c.req.method && this._matchPath(route.path, pathname)) {
|
|
451
396
|
return await this._handleRoute(c, route, pathname)
|
|
452
397
|
}
|
|
453
398
|
}
|
|
454
399
|
|
|
455
|
-
// 404
|
|
456
400
|
return c.json({ success: false, error: 'Not Found', path: pathname }, 404)
|
|
457
401
|
})
|
|
458
402
|
}
|
|
459
403
|
|
|
460
|
-
// ==================== 请求处理 ====================
|
|
461
|
-
|
|
462
404
|
async _handleRoute(c, route, pathname) {
|
|
463
405
|
const params = this._extractParams(route.path, pathname)
|
|
464
406
|
const query = this._parseQuery(c)
|
|
@@ -466,13 +408,10 @@ class WebPlugin extends Plugin {
|
|
|
466
408
|
|
|
467
409
|
const context = { params, query, body }
|
|
468
410
|
|
|
469
|
-
// 构建 tools 代理对象,允许 handler 以函数方式直接调用工具
|
|
470
|
-
// 例如: const user = await tools.get_user({ id: 1 })
|
|
471
411
|
const registry = this._framework.toolRegistry
|
|
472
412
|
const tools = new Proxy({}, {
|
|
473
413
|
get: (_, name) => {
|
|
474
414
|
if (name === 'call') {
|
|
475
|
-
// 保留 call 方式作为后备
|
|
476
415
|
return async (toolName, args) => registry.execute(toolName, args || {}, this._framework)
|
|
477
416
|
}
|
|
478
417
|
return async (args) => registry.execute(name, args || {}, this._framework)
|
|
@@ -494,11 +433,9 @@ class WebPlugin extends Plugin {
|
|
|
494
433
|
timestamp: new Date().toISOString()
|
|
495
434
|
}
|
|
496
435
|
|
|
497
|
-
// 从执行上下文获取 sessionId
|
|
498
436
|
const ctx = this._framework.getExecutionContext()
|
|
499
437
|
const sessionId = ctx?.sessionId || null
|
|
500
438
|
|
|
501
|
-
// 获取 Agent
|
|
502
439
|
const agent = this._getAgent(sessionId)
|
|
503
440
|
if (!agent) {
|
|
504
441
|
log.error(' No agent available')
|
|
@@ -508,7 +445,6 @@ class WebPlugin extends Plugin {
|
|
|
508
445
|
const prompt = webhook.prompt || '处理以下 webhook 数据,返回适当的响应:'
|
|
509
446
|
const finalSessionId = sessionId || `web_${Date.now()}`
|
|
510
447
|
|
|
511
|
-
// 触发 webhook 接收事件(扁平化结构)
|
|
512
448
|
this._framework.emit('webhook:received', {
|
|
513
449
|
path: webhook.path,
|
|
514
450
|
method: c.req.method,
|
|
@@ -517,19 +453,15 @@ class WebPlugin extends Plugin {
|
|
|
517
453
|
timestamp: webhookData.timestamp
|
|
518
454
|
})
|
|
519
455
|
|
|
520
|
-
// 使用子Agent处理 webhook
|
|
521
456
|
const webhookAgent = this._framework.createSubAgent({
|
|
522
457
|
name: 'webhook_handler',
|
|
523
458
|
role: 'Webhook处理助手,专注于处理webhook数据并生成适当响应'
|
|
524
459
|
})
|
|
525
460
|
|
|
526
461
|
if (!webhook.awaitResponse) {
|
|
527
|
-
// 不等待,立即返回
|
|
528
462
|
webhookAgent.chat(`${prompt}\n\n数据:\n${JSON.stringify(webhookData, null, 2)}`).then(result => {
|
|
529
463
|
const responseText = result.message || ''
|
|
530
|
-
// log.info(` Webhook processed (${webhook.path}), LLM response (${responseText.length} chars)`)
|
|
531
464
|
|
|
532
|
-
// 添加到 session 历史
|
|
533
465
|
if (sessionId) {
|
|
534
466
|
const sessionPlugin = this._framework.pluginManager.get('session')
|
|
535
467
|
if (sessionPlugin) {
|
|
@@ -538,7 +470,6 @@ class WebPlugin extends Plugin {
|
|
|
538
470
|
}
|
|
539
471
|
}
|
|
540
472
|
|
|
541
|
-
// 触发 webhook 处理完成事件
|
|
542
473
|
this._framework.emit('webhook:processed', {
|
|
543
474
|
path: webhook.path,
|
|
544
475
|
method: c.req.method,
|
|
@@ -554,13 +485,10 @@ class WebPlugin extends Plugin {
|
|
|
554
485
|
return { success: true, message: 'Webhook received, processing in background' }
|
|
555
486
|
}
|
|
556
487
|
|
|
557
|
-
// 等待 LLM 处理完成
|
|
558
488
|
try {
|
|
559
489
|
const result = await webhookAgent.chat(`${prompt}\n\n数据:\n${JSON.stringify(webhookData, null, 2)}`)
|
|
560
490
|
const responseText = result.message || result.text || ''
|
|
561
|
-
// log.info(` Webhook processed (${webhook.path}), LLM response (${responseText.length} chars)`)
|
|
562
491
|
|
|
563
|
-
// 添加到 session 历史
|
|
564
492
|
if (sessionId) {
|
|
565
493
|
const sessionPlugin = this._framework.pluginManager.get('session')
|
|
566
494
|
if (sessionPlugin) {
|
|
@@ -569,7 +497,6 @@ class WebPlugin extends Plugin {
|
|
|
569
497
|
}
|
|
570
498
|
}
|
|
571
499
|
|
|
572
|
-
// 触发 webhook 处理完成事件
|
|
573
500
|
this._framework.emit('webhook:processed', {
|
|
574
501
|
path: webhook.path,
|
|
575
502
|
method: c.req.method,
|
|
@@ -586,8 +513,6 @@ class WebPlugin extends Plugin {
|
|
|
586
513
|
}
|
|
587
514
|
}
|
|
588
515
|
|
|
589
|
-
// ==================== 路由注册 ====================
|
|
590
|
-
|
|
591
516
|
async _registerRoute(method, path, handler, description) {
|
|
592
517
|
if (!path.startsWith('/') || path.length < 2) {
|
|
593
518
|
return { success: false, error: 'Invalid path format' }
|
|
@@ -605,10 +530,8 @@ class WebPlugin extends Plugin {
|
|
|
605
530
|
this._routes.push(route)
|
|
606
531
|
}
|
|
607
532
|
|
|
608
|
-
// 持久化保存
|
|
609
533
|
this._saveConfig()
|
|
610
534
|
|
|
611
|
-
// log.info(` Route registered: ${method} ${path}`)
|
|
612
535
|
return { success: true, message: `Route ${method} ${path} registered`, url: this._getUrl(path), route: { method, path, description } }
|
|
613
536
|
}
|
|
614
537
|
|
|
@@ -617,7 +540,6 @@ class WebPlugin extends Plugin {
|
|
|
617
540
|
await this._startServer()
|
|
618
541
|
}
|
|
619
542
|
|
|
620
|
-
// 生成唯一 ID 和路径:/webhook/{id}
|
|
621
543
|
const id = this._generateId()
|
|
622
544
|
const webhookPath = `/webhook/${id}`
|
|
623
545
|
|
|
@@ -628,10 +550,8 @@ class WebPlugin extends Plugin {
|
|
|
628
550
|
awaitResponse
|
|
629
551
|
})
|
|
630
552
|
|
|
631
|
-
// 持久化保存
|
|
632
553
|
this._saveConfig()
|
|
633
554
|
|
|
634
|
-
// log.info(` Webhook registered: ${webhookPath}`)
|
|
635
555
|
return {
|
|
636
556
|
success: true,
|
|
637
557
|
message: `Webhook registered`,
|
|
@@ -658,10 +578,8 @@ class WebPlugin extends Plugin {
|
|
|
658
578
|
}
|
|
659
579
|
})
|
|
660
580
|
|
|
661
|
-
// 持久化保存
|
|
662
581
|
this._saveConfig()
|
|
663
582
|
|
|
664
|
-
// log.info(` Static registered: ${normalizedPath} -> ${folder}`)
|
|
665
583
|
return {
|
|
666
584
|
success: true,
|
|
667
585
|
message: `Static folder registered`,
|
|
@@ -689,7 +607,6 @@ class WebPlugin extends Plugin {
|
|
|
689
607
|
|
|
690
608
|
this._routes.splice(index, 1)
|
|
691
609
|
this._saveConfig()
|
|
692
|
-
// log.info(` Route deleted: ${method} ${path}`)
|
|
693
610
|
return { success: true, message: `Route deleted: ${method} ${path}` }
|
|
694
611
|
}
|
|
695
612
|
|
|
@@ -708,7 +625,6 @@ class WebPlugin extends Plugin {
|
|
|
708
625
|
|
|
709
626
|
this._webhooks.delete(found)
|
|
710
627
|
this._saveConfig()
|
|
711
|
-
// log.info(` Webhook deleted: ${found}`)
|
|
712
628
|
return { success: true, message: `Webhook deleted: ${found}` }
|
|
713
629
|
}
|
|
714
630
|
|
|
@@ -721,12 +637,9 @@ class WebPlugin extends Plugin {
|
|
|
721
637
|
|
|
722
638
|
this._statics.splice(index, 1)
|
|
723
639
|
this._saveConfig()
|
|
724
|
-
// log.info(` Static deleted: ${normalizedPath}`)
|
|
725
640
|
return { success: true, message: `Static folder deleted: ${normalizedPath}` }
|
|
726
641
|
}
|
|
727
642
|
|
|
728
|
-
// ==================== HTTP 客户端 ====================
|
|
729
|
-
|
|
730
643
|
async _sendRequest(method, urlPath, body, headers) {
|
|
731
644
|
if (!this._server) {
|
|
732
645
|
return { success: false, error: 'Server not started' }
|
|
@@ -747,7 +660,7 @@ class WebPlugin extends Plugin {
|
|
|
747
660
|
const response = await fetch(url, options)
|
|
748
661
|
const text = await response.text()
|
|
749
662
|
let parsed = text
|
|
750
|
-
try { parsed = JSON.parse(text) } catch {
|
|
663
|
+
try { parsed = JSON.parse(text) } catch {}
|
|
751
664
|
|
|
752
665
|
return { success: true, status: response.status, headers: Object.fromEntries(response.headers.entries()), body: parsed }
|
|
753
666
|
} catch (err) {
|
|
@@ -755,8 +668,6 @@ class WebPlugin extends Plugin {
|
|
|
755
668
|
}
|
|
756
669
|
}
|
|
757
670
|
|
|
758
|
-
// ==================== 工具方法 ====================
|
|
759
|
-
|
|
760
671
|
_matchPath(routePath, reqPath) {
|
|
761
672
|
const routeParts = routePath.split('/').filter(Boolean)
|
|
762
673
|
const reqParts = reqPath.split('/').filter(Boolean)
|
|
@@ -788,7 +699,6 @@ class WebPlugin extends Plugin {
|
|
|
788
699
|
async _parseBody(c) {
|
|
789
700
|
try {
|
|
790
701
|
const rawText = await c.req.text()
|
|
791
|
-
// log.info(rawText)
|
|
792
702
|
if (!rawText) return {}
|
|
793
703
|
return JSON.parse(rawText)
|
|
794
704
|
} catch (e) {
|
|
@@ -805,32 +715,23 @@ class WebPlugin extends Plugin {
|
|
|
805
715
|
|
|
806
716
|
async _executeHandler(handlerCode, context, tools) {
|
|
807
717
|
try {
|
|
808
|
-
// 辅助函数
|
|
809
718
|
const helpers = {
|
|
810
|
-
// 基础工具
|
|
811
719
|
echo: (val) => val,
|
|
812
720
|
json: (val) => JSON.stringify(val),
|
|
813
721
|
JSON: JSON,
|
|
814
|
-
// 日期时间
|
|
815
722
|
Date: Date,
|
|
816
723
|
now: () => Date.now(),
|
|
817
|
-
// 字符串
|
|
818
724
|
Str: String,
|
|
819
|
-
// 编码
|
|
820
725
|
btoa: (str) => Buffer.from(str).toString('base64'),
|
|
821
726
|
atob: (str) => Buffer.from(str, 'base64').toString(),
|
|
822
|
-
// 格式化
|
|
823
727
|
template: (str, vars) => str.replace(/\{\{(\w+)\}\}/g, (_, k) => vars[k] ?? `{{${k}}}`),
|
|
824
|
-
// 随机
|
|
825
728
|
uuid: () => Math.random().toString(36).substring(2) + Date.now().toString(36),
|
|
826
|
-
// HTTP 请求(通过 fetch)
|
|
827
729
|
fetch: async (url, options = {}) => {
|
|
828
730
|
const { method = 'GET', headers = {}, body } = options
|
|
829
731
|
const res = await fetch(url, { method, headers, body })
|
|
830
732
|
return { status: res.status, headers: Object.fromEntries(res.headers), body: await res.text() }
|
|
831
733
|
}
|
|
832
734
|
}
|
|
833
|
-
// 使用沙箱执行用户代码,防止恶意代码执行
|
|
834
735
|
return await runInSandbox(handlerCode, { context, tools, ...helpers }, { timeout: 10000 })
|
|
835
736
|
} catch (err) {
|
|
836
737
|
return { success: false, error: `Handler error: ${err.message}` }
|
|
@@ -843,7 +744,6 @@ class WebPlugin extends Plugin {
|
|
|
843
744
|
const relativePath = pathname.substring(staticFolder.urlPath.length) || staticFolder.options.index
|
|
844
745
|
const filePath = path.join(staticFolder.folder, relativePath)
|
|
845
746
|
|
|
846
|
-
// 安全检查
|
|
847
747
|
if (!filePath.startsWith(staticFolder.folder)) {
|
|
848
748
|
return { type: 'forbidden' }
|
|
849
749
|
}
|
|
@@ -880,7 +780,6 @@ class WebPlugin extends Plugin {
|
|
|
880
780
|
_getAgent(sessionId) {
|
|
881
781
|
const finalSessionId = sessionId || `web_${Date.now()}`
|
|
882
782
|
|
|
883
|
-
// 尝试从对应平台插件获取 Agent
|
|
884
783
|
const platformPrefixes = ['weixin_', 'telegram_', 'feishu_']
|
|
885
784
|
for (const prefix of platformPrefixes) {
|
|
886
785
|
if (finalSessionId.startsWith(prefix)) {
|
|
@@ -893,9 +792,8 @@ class WebPlugin extends Plugin {
|
|
|
893
792
|
}
|
|
894
793
|
}
|
|
895
794
|
|
|
896
|
-
// 返回主 Agent
|
|
897
795
|
return this._framework._mainAgent || this._framework._agents?.[0]
|
|
898
796
|
}
|
|
899
797
|
}
|
|
900
798
|
|
|
901
|
-
module.exports = WebPlugin
|
|
799
|
+
module.exports = WebPlugin
|
|
@@ -3,14 +3,14 @@
|
|
|
3
3
|
* 四层记忆系统:user, feedback, project, reference
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
const { Plugin } = require('
|
|
7
|
-
const { logger } = require('
|
|
6
|
+
const { Plugin } = require('../../src/plugin/base')
|
|
7
|
+
const { logger } = require('../../src/common/logger')
|
|
8
8
|
const log = logger.child('Memory')
|
|
9
9
|
const { z } = require('zod')
|
|
10
10
|
const fs = require('fs')
|
|
11
11
|
const path = require('path')
|
|
12
12
|
const { EventEmitter } = require('events')
|
|
13
|
-
const {cleanResponse} =require('
|
|
13
|
+
const {cleanResponse} =require('../../src/utils')
|
|
14
14
|
/**
|
|
15
15
|
* 记忆类型常量
|
|
16
16
|
*/
|
|
@@ -972,20 +972,6 @@ class MemoryPlugin extends Plugin {
|
|
|
972
972
|
}
|
|
973
973
|
}
|
|
974
974
|
}
|
|
975
|
-
|
|
976
|
-
// 批量处理错误
|
|
977
|
-
// if (this._pendingErrors.length > 0) {
|
|
978
|
-
// const errors = this._pendingErrors.splice(0, 10) // 每次最多处理 10 条
|
|
979
|
-
// log.debug(`Processing ${errors.length} pending errors`)
|
|
980
|
-
|
|
981
|
-
// for (const errorData of errors) {
|
|
982
|
-
// try {
|
|
983
|
-
// await this._extractErrorLesson(errorData)
|
|
984
|
-
// } catch (err) {
|
|
985
|
-
// log.warn('Failed to extract error lesson:', err.message)
|
|
986
|
-
// }
|
|
987
|
-
// }
|
|
988
|
-
// }
|
|
989
975
|
} finally {
|
|
990
976
|
this._isExtracting = false
|
|
991
977
|
}
|
|
@@ -1158,7 +1144,7 @@ ${prompt}`
|
|
|
1158
1144
|
return parsed
|
|
1159
1145
|
} catch (parseErr) {
|
|
1160
1146
|
// JSON 解析失败,尝试清理不可见字符后重试
|
|
1161
|
-
const cleaned = jsonStr.replace(/[\
|
|
1147
|
+
const cleaned = jsonStr.replace(/[\x00-\x1f\x7f-\x9f\u200b-\u200f\u2028-\u2029]/g, '')
|
|
1162
1148
|
try {
|
|
1163
1149
|
const parsed = JSON.parse(cleaned)
|
|
1164
1150
|
return parsed
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# Email Plugin
|
|
2
|
+
|
|
3
|
+
SMTP/IMAP 邮件集成插件。
|
|
4
|
+
|
|
5
|
+
## 配置
|
|
6
|
+
|
|
7
|
+
通过 `config.email` 在 plugins.json 中配置:
|
|
8
|
+
- `smtpHost` — SMTP 服务器地址
|
|
9
|
+
- `smtpPort` — SMTP 端口
|
|
10
|
+
- `imapHost` — IMAP 服务器地址
|
|
11
|
+
- `imapPort` — IMAP 端口
|
|
12
|
+
- `user` — 邮箱账号
|
|
13
|
+
- `pass` — 邮箱密码
|
|
14
|
+
|
|
15
|
+
## 能力
|
|
16
|
+
|
|
17
|
+
- 发送邮件 (SMTP)
|
|
18
|
+
- 接收/监控邮件 (IMAP idle)
|
|
19
|
+
- 邮件回复、转发
|
|
@@ -3,8 +3,8 @@
|
|
|
3
3
|
* 邮件收发插件 - 支持读取和发送电子邮件、监控新邮件
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
const { Plugin } = require('
|
|
7
|
-
const { logger } = require('
|
|
6
|
+
const { Plugin } = require('../../../src/plugin/base')
|
|
7
|
+
const { logger } = require('../../../src/common/logger')
|
|
8
8
|
const log = logger.child('Email')
|
|
9
9
|
const { z } = require('zod')
|
|
10
10
|
const fs = require('fs')
|
|
@@ -75,7 +75,7 @@ class EmailPlugin extends Plugin {
|
|
|
75
75
|
- attachments.content: Base64内容
|
|
76
76
|
- attachments.cid: 嵌入式图片CID(HTML中用 <img src="cid:xxx"> 引用)`
|
|
77
77
|
this.priority = 50
|
|
78
|
-
this.enabled =
|
|
78
|
+
this.enabled = config.enabled === true
|
|
79
79
|
|
|
80
80
|
this.tools={}
|
|
81
81
|
|
|
@@ -8,10 +8,10 @@
|
|
|
8
8
|
* - allowedUsers: 允许的用户 openId 数组
|
|
9
9
|
*/
|
|
10
10
|
|
|
11
|
-
const { Plugin } = require('
|
|
12
|
-
const { logger } = require('
|
|
11
|
+
const { Plugin } = require('../../../src/plugin/base')
|
|
12
|
+
const { logger } = require('../../../src/common/logger')
|
|
13
13
|
const log = logger.child('Feishu')
|
|
14
|
-
const {cleanResponse} =require('
|
|
14
|
+
const {cleanResponse} =require('../../../src/utils')
|
|
15
15
|
const removeMarkdown = require('remove-markdown');
|
|
16
16
|
class FeishuPlugin extends Plugin {
|
|
17
17
|
constructor(config = {}) {
|
|
@@ -20,7 +20,7 @@ class FeishuPlugin extends Plugin {
|
|
|
20
20
|
this.version = '1.1.0'
|
|
21
21
|
this.description = '飞书对话插件,使用 WebSocket 长连接接收消息'
|
|
22
22
|
this.priority = 80
|
|
23
|
-
this.enabled =
|
|
23
|
+
this.enabled = config.enabled === true
|
|
24
24
|
this.systemPrompt = `你是一个飞书助手。回复内容不要使用markdown格式文本。
|
|
25
25
|
|
|
26
26
|
**重要:** 子Agent 匹配规则必须遵守:
|