@keyou007/agent-bot 0.1.14-alpha.0 → 0.1.14-alpha.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 (113) hide show
  1. package/CHANGELOG.md +26 -0
  2. package/README.md +82 -55
  3. package/README.zh.md +82 -55
  4. package/config.example.yaml +5 -1
  5. package/dist/cli/AutostartManager.js +431 -0
  6. package/dist/cli/AutostartManager.js.map +1 -0
  7. package/dist/cli/FeishuAppConfiguration.js +17 -13
  8. package/dist/cli/FeishuAppConfiguration.js.map +1 -1
  9. package/dist/cli/Initializer.js +35 -0
  10. package/dist/cli/Initializer.js.map +1 -1
  11. package/dist/cli/SelfUpdateRunner.js +552 -0
  12. package/dist/cli/SelfUpdateRunner.js.map +1 -0
  13. package/dist/cli/SelfUpdater.js +431 -0
  14. package/dist/cli/SelfUpdater.js.map +1 -0
  15. package/dist/cli/autostartOutput.js +63 -0
  16. package/dist/cli/autostartOutput.js.map +1 -0
  17. package/dist/cli/controlProtocol.js.map +1 -1
  18. package/dist/cli/help.js +92 -18
  19. package/dist/cli/help.js.map +1 -1
  20. package/dist/cli/taskGroupOptions.js +14 -11
  21. package/dist/cli/taskGroupOptions.js.map +1 -1
  22. package/dist/cli/taskListOutput.js +3 -0
  23. package/dist/cli/taskListOutput.js.map +1 -1
  24. package/dist/cli/taskTarget.js +99 -0
  25. package/dist/cli/taskTarget.js.map +1 -0
  26. package/dist/cli.js +643 -58
  27. package/dist/cli.js.map +1 -1
  28. package/dist/codex/CodexRuntime.js +16 -5
  29. package/dist/codex/CodexRuntime.js.map +1 -1
  30. package/dist/commands/CommandRouter.js +20 -1
  31. package/dist/commands/CommandRouter.js.map +1 -1
  32. package/dist/config/loadConfig.js +2 -0
  33. package/dist/config/loadConfig.js.map +1 -1
  34. package/dist/config/schema.js +2 -0
  35. package/dist/config/schema.js.map +1 -1
  36. package/dist/console/ConsoleTurnPresenter.js +2 -0
  37. package/dist/console/ConsoleTurnPresenter.js.map +1 -1
  38. package/dist/feishu/CardRenderer.js +584 -16
  39. package/dist/feishu/CardRenderer.js.map +1 -1
  40. package/dist/feishu/FeishuConnector.js +29 -8
  41. package/dist/feishu/FeishuConnector.js.map +1 -1
  42. package/dist/feishu/FeishuMarkdown.js +25 -1
  43. package/dist/feishu/FeishuMarkdown.js.map +1 -1
  44. package/dist/feishu/FeishuMessageClient.js +43 -0
  45. package/dist/feishu/FeishuMessageClient.js.map +1 -1
  46. package/dist/feishu/FeishuTurnPresenter.js +29 -1
  47. package/dist/feishu/FeishuTurnPresenter.js.map +1 -1
  48. package/dist/feishu/ownerAccess.js +7 -0
  49. package/dist/feishu/ownerAccess.js.map +1 -0
  50. package/dist/index.js +148 -19
  51. package/dist/index.js.map +1 -1
  52. package/dist/presentation/OutboundRouter.js +19 -1
  53. package/dist/presentation/OutboundRouter.js.map +1 -1
  54. package/dist/proxy/ProxySessionController.js +1444 -66
  55. package/dist/proxy/ProxySessionController.js.map +1 -1
  56. package/dist/startup/StartupNotifier.js +65 -16
  57. package/dist/startup/StartupNotifier.js.map +1 -1
  58. package/dist/startup/startFeishu.js +2 -2
  59. package/dist/startup/startFeishu.js.map +1 -1
  60. package/dist/state/StateStore.js +268 -67
  61. package/dist/state/StateStore.js.map +1 -1
  62. package/dist/state/migrations.js +26 -0
  63. package/dist/state/migrations.js.map +1 -1
  64. package/dist/supervision/SafeRestartNotifier.js +17 -16
  65. package/dist/supervision/SafeRestartNotifier.js.map +1 -1
  66. package/dist/supervision/SafeRestartScheduler.js +12 -7
  67. package/dist/supervision/SafeRestartScheduler.js.map +1 -1
  68. package/dist/supervision/replacementSupervisor.js +45 -4
  69. package/dist/supervision/replacementSupervisor.js.map +1 -1
  70. package/dist/supervisor.js +30 -18
  71. package/dist/supervisor.js.map +1 -1
  72. package/docs/technical-reference.md +33 -10
  73. package/docs/technical-reference.zh.md +33 -10
  74. package/npm-shrinkwrap.json +2 -2
  75. package/package.json +2 -2
  76. package/skills/agent-bot/SKILL.md +107 -182
  77. package/src/cli/AutostartManager.ts +579 -0
  78. package/src/cli/FeishuAppConfiguration.ts +22 -7
  79. package/src/cli/Initializer.ts +57 -0
  80. package/src/cli/SelfUpdateRunner.ts +817 -0
  81. package/src/cli/SelfUpdater.ts +688 -0
  82. package/src/cli/autostartOutput.ts +75 -0
  83. package/src/cli/controlProtocol.ts +111 -1
  84. package/src/cli/help.ts +92 -18
  85. package/src/cli/taskGroupOptions.ts +27 -17
  86. package/src/cli/taskListOutput.ts +10 -0
  87. package/src/cli/taskTarget.ts +168 -0
  88. package/src/cli.ts +781 -65
  89. package/src/codex/CodexRuntime.ts +17 -5
  90. package/src/commands/CommandRouter.ts +19 -1
  91. package/src/commands/commandTypes.ts +3 -0
  92. package/src/config/loadConfig.ts +2 -0
  93. package/src/config/schema.ts +2 -0
  94. package/src/console/ConsoleTurnPresenter.ts +4 -1
  95. package/src/feishu/CardRenderer.ts +716 -16
  96. package/src/feishu/FeishuConnector.ts +44 -10
  97. package/src/feishu/FeishuMarkdown.ts +27 -1
  98. package/src/feishu/FeishuMessageClient.ts +58 -0
  99. package/src/feishu/FeishuTurnPresenter.ts +35 -2
  100. package/src/feishu/ownerAccess.ts +7 -0
  101. package/src/feishu/types.ts +7 -0
  102. package/src/index.ts +192 -22
  103. package/src/presentation/OutboundRouter.ts +28 -3
  104. package/src/proxy/ProxySessionController.ts +1707 -70
  105. package/src/runtime/types.ts +1 -0
  106. package/src/startup/StartupNotifier.ts +67 -17
  107. package/src/startup/startFeishu.ts +5 -3
  108. package/src/state/StateStore.ts +413 -65
  109. package/src/state/migrations.ts +26 -0
  110. package/src/supervision/SafeRestartNotifier.ts +17 -17
  111. package/src/supervision/SafeRestartScheduler.ts +13 -6
  112. package/src/supervision/replacementSupervisor.ts +50 -4
  113. package/src/supervisor.ts +35 -16
