evolcore 0.0.9 → 0.0.11
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/CHANGELOG.md +29 -0
- package/README.md +3 -3
- package/dist/agents/baseagent.js +4 -0
- package/dist/agents/claude-runner.js +123 -42
- package/dist/agents/codex-app-server-client.js +33 -9
- package/dist/agents/codex-runner.js +58 -8
- package/dist/agents/ecagent-runner.js +17 -2
- package/dist/agents/request-identity.js +55 -0
- package/dist/aun/outbox.js +28 -31
- package/dist/channels/aun.js +131 -128
- package/dist/cli/agent-command.js +16 -9
- package/dist/cli/agent.js +82 -19
- package/dist/cli/daemon-commands.js +21 -2
- package/dist/cli/index.js +76 -61
- package/dist/cli/init-cancel.js +208 -0
- package/dist/cli/init-channel.js +343 -195
- package/dist/cli/init.js +21 -9
- package/dist/config/builtin-roles.js +1 -0
- package/dist/config/contact-book-store.js +1 -1
- package/dist/config/gateway-config.js +26 -10
- package/dist/core/agent-reload-coordinator.js +53 -0
- package/dist/core/auth/operation-authorizer.js +32 -147
- package/dist/core/auth/operation-catalog.js +80 -0
- package/dist/core/bootstrap-messages.js +50 -0
- package/dist/core/bootstrap-service.js +85 -10
- package/dist/core/channel-loader.js +23 -6
- package/dist/core/command/agent-control.js +14 -11
- package/dist/core/command/menu-handler.js +67 -76
- package/dist/core/command/slash-handler.js +4 -4
- package/dist/core/data-migration.js +79 -27
- package/dist/core/evolagent-registry.js +125 -35
- package/dist/core/evolagent.js +8 -3
- package/dist/core/inference/text-inference.js +38 -4
- package/dist/core/message/message-bridge.js +1 -1
- package/dist/core/message/message-log.js +22 -0
- package/dist/core/message/message-queue.js +19 -4
- package/dist/core/model/model-catalog.js +143 -24
- package/dist/core/model/model-diagnostics.js +28 -10
- package/dist/core/permission/index.js +1 -0
- package/dist/core/permission/readonly-shell-query.js +532 -0
- package/dist/core/permission/shell-environment.js +46 -0
- package/dist/core/permission/tool-policy.js +231 -93
- package/dist/core/protected-paths.js +10 -7
- package/dist/core/runner-reload-transaction.js +57 -0
- package/dist/index.js +262 -84
- package/dist/ipc.js +29 -11
- package/dist/utils/aid-bind.js +3 -8
- package/dist/utils/log-writer.js +6 -10
- package/dist/utils/logger.js +5 -5
- package/kits/docs/evolcore/msg.md +13 -0
- package/kits/rules/01-overview.md +9 -0
- package/kits/schemas/agent-config.schema.3.json +1 -1
- package/kits/schemas/agent-config.schema.4.json +1 -1
- package/kits/schemas/relation-config.schema.2.json +1 -1
- package/kits/schemas/role-config.schema.1.json +1 -1
- package/kits/templates/roles/admin.json +5 -0
- package/kits/templates/roles/member.json +17 -0
- package/kits/templates/roles/visitor.json +8 -0
- package/kits/templates/system-fragments/bootstrap.md +12 -6
- package/kits/templates/system-fragments/channel.md +6 -0
- package/kits/templates/system-fragments/session.md +2 -0
- package/package.json +2 -1
- package/skills/eclink/SKILL.md +15 -3
- package/skills/eclink/agents/openai.yaml +3 -3
|
@@ -179,6 +179,8 @@ Options:
|
|
|
179
179
|
}
|
|
180
180
|
process.exit(1);
|
|
181
181
|
}
|
|
182
|
+
if (result.ownerBindInterrupted)
|
|
183
|
+
return;
|
|
182
184
|
if (formatJson) {
|
|
183
185
|
console.log(JSON.stringify(result, null, 2));
|
|
184
186
|
}
|
|
@@ -211,6 +213,8 @@ Options:
|
|
|
211
213
|
}
|
|
212
214
|
process.exit(1);
|
|
213
215
|
}
|
|
216
|
+
if (result.ownerBindInterrupted)
|
|
217
|
+
return;
|
|
214
218
|
if (formatJson) {
|
|
215
219
|
console.log(JSON.stringify(result, null, 2));
|
|
216
220
|
}
|
|
@@ -259,15 +263,16 @@ Options:
|
|
|
259
263
|
// --- reload ---
|
|
260
264
|
if (sub === 'reload') {
|
|
261
265
|
if (wantsHelp(args)) {
|
|
262
|
-
console.log(`用法: ec agent reload [aid] [--format json]
|
|
266
|
+
console.log(`用法: ec agent reload [aid] [--force] [--format json]
|
|
263
267
|
|
|
264
268
|
热重载 agent 配置。
|
|
265
269
|
无参数 全量 resync(扫磁盘,新增上线、删除下线、修改热更新)
|
|
266
|
-
<aid> 仅热重载指定 agent
|
|
270
|
+
<aid> 仅热重载指定 agent
|
|
271
|
+
--force 中断目标 Agent 的运行中任务并清空排队任务后重载(仅与 <aid> 同用)`);
|
|
267
272
|
return;
|
|
268
273
|
}
|
|
269
274
|
const target = args[1] && !args[1].startsWith('--') ? args[1] : undefined;
|
|
270
|
-
const result = await agentReload(target);
|
|
275
|
+
const result = await agentReload(target, { force: args.includes('--force') });
|
|
271
276
|
if (!result.ok) {
|
|
272
277
|
if (formatJson) {
|
|
273
278
|
console.log(JSON.stringify(result));
|
|
@@ -294,9 +299,10 @@ Options:
|
|
|
294
299
|
// --- enable ---
|
|
295
300
|
if (sub === 'enable') {
|
|
296
301
|
if (wantsHelp(args)) {
|
|
297
|
-
console.log(`用法: ec agent enable <aid> [--format json]
|
|
302
|
+
console.log(`用法: ec agent enable <aid> [--force] [--format json]
|
|
298
303
|
|
|
299
|
-
启用 agent。若服务运行中会热重载,否则下次 ec start
|
|
304
|
+
启用 agent。若服务运行中会热重载,否则下次 ec start 时生效。
|
|
305
|
+
--force 中断目标 Agent 的运行中任务并清空排队任务后重载`);
|
|
300
306
|
return;
|
|
301
307
|
}
|
|
302
308
|
const aid = args[1];
|
|
@@ -304,7 +310,7 @@ Options:
|
|
|
304
310
|
console.error('用法: ec agent enable <aid>');
|
|
305
311
|
process.exit(1);
|
|
306
312
|
}
|
|
307
|
-
const result = await agentEnable(aid);
|
|
313
|
+
const result = await agentEnable(aid, { force: args.includes('--force') });
|
|
308
314
|
if (!result.ok) {
|
|
309
315
|
if (formatJson) {
|
|
310
316
|
console.log(JSON.stringify(result));
|
|
@@ -325,9 +331,10 @@ Options:
|
|
|
325
331
|
// --- disable ---
|
|
326
332
|
if (sub === 'disable') {
|
|
327
333
|
if (wantsHelp(args)) {
|
|
328
|
-
console.log(`用法: ec agent disable <aid> [--format json]
|
|
334
|
+
console.log(`用法: ec agent disable <aid> [--force] [--format json]
|
|
329
335
|
|
|
330
|
-
停用 agent
|
|
336
|
+
停用 agent。若服务运行中会热重载离线,否则在配置中标记为禁用。
|
|
337
|
+
--force 中断目标 Agent 的运行中任务并清空排队任务后重载`);
|
|
331
338
|
return;
|
|
332
339
|
}
|
|
333
340
|
const aid = args[1];
|
|
@@ -335,7 +342,7 @@ Options:
|
|
|
335
342
|
console.error('用法: ec agent disable <aid>');
|
|
336
343
|
process.exit(1);
|
|
337
344
|
}
|
|
338
|
-
const result = await agentDisable(aid);
|
|
345
|
+
const result = await agentDisable(aid, { force: args.includes('--force') });
|
|
339
346
|
if (!result.ok) {
|
|
340
347
|
if (formatJson) {
|
|
341
348
|
console.log(JSON.stringify(result));
|
package/dist/cli/agent.js
CHANGED
|
@@ -8,7 +8,8 @@ import { resolveConfigCommand } from '../config/resolved-config-op.js';
|
|
|
8
8
|
import { executeResolvedConfigCommand } from '../config/config-operation-service.js';
|
|
9
9
|
import { ipcQuery } from '../ipc.js';
|
|
10
10
|
import { CONFIG_SCHEMA_VERSION } from '../types.js';
|
|
11
|
-
import { withLifecycleForWrite } from '../config/lifecycle.js';
|
|
11
|
+
import { normalizeAgentLifecycle, withLifecycleForWrite } from '../config/lifecycle.js';
|
|
12
|
+
import { preparePostBootstrapWelcomeOutbox } from '../core/bootstrap-messages.js';
|
|
12
13
|
import { ensureInitialRoleRegistry } from '../config/role-service.js';
|
|
13
14
|
import { isValidChannelName } from '../core/channel-loader.js';
|
|
14
15
|
import { commandExists } from '../utils/cross-platform.js';
|
|
@@ -16,6 +17,7 @@ import { getCodexAppServerAvailability, isCodexAppServerAvailable } from '../age
|
|
|
16
17
|
import { resolveEcagentConfig } from '../agents/baseagent.js';
|
|
17
18
|
import { agentProjectRootFromDefaults, deriveAgentProjectPath } from '../utils/project-path.js';
|
|
18
19
|
import { AGENT_DELEGATION_TOKEN_ENV } from '../core/auth/agent-delegation.js';
|
|
20
|
+
import { readTaskRuntimeContextFromEnv } from './task-context.js';
|
|
19
21
|
function withStaticOwner(config, owner) {
|
|
20
22
|
const value = owner?.trim();
|
|
21
23
|
if (!value)
|
|
@@ -458,6 +460,7 @@ export async function agentCreateInteractive(opts = {}) {
|
|
|
458
460
|
catch { /* daemon not running */ }
|
|
459
461
|
let ownerBoundAid;
|
|
460
462
|
let ownerBindSkipped = false;
|
|
463
|
+
let ownerBindInterrupted = false;
|
|
461
464
|
// Only prompt for agent owner binding if:
|
|
462
465
|
// 1. User didn't manually input owner during setup (owner is undefined)
|
|
463
466
|
// 2. User didn't skip QR binding explicitly (skipQrBinding is false)
|
|
@@ -467,15 +470,18 @@ export async function agentCreateInteractive(opts = {}) {
|
|
|
467
470
|
console.log('\n📡 Agent owner 绑定 — 请用 evol app 扫描二维码,10 分钟内有效\n');
|
|
468
471
|
try {
|
|
469
472
|
const { runAgentOwnerQrBindFlow } = await import('./init-channel.js');
|
|
470
|
-
const bound = await runAgentOwnerQrBindFlow(aid, agentName
|
|
471
|
-
if (bound
|
|
473
|
+
const bound = await runAgentOwnerQrBindFlow(aid, agentName);
|
|
474
|
+
if (bound.action === 'bound') {
|
|
472
475
|
ownerBoundAid = bound.boundAid;
|
|
473
476
|
console.log(` ✓ 已配置 agent owner: ${bound.boundAid}`);
|
|
474
477
|
}
|
|
475
|
-
else {
|
|
478
|
+
else if (bound.action === 'manual') {
|
|
476
479
|
ownerBindSkipped = true;
|
|
477
480
|
ownerBoundAid = await promptAgentOwnerManually(aid);
|
|
478
481
|
}
|
|
482
|
+
else {
|
|
483
|
+
ownerBindInterrupted = true;
|
|
484
|
+
}
|
|
479
485
|
}
|
|
480
486
|
catch (e) {
|
|
481
487
|
ownerBindSkipped = true;
|
|
@@ -493,6 +499,7 @@ export async function agentCreateInteractive(opts = {}) {
|
|
|
493
499
|
hotLoadError,
|
|
494
500
|
ownerBoundAid,
|
|
495
501
|
ownerBindSkipped,
|
|
502
|
+
ownerBindInterrupted,
|
|
496
503
|
};
|
|
497
504
|
}
|
|
498
505
|
finally {
|
|
@@ -784,12 +791,17 @@ export async function agentSyncAids() {
|
|
|
784
791
|
return { ok: true, created, template: templateAgent.aid, hotReloaded };
|
|
785
792
|
}
|
|
786
793
|
// ==================== agentReload ====================
|
|
787
|
-
|
|
794
|
+
const AGENT_RELOAD_TIMEOUT_MS = 45_000;
|
|
795
|
+
const AGENT_RESYNC_TIMEOUT_MS = 5 * 60_000;
|
|
796
|
+
export async function agentReload(aid, options = {}) {
|
|
788
797
|
const p = resolvePaths();
|
|
789
798
|
if (!aid) {
|
|
799
|
+
if (options.force) {
|
|
800
|
+
return { ok: false, code: 'INVALID_ARGS', error: '--force requires a target Agent AID' };
|
|
801
|
+
}
|
|
790
802
|
// Full resync
|
|
791
803
|
try {
|
|
792
|
-
const result = await ipcQuery(p.socket, { type: 'evolagent.resync' });
|
|
804
|
+
const result = await ipcQuery(p.socket, { type: 'evolagent.resync' }, AGENT_RESYNC_TIMEOUT_MS);
|
|
793
805
|
if (result === null) {
|
|
794
806
|
return { ok: false, error: 'evolcore 未运行,请先 ec start' };
|
|
795
807
|
}
|
|
@@ -804,27 +816,27 @@ export async function agentReload(aid) {
|
|
|
804
816
|
}
|
|
805
817
|
// Single agent reload
|
|
806
818
|
try {
|
|
807
|
-
const result = await ipcQuery(p.socket, { type: 'evolagent.reload', name: aid });
|
|
819
|
+
const result = await ipcQuery(p.socket, { type: 'evolagent.reload', name: aid, force: options.force === true }, AGENT_RELOAD_TIMEOUT_MS);
|
|
808
820
|
if (result === null) {
|
|
809
821
|
return { ok: false, error: 'evolcore 未运行,请先 ec start 后再 reload' };
|
|
810
822
|
}
|
|
811
823
|
if (result?.ok) {
|
|
812
824
|
return { ok: true };
|
|
813
825
|
}
|
|
814
|
-
return { ok: false, error: result?.error || 'unknown error' };
|
|
826
|
+
return { ok: false, code: result?.code, error: result?.error || 'unknown error' };
|
|
815
827
|
}
|
|
816
828
|
catch {
|
|
817
829
|
return { ok: false, error: 'evolcore 未运行,请先 ec start 后再 reload' };
|
|
818
830
|
}
|
|
819
831
|
}
|
|
820
832
|
// ==================== agentEnable / agentDisable ====================
|
|
821
|
-
export async function agentEnable(aid) {
|
|
822
|
-
return agentSetEnabled(aid, true);
|
|
833
|
+
export async function agentEnable(aid, options = {}) {
|
|
834
|
+
return agentSetEnabled(aid, true, options);
|
|
823
835
|
}
|
|
824
|
-
export async function agentDisable(aid) {
|
|
825
|
-
return agentSetEnabled(aid, false);
|
|
836
|
+
export async function agentDisable(aid, options = {}) {
|
|
837
|
+
return agentSetEnabled(aid, false, options);
|
|
826
838
|
}
|
|
827
|
-
async function agentSetEnabled(aid, enabled) {
|
|
839
|
+
async function agentSetEnabled(aid, enabled, options = {}) {
|
|
828
840
|
const p = resolvePaths();
|
|
829
841
|
let config;
|
|
830
842
|
try {
|
|
@@ -836,15 +848,28 @@ async function agentSetEnabled(aid, enabled) {
|
|
|
836
848
|
if (!config) {
|
|
837
849
|
return { ok: false, error: `Agent "${aid}" not found` };
|
|
838
850
|
}
|
|
851
|
+
const previousEnabled = config.enabled;
|
|
839
852
|
config.enabled = enabled;
|
|
840
853
|
saveAgent(config);
|
|
841
854
|
// Try to hot-reload if daemon is running, but don't fail if it's not
|
|
842
855
|
let reloaded = false;
|
|
843
856
|
try {
|
|
844
|
-
const result = await ipcQuery(p.socket, {
|
|
857
|
+
const result = await ipcQuery(p.socket, {
|
|
858
|
+
type: 'evolagent.reload',
|
|
859
|
+
name: aid,
|
|
860
|
+
force: options.force === true,
|
|
861
|
+
}, AGENT_RELOAD_TIMEOUT_MS);
|
|
845
862
|
if (result?.ok) {
|
|
846
863
|
reloaded = true;
|
|
847
864
|
}
|
|
865
|
+
else if (result?.code === 'AGENT_BUSY') {
|
|
866
|
+
if (previousEnabled === undefined)
|
|
867
|
+
delete config.enabled;
|
|
868
|
+
else
|
|
869
|
+
config.enabled = previousEnabled;
|
|
870
|
+
saveAgent(config);
|
|
871
|
+
return { ok: false, code: result.code, error: result.error || 'Agent is busy' };
|
|
872
|
+
}
|
|
848
873
|
}
|
|
849
874
|
catch {
|
|
850
875
|
// Daemon not running or unreachable — that's ok, config is already saved
|
|
@@ -1075,16 +1100,54 @@ export async function agentRename(aid, name) {
|
|
|
1075
1100
|
}
|
|
1076
1101
|
// ==================== agentReady ====================
|
|
1077
1102
|
export async function agentReady(aid) {
|
|
1103
|
+
const taskSelfAid = readTaskRuntimeContextFromEnv()?.selfAid;
|
|
1104
|
+
if (taskSelfAid && taskSelfAid.replace(/^@/, '') !== aid.replace(/^@/, '')) {
|
|
1105
|
+
return {
|
|
1106
|
+
ok: false,
|
|
1107
|
+
code: 'SELF_AGENT_REQUIRED',
|
|
1108
|
+
error: `A managed task can only complete bootstrap for itself (${taskSelfAid})`,
|
|
1109
|
+
};
|
|
1110
|
+
}
|
|
1078
1111
|
const p = resolvePaths();
|
|
1079
1112
|
const config = loadAgent(aid);
|
|
1080
1113
|
if (!config)
|
|
1081
1114
|
return { ok: false, error: `Agent "${aid}" not found` };
|
|
1082
|
-
saveAgent(withLifecycleForWrite(config, 'active'));
|
|
1083
|
-
let reloaded = false;
|
|
1084
1115
|
try {
|
|
1085
1116
|
const result = await ipcQuery(p.socket, { type: 'evolagent.bootstrapComplete', aid }, 30_000);
|
|
1086
|
-
|
|
1117
|
+
if (!result) {
|
|
1118
|
+
const offlineConfig = loadAgent(aid) || config;
|
|
1119
|
+
const lifecycle = normalizeAgentLifecycle(offlineConfig).lifecycle;
|
|
1120
|
+
if (lifecycle === 'active')
|
|
1121
|
+
return { ok: true, aid, reloaded: false };
|
|
1122
|
+
if (lifecycle !== 'bootstrapping') {
|
|
1123
|
+
return { ok: false, code: 'INVALID_LIFECYCLE', error: `Agent "${aid}" is ${lifecycle}; only a bootstrapping agent can become ready` };
|
|
1124
|
+
}
|
|
1125
|
+
const owner = offlineConfig.owners?.[0];
|
|
1126
|
+
if (!owner)
|
|
1127
|
+
return { ok: false, code: 'OWNER_REQUIRED', error: `Agent "${aid}" has no owner for the completion welcome` };
|
|
1128
|
+
try {
|
|
1129
|
+
preparePostBootstrapWelcomeOutbox(aid, owner);
|
|
1130
|
+
saveAgent(withLifecycleForWrite(offlineConfig, 'active'));
|
|
1131
|
+
}
|
|
1132
|
+
catch (e) {
|
|
1133
|
+
return {
|
|
1134
|
+
ok: false,
|
|
1135
|
+
code: 'READY_PERSIST_FAILED',
|
|
1136
|
+
error: e instanceof Error ? e.message : 'Failed to persist bootstrap completion',
|
|
1137
|
+
};
|
|
1138
|
+
}
|
|
1139
|
+
return { ok: true, aid, reloaded: false };
|
|
1140
|
+
}
|
|
1141
|
+
if (!result.ok) {
|
|
1142
|
+
return { ok: false, code: result.code, error: result.error || 'Failed to complete bootstrap' };
|
|
1143
|
+
}
|
|
1144
|
+
return { ok: true, aid, reloaded: true };
|
|
1145
|
+
}
|
|
1146
|
+
catch (e) {
|
|
1147
|
+
return {
|
|
1148
|
+
ok: false,
|
|
1149
|
+
code: 'DAEMON_UNAVAILABLE',
|
|
1150
|
+
error: e instanceof Error ? e.message : 'Unable to connect to the EvolCore daemon',
|
|
1151
|
+
};
|
|
1087
1152
|
}
|
|
1088
|
-
catch { /* daemon not running */ }
|
|
1089
|
-
return { ok: true, aid, reloaded };
|
|
1090
1153
|
}
|
|
@@ -28,7 +28,20 @@ import { AGENT_DELEGATION_TOKEN_ENV } from '../core/auth/agent-delegation.js';
|
|
|
28
28
|
import { WEB_CLI_BIN, WEB_PACKAGE_LATEST, WEB_PACKAGE_NAME } from '../product.js';
|
|
29
29
|
import { rotateStdoutLog } from '../utils/log-writer.js';
|
|
30
30
|
import { inspectDataMigrationRequirement } from '../core/data-migration.js';
|
|
31
|
+
import { isInitCancelledError, printInitCancelHint } from './init-cancel.js';
|
|
31
32
|
const execFileAsync = promisify(execFile);
|
|
33
|
+
async function runAutomaticInit(action) {
|
|
34
|
+
try {
|
|
35
|
+
return await action();
|
|
36
|
+
}
|
|
37
|
+
catch (error) {
|
|
38
|
+
if (!isInitCancelledError(error))
|
|
39
|
+
throw error;
|
|
40
|
+
console.log('\n已退出初始化,未启动 EvolCore。');
|
|
41
|
+
process.exitCode = 130;
|
|
42
|
+
return false;
|
|
43
|
+
}
|
|
44
|
+
}
|
|
32
45
|
function printNoSelfAgentHints(options) {
|
|
33
46
|
const { daemonConfig, ecwebStarted, skipped } = options;
|
|
34
47
|
console.log('\nℹ 未配置任何 self-agent,Control Plane 已启动。');
|
|
@@ -265,7 +278,11 @@ export async function cmdStart(opts = {}) {
|
|
|
265
278
|
// 这里需显式抑制 AUN SDK 的常规 keystore 日志。
|
|
266
279
|
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
267
280
|
suppressSdkLogs();
|
|
268
|
-
await cmdInit({ invokedByStart: true })
|
|
281
|
+
if (!await runAutomaticInit(() => cmdInit({ invokedByStart: true }))) {
|
|
282
|
+
if (process.exitCode == null)
|
|
283
|
+
console.log('⚠ 初始化未完成,未启动 EvolCore。');
|
|
284
|
+
return;
|
|
285
|
+
}
|
|
269
286
|
if (!loadDefaults()) {
|
|
270
287
|
console.log('⚠ 初始化未完成,未启动 EvolCore。');
|
|
271
288
|
return;
|
|
@@ -280,7 +297,9 @@ export async function cmdStart(opts = {}) {
|
|
|
280
297
|
console.log('⚡ 控制 AID 未配置,自动补全...\n');
|
|
281
298
|
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
282
299
|
suppressSdkLogs();
|
|
283
|
-
|
|
300
|
+
printInitCancelHint();
|
|
301
|
+
if (!await runAutomaticInit(() => initTail()))
|
|
302
|
+
return;
|
|
284
303
|
return;
|
|
285
304
|
}
|
|
286
305
|
if (!daemonCfgStart.aid) {
|
package/dist/cli/index.js
CHANGED
|
@@ -15,6 +15,7 @@ import { cmdCtl } from './ctl-command.js';
|
|
|
15
15
|
import { cmdQueue } from './queue-command.js';
|
|
16
16
|
import { cmdStart, cmdStop, cmdRestart, cmdStatus, cmdLogs, cmdWatchCommand, cmdMv, cmdDiagnose } from './daemon-commands.js';
|
|
17
17
|
import { logCliCommand } from './command-log.js';
|
|
18
|
+
import { isInitCancelledError, printInitCancelHint } from './init-cancel.js';
|
|
18
19
|
const MAIN_HELP = `用法: ec <command> [选项]
|
|
19
20
|
|
|
20
21
|
服务:
|
|
@@ -97,9 +98,10 @@ export async function main(args) {
|
|
|
97
98
|
return;
|
|
98
99
|
}
|
|
99
100
|
switch (cmd) {
|
|
100
|
-
case 'init':
|
|
101
|
-
|
|
102
|
-
|
|
101
|
+
case 'init': {
|
|
102
|
+
try {
|
|
103
|
+
if (wantsHelp(args.slice(1))) {
|
|
104
|
+
console.log(`用法: ec init [渠道] [选项]
|
|
103
105
|
|
|
104
106
|
仅初始化 defaults.json:
|
|
105
107
|
ec init 交互式(写完 defaults.json 后嵌套 agent new)
|
|
@@ -119,72 +121,85 @@ export async function main(args) {
|
|
|
119
121
|
--force 已有不同 owner 时强制覆盖
|
|
120
122
|
|
|
121
123
|
配置渠道(先 ec agent new 创建 agent):
|
|
122
|
-
ec init aun AUN owner
|
|
124
|
+
ec init aun AUN owner 追加绑定(daemon 或指定 agent)
|
|
123
125
|
ec init feishu 飞书扫码登录
|
|
124
126
|
ec init wechat 微信扫码登录
|
|
125
127
|
ec init dingtalk 钉钉扫码登录
|
|
126
128
|
ec init qqbot QQ 机器人扫码绑定
|
|
127
129
|
ec init wecom 企业微信 AI Bot 扫码创建/手工配置`);
|
|
128
|
-
}
|
|
129
|
-
else if (args[1] === 'aun') {
|
|
130
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
131
|
-
suppressSdkLogs();
|
|
132
|
-
await cmdInitAun();
|
|
133
|
-
}
|
|
134
|
-
else if (args[1] === 'wechat') {
|
|
135
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
136
|
-
suppressSdkLogs();
|
|
137
|
-
await cmdInitWechat();
|
|
138
|
-
}
|
|
139
|
-
else if (args[1] === 'feishu') {
|
|
140
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
141
|
-
suppressSdkLogs();
|
|
142
|
-
await cmdInitFeishu();
|
|
143
|
-
}
|
|
144
|
-
else if (args[1] === 'dingtalk') {
|
|
145
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
146
|
-
suppressSdkLogs();
|
|
147
|
-
await cmdInitDingtalk();
|
|
148
|
-
}
|
|
149
|
-
else if (args[1] === 'qqbot') {
|
|
150
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
151
|
-
suppressSdkLogs();
|
|
152
|
-
await cmdInitQQBot();
|
|
153
|
-
}
|
|
154
|
-
else if (args[1] === 'wecom') {
|
|
155
|
-
await cmdInitWecom();
|
|
156
|
-
}
|
|
157
|
-
else if (args[1] && !args[1].startsWith('-')) {
|
|
158
|
-
const supported = ['feishu', 'wechat', 'aun', 'dingtalk', 'qqbot', 'wecom'];
|
|
159
|
-
console.error(`❌ 不支持的渠道: ${args[1]}`);
|
|
160
|
-
console.error(` 支持的渠道: ${supported.join(', ')}`);
|
|
161
|
-
process.exit(1);
|
|
162
|
-
}
|
|
163
|
-
else {
|
|
164
|
-
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
165
|
-
suppressSdkLogs();
|
|
166
|
-
const nonInteractive = args.includes('--non-interactive');
|
|
167
|
-
const wantsAutoStart = args.includes('--auto-start');
|
|
168
|
-
const wantsNoAutoStart = args.includes('--no-auto-start');
|
|
169
|
-
if (wantsAutoStart && wantsNoAutoStart) {
|
|
170
|
-
console.error('❌ --auto-start 与 --no-auto-start 不能同时使用');
|
|
171
|
-
process.exitCode = 1;
|
|
172
|
-
break;
|
|
173
130
|
}
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
131
|
+
else {
|
|
132
|
+
const hasChannelTarget = Boolean(args[1] && !args[1].startsWith('-'));
|
|
133
|
+
if (hasChannelTarget)
|
|
134
|
+
printInitCancelHint();
|
|
135
|
+
if (args[1] === 'aun') {
|
|
136
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
137
|
+
suppressSdkLogs();
|
|
138
|
+
await cmdInitAun();
|
|
139
|
+
}
|
|
140
|
+
else if (args[1] === 'wechat') {
|
|
141
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
142
|
+
suppressSdkLogs();
|
|
143
|
+
await cmdInitWechat();
|
|
144
|
+
}
|
|
145
|
+
else if (args[1] === 'feishu') {
|
|
146
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
147
|
+
suppressSdkLogs();
|
|
148
|
+
await cmdInitFeishu();
|
|
149
|
+
}
|
|
150
|
+
else if (args[1] === 'dingtalk') {
|
|
151
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
152
|
+
suppressSdkLogs();
|
|
153
|
+
await cmdInitDingtalk();
|
|
154
|
+
}
|
|
155
|
+
else if (args[1] === 'qqbot') {
|
|
156
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
157
|
+
suppressSdkLogs();
|
|
158
|
+
await cmdInitQQBot();
|
|
159
|
+
}
|
|
160
|
+
else if (args[1] === 'wecom') {
|
|
161
|
+
await cmdInitWecom();
|
|
162
|
+
}
|
|
163
|
+
else if (args[1] && !args[1].startsWith('-')) {
|
|
164
|
+
const supported = ['feishu', 'wechat', 'aun', 'dingtalk', 'qqbot', 'wecom'];
|
|
165
|
+
console.error(`❌ 不支持的渠道: ${args[1]}`);
|
|
166
|
+
console.error(` 支持的渠道: ${supported.join(', ')}`);
|
|
167
|
+
process.exit(1);
|
|
168
|
+
}
|
|
169
|
+
else {
|
|
170
|
+
const { suppressSdkLogs } = await import('../aun/aid/index.js');
|
|
171
|
+
suppressSdkLogs();
|
|
172
|
+
const nonInteractive = args.includes('--non-interactive');
|
|
173
|
+
const wantsAutoStart = args.includes('--auto-start');
|
|
174
|
+
const wantsNoAutoStart = args.includes('--no-auto-start');
|
|
175
|
+
if (wantsAutoStart && wantsNoAutoStart) {
|
|
176
|
+
console.error('❌ --auto-start 与 --no-auto-start 不能同时使用');
|
|
177
|
+
process.exitCode = 1;
|
|
178
|
+
break;
|
|
179
|
+
}
|
|
180
|
+
const initialized = await cmdInit({
|
|
181
|
+
nonInteractive,
|
|
182
|
+
baseagent: getArgValue(args, '--baseagent'),
|
|
183
|
+
force: args.includes('--force'),
|
|
184
|
+
owner: getArgValue(args, '--owner'),
|
|
185
|
+
projectpath: getArgValue(args, '--projectpath'),
|
|
186
|
+
ecweb: args.includes('--ecweb') ? true : undefined,
|
|
187
|
+
format: getArgValue(args, '--format'),
|
|
188
|
+
autoStart: wantsAutoStart ? true : wantsNoAutoStart ? false : undefined,
|
|
189
|
+
});
|
|
190
|
+
if (!initialized && process.exitCode == null)
|
|
191
|
+
process.exitCode = 1;
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
}
|
|
195
|
+
catch (error) {
|
|
196
|
+
if (!isInitCancelledError(error))
|
|
197
|
+
throw error;
|
|
198
|
+
console.log('\n已退出初始化');
|
|
199
|
+
process.exitCode = 130;
|
|
186
200
|
}
|
|
187
201
|
break;
|
|
202
|
+
}
|
|
188
203
|
case 'start':
|
|
189
204
|
if (wantsHelp(args.slice(1))) {
|
|
190
205
|
printLifecycleHelp('start');
|