@@ -221,6 +221,7 @@ export interface AgentRuntime {
221
221
  steerTurn(sessionId: string, turnId: string, prompt: RuntimePrompt): Promise<void>;
222
222
  cancelTurn(sessionId: string, turnId: string): Promise<void>;
223
223
  interruptRemoteTurn?(remoteSessionId: string, turnId: string): Promise<void>;
224
+ archiveRemoteSession?(remoteSessionId: string): Promise<void>;
224
225
  closeSession(sessionId: string): Promise<void>;
225
226
  setTitle?(sessionId: string, title: string): Promise<void>;
226
227
  getGoal?(sessionId: string): Promise<RuntimeGoal | undefined>;
@@ -4,6 +4,7 @@ import { CardRenderer } from "../feishu/CardRenderer.js";
4
4
  import { baseChatContextKey, isThreadContextKey } from "../feishu/contextKey.js";
5
5
  import type { FeishuOutbound } from "../feishu/types.js";
6
6
  import type { SessionRecord, StateStore, UserContextRecord } from "../state/StateStore.js";
7
+ import type { RestartNotificationTarget } from "../supervision/SafeRestartScheduler.js";
7
8
 
8
9
  export interface StartupNotificationOptions {
9
10
  agentBotVersion: string;
@@ -20,6 +21,7 @@ export interface StartupTaskMetadataHydrator {
20
21
 
21
22
  interface StartupNotificationTarget {
22
23
  contextKey: string;
24
+ replyMessageId?: string;
23
25
  context?: UserContextRecord;
24
26
  }
25
27
 
@@ -36,7 +38,7 @@ export class StartupNotifier {
36
38
  async notify(
37
39
  startedAt: Date,
38
40
  restartReason: string,
39
- restartGroupContextKeys: string[] = [],
41
+ restartTargets: RestartNotificationTarget[] = [],
40
42
  ): Promise<void> {
41
43
  let targets: StartupNotificationTarget[];
42
44
  try {
@@ -46,21 +48,58 @@ export class StartupNotifier {
46
48
  .filter((chat) => !isThreadContextKey(chat.contextKey))
47
49
  .map((chat) => [chat.contextKey, chat]),
48
50
  );
49
- const targetGroups = new Map(
50
- this.store.listRecentlyActiveChatContexts(activeGroupSince)
51
- .filter((chat) => chat.chatType === "group" && !isThreadContextKey(chat.contextKey))
52
- .map((chat) => [chat.contextKey, chat]),
53
- );
54
- for (const contextKey of restartGroupContextKeys) {
55
- const baseContextKey = baseChatContextKey(contextKey.trim());
56
- const group = knownGroups.get(baseContextKey);
57
- if (group) targetGroups.set(baseContextKey, group);
51
+ const targetsByContext = new Map<string, StartupNotificationTarget>();
52
+ for (const chat of this.store.listChatContexts("p2p")) {
53
+ targetsByContext.set(chat.contextKey, {
54
+ contextKey: chat.contextKey,
55
+ context: this.store.getUserContext(chat.contextKey),
56
+ });
57
+ }
58
+ const recentGroups = this.store.listRecentlyActiveChatContexts(activeGroupSince)
59
+ .filter((chat) => chat.chatType === "group" && !isThreadContextKey(chat.contextKey));
60
+ for (const chat of recentGroups) {
61
+ targetsByContext.set(chat.contextKey, {
62
+ contextKey: chat.contextKey,
63
+ context: this.store.getUserContext(chat.contextKey),
64
+ });
58
65
  }
59
- const chats = [...this.store.listChatContexts("p2p"), ...targetGroups.values()];
60
- targets = chats.map((chat) => ({
61
- contextKey: chat.contextKey,
62
- context: this.store.getUserContext(chat.contextKey),
63
- }));
66
+ const explicitBaseContextKeys = new Set(restartTargets
67
+ .map((target) => target.contextKey.trim())
68
+ .filter((contextKey) => contextKey && !isThreadContextKey(contextKey)));
69
+ for (const target of restartTargets) {
70
+ const contextKey = target.contextKey.trim();
71
+ if (!contextKey) continue;
72
+ if (isThreadContextKey(contextKey)) {
73
+ const baseContextKey = baseChatContextKey(contextKey);
74
+ if (!knownGroups.has(baseContextKey)) continue;
75
+ const replyMessageId = target.replyMessageId?.trim();
76
+ if (replyMessageId) {
77
+ if (!explicitBaseContextKeys.has(baseContextKey)) {
78
+ targetsByContext.delete(baseContextKey);
79
+ }
80
+ targetsByContext.set(contextKey, {
81
+ contextKey,
82
+ replyMessageId,
83
+ context: this.store.getUserContext(contextKey),
84
+ });
85
+ } else {
86
+ const group = knownGroups.get(baseContextKey)!;
87
+ targetsByContext.set(baseContextKey, {
88
+ contextKey: baseContextKey,
89
+ context: this.store.getUserContext(baseContextKey),
90
+ });
91
+ }
92
+ continue;
93
+ }
94
+ const group = knownGroups.get(contextKey);
95
+ if (group) {
96
+ targetsByContext.set(contextKey, {
97
+ contextKey,
98
+ context: this.store.getUserContext(contextKey),
99
+ });
100
+ }
101
+ }
102
+ targets = [...targetsByContext.values()];
64
103
  } catch (error) {
65
104
  this.logger.warn({ error }, "Failed to load startup notification targets.");
66
105
  throw new Error("Failed to load startup notification targets.", { cause: error });
@@ -72,7 +111,7 @@ export class StartupNotifier {
72
111
  targets = [{ contextKey: `open_id:${defaultUserOpenId}` }];
73
112
  }
74
113
 
75
- const deliveries = await Promise.all(targets.map(async ({ contextKey, context }) => {
114
+ const deliveries = await Promise.all(targets.map(async ({ contextKey, replyMessageId, context }) => {
76
115
  let session = context?.currentSessionId ? this.store.getSession(context.currentSessionId) : undefined;
77
116
  if (session && this.metadataHydrator) {
78
117
  try {
@@ -111,7 +150,18 @@ export class StartupNotifier {
111
150
  : undefined,
112
151
  });
113
152
  try {
114
- await this.outbound.sendInteractiveCard(contextKey, card);
153
+ if (replyMessageId) {
154
+ if (!this.outbound.replyInteractiveCard) {
155
+ throw new Error("The outbound transport cannot preserve the safe-restart topic.");
156
+ }
157
+ await this.outbound.replyInteractiveCard(
158
+ contextKey,
159
+ { messageId: replyMessageId, replyInThread: true },
160
+ card,
161
+ );
162
+ } else {
163
+ await this.outbound.sendInteractiveCard(contextKey, card);
164
+ }
115
165
  return true;
116
166
  } catch (error) {
117
167
  this.logger.warn(
@@ -1,9 +1,11 @@
1
+ import type { RestartNotificationTarget } from "../supervision/SafeRestartScheduler.js";
2
+
1
3
  export interface StartableFeishuConnector {
2
4
  start(): Promise<void>;
3
5
  }
4
6
 
5
7
  export interface StartupNotificationSender {
6
- notify(startedAt: Date, restartReason: string, restartGroupContextKeys?: string[]): Promise<void>;
8
+ notify(startedAt: Date, restartReason: string, restartTargets?: RestartNotificationTarget[]): Promise<void>;
7
9
  }
8
10
 
9
11
  export async function startFeishu(
@@ -13,10 +15,10 @@ export async function startFeishu(
13
15
  restartReason: string,
14
16
  prepare?: () => Promise<void>,
15
17
  onConnected?: () => void,
16
- restartGroupContextKeys: string[] = [],
18
+ restartTargets: RestartNotificationTarget[] = [],
17
19
  ): Promise<void> {
18
20
  await prepare?.();
19
21
  await connector.start();
20
- await notifier.notify(startedAt, restartReason, restartGroupContextKeys);
22
+ await notifier.notify(startedAt, restartReason, restartTargets);
21
23
  onConnected?.();
22
24
  }