pi-harness-runtime 1.1.342 → 1.1.343

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 (123) hide show
  1. package/README.md +9 -0
  2. package/harness/notification-center.ts +363 -0
  3. package/index.ts +53 -15
  4. package/package.json +1 -1
  5. package/packages/a2a-adapter/package.json +1 -1
  6. package/packages/agent-policy/package.json +1 -1
  7. package/packages/architecture-generator/package.json +1 -1
  8. package/packages/auth/package.json +1 -1
  9. package/packages/autonomous-refactor/package.json +1 -1
  10. package/packages/autonomous-runtime/package.json +1 -1
  11. package/packages/cache-strategy/package.json +1 -1
  12. package/packages/capability-registry/package.json +1 -1
  13. package/packages/checkpoint/package.json +1 -1
  14. package/packages/cli-plugin-sdk/package.json +1 -1
  15. package/packages/clipboard/package.json +1 -1
  16. package/packages/clipboard-plugin/package.json +1 -1
  17. package/packages/code-generation/package.json +1 -1
  18. package/packages/code-review/package.json +1 -1
  19. package/packages/codex-adapter/package.json +1 -1
  20. package/packages/codex-watcher/package.json +1 -1
  21. package/packages/config-capture/package.json +1 -1
  22. package/packages/connection-runtime/package.json +1 -1
  23. package/packages/context-compiler/package.json +1 -1
  24. package/packages/context-discovery/package.json +1 -1
  25. package/packages/context-manager/package.json +1 -1
  26. package/packages/contracts/package.json +1 -1
  27. package/packages/cookie-sanitizer/package.json +1 -1
  28. package/packages/cost-optimizer/package.json +1 -1
  29. package/packages/dependency-analyzer/package.json +1 -1
  30. package/packages/django-plugin/package.json +1 -1
  31. package/packages/doc-generator/package.json +1 -1
  32. package/packages/durable-review/package.json +1 -1
  33. package/packages/e2e-tester/package.json +1 -1
  34. package/packages/evaluation-engine/package.json +1 -1
  35. package/packages/evaluation-runner/package.json +1 -1
  36. package/packages/event-bus/package.json +1 -1
  37. package/packages/event-sink/package.json +1 -1
  38. package/packages/event-store/package.json +1 -1
  39. package/packages/experience-replay/package.json +1 -1
  40. package/packages/feedback-collector/package.json +1 -1
  41. package/packages/file-copy-helper/package.json +1 -1
  42. package/packages/framework-detector/package.json +1 -1
  43. package/packages/framework-plugin-sdk/package.json +1 -1
  44. package/packages/frappe-plugin/package.json +1 -1
  45. package/packages/generic-web-plugin/package.json +1 -1
  46. package/packages/health-monitor/package.json +1 -1
  47. package/packages/intent-analyzer/package.json +1 -1
  48. package/packages/jev-judge/package.json +1 -1
  49. package/packages/knowledge-graph/package.json +1 -1
  50. package/packages/knowledge-retrieval/package.json +1 -1
  51. package/packages/laravel-plugin/package.json +1 -1
  52. package/packages/learning-engine/package.json +1 -1
  53. package/packages/mcp-adapter/package.json +1 -1
  54. package/packages/memory-engine/package.json +1 -1
  55. package/packages/milestone-manager/package.json +1 -1
  56. package/packages/model-registry/package.json +1 -1
  57. package/packages/nextjs-plugin/package.json +1 -1
  58. package/packages/notification/dist/notification-center.d.ts +13 -0
  59. package/packages/notification/dist/notification-center.d.ts.map +1 -1
  60. package/packages/notification/dist/notification-center.js +24 -0
  61. package/packages/notification/dist/notification-center.js.map +1 -1
  62. package/packages/notification/dist/telegram-webhook-handler.d.ts +4 -0
  63. package/packages/notification/dist/telegram-webhook-handler.d.ts.map +1 -1
  64. package/packages/notification/dist/telegram-webhook-handler.js +4 -0
  65. package/packages/notification/dist/telegram-webhook-handler.js.map +1 -1
  66. package/packages/notification/package.json +1 -1
  67. package/packages/notification/src/notification-center.ts +40 -13
  68. package/packages/notification/src/telegram-webhook-handler.ts +4 -0
  69. package/packages/observability/package.json +1 -1
  70. package/packages/okf-indexer/package.json +1 -1
  71. package/packages/paperclip-integration/package.json +1 -1
  72. package/packages/performance-optimizer/package.json +1 -1
  73. package/packages/permission-mode/package.json +1 -1
  74. package/packages/privilege-broker/package.json +1 -1
  75. package/packages/project-analyzer/package.json +1 -1
  76. package/packages/project-bootstrap/package.json +1 -1
  77. package/packages/projection-engine/package.json +1 -1
  78. package/packages/prompt-compiler/package.json +1 -1
  79. package/packages/prompt-versioning/package.json +1 -1
  80. package/packages/provider-adapter-sdk/package.json +1 -1
  81. package/packages/provider-router/package.json +1 -1
  82. package/packages/provider-selector/package.json +1 -1
  83. package/packages/providers/package.json +1 -1
  84. package/packages/qdrant-skills/package.json +1 -1
  85. package/packages/quota-manager/package.json +1 -1
  86. package/packages/rate-limiter/package.json +1 -1
  87. package/packages/react-vite-plugin/package.json +1 -1
  88. package/packages/relay/package.json +1 -1
  89. package/packages/release-manager/package.json +1 -1
  90. package/packages/requirement-compiler/package.json +1 -1
  91. package/packages/runtime/package.json +1 -1
  92. package/packages/scheduler/package.json +1 -1
  93. package/packages/scheduler-adapter/package.json +1 -1
  94. package/packages/session/package.json +1 -1
  95. package/packages/session-api/package.json +1 -1
  96. package/packages/session-export/package.json +1 -1
  97. package/packages/shared-context/package.json +1 -1
  98. package/packages/skill-mcp-client/package.json +1 -1
  99. package/packages/skill-registry/package.json +1 -1
  100. package/packages/skills/package.json +1 -1
  101. package/packages/sprint-planner/package.json +1 -1
  102. package/packages/subscription-engine/package.json +1 -1
  103. package/packages/task-compiler/package.json +1 -1
  104. package/packages/telegram/package.json +1 -1
  105. package/packages/tencentdb-memory/package.json +1 -1
  106. package/packages/tencentdb-sync/package.json +1 -1
  107. package/packages/test-data-generator/package.json +1 -1
  108. package/packages/test-generator/package.json +1 -1
  109. package/packages/todo-bd-sync/package.json +1 -1
  110. package/packages/token-estimation/package.json +1 -1
  111. package/packages/token-optimizer/package.json +1 -1
  112. package/packages/trajectory/package.json +1 -1
  113. package/packages/tui/package.json +1 -1
  114. package/packages/types/package.json +1 -1
  115. package/packages/voice-api/dist/telegram.js +8 -1
  116. package/packages/voice-api/package.json +1 -1
  117. package/packages/voice-api/src/telegram.ts +9 -1
  118. package/packages/webmcp-tester/package.json +1 -1
  119. package/packages/wiki/package.json +1 -1
  120. package/packages/workflow-events/package.json +1 -1
  121. package/packages/workspace-scanner/package.json +1 -1
  122. package/packages/worktree/package.json +1 -1
  123. package/packages/write-review/package.json +1 -1
package/README.md CHANGED
@@ -25,6 +25,15 @@ Give the runtime a requirement. It keeps working, survives interruption, and ret
25
25
  pi install npm:pi-harness-runtime
26
26
  ```
27
27
 
28
+ ### Recommended Extensions
29
+
30
+ This runtime works best with these extensions (auto-installed by pi-harness-runtime):
31
+
32
+ ```bash
33
+ pi install npm:pi-mcp-adapter # MCP protocol adapter for external tools
34
+ pi install npm:@juicesharp/rpiv-todo # Task tracking with bd sync
35
+ ```
36
+
28
37
  Requires Pi v0.37.3+.
29
38
 
30
39
  ### Headless Server Setup (herdr clipboard bridge)
@@ -0,0 +1,363 @@
1
+ /**
2
+ * Multi-Channel Notification Center
3
+ *
4
+ * Unified notification system supporting Telegram and LINE.
5
+ * Users can configure which channels to use and toggle them via inline buttons.
6
+ */
7
+
8
+ import * as https from "https";
9
+
10
+ export interface NotificationConfig {
11
+ telegram?: {
12
+ botToken: string;
13
+ chatId: string;
14
+ enabled: boolean;
15
+ };
16
+ line?: {
17
+ channelAccessToken: string;
18
+ userId: string;
19
+ enabled: boolean;
20
+ };
21
+ }
22
+
23
+ export interface NotificationEvent {
24
+ type: string;
25
+ emoji: string;
26
+ title: string;
27
+ message: string;
28
+ metadata?: Record<string, unknown>;
29
+ }
30
+
31
+ export interface NotificationButtons {
32
+ label: string;
33
+ action: string;
34
+ style?: "primary" | "secondary" | "danger";
35
+ }
36
+
37
+ const DEFAULT_CONFIG_FILE = `${process.env.HOME || "/home/frappe"}/.pi-harness-runtime/notification-config.json`;
38
+
39
+ /**
40
+ * Load notification configuration
41
+ */
42
+ function loadConfig(): NotificationConfig {
43
+ try {
44
+ const { existsSync, readFileSync } = require("fs");
45
+ if (existsSync(DEFAULT_CONFIG_FILE)) {
46
+ return JSON.parse(readFileSync(DEFAULT_CONFIG_FILE, "utf-8"));
47
+ }
48
+ } catch (e) {
49
+ console.error("Failed to save notification config:", e);
50
+ }
51
+ return {};
52
+ }
53
+
54
+ /**
55
+ * Save notification configuration
56
+ */
57
+ function saveConfig(config: NotificationConfig): void {
58
+ try {
59
+ const { writeFileSync, mkdirSync, existsSync } = require("fs");
60
+ const dir = DEFAULT_CONFIG_FILE.substring(0, DEFAULT_CONFIG_FILE.lastIndexOf("/"));
61
+ if (!existsSync(dir)) {
62
+ mkdirSync(dir, { recursive: true });
63
+ }
64
+ writeFileSync(DEFAULT_CONFIG_FILE, JSON.stringify(config, null, 2), "utf-8");
65
+ } catch (e) {
66
+ console.error("Failed to save notification config:", e);
67
+ }
68
+ }
69
+
70
+ /**
71
+ * Multi-Channel Notification Center
72
+ */
73
+ export class NotificationCenter {
74
+ private config: NotificationConfig;
75
+
76
+ constructor(config?: Partial<NotificationConfig>) {
77
+ this.config = loadConfig();
78
+ if (config?.telegram) {
79
+ this.config.telegram = { ...this.config.telegram, ...config.telegram };
80
+ }
81
+ if (config?.line) {
82
+ this.config.line = { ...this.config.line, ...config.line };
83
+ }
84
+ }
85
+
86
+ /**
87
+ * Update configuration
88
+ */
89
+ updateConfig(updates: Partial<NotificationConfig>): void {
90
+ this.config = { ...this.config, ...updates };
91
+ if (updates.telegram) {
92
+ this.config.telegram = { ...this.config.telegram!, ...updates.telegram };
93
+ }
94
+ if (updates.line) {
95
+ this.config.line = { ...this.config.line!, ...updates.line };
96
+ }
97
+ saveConfig(this.config);
98
+ }
99
+
100
+ /**
101
+ * Get current configuration
102
+ */
103
+ getConfig(): NotificationConfig {
104
+ return { ...this.config };
105
+ }
106
+
107
+ /**
108
+ * Send notification to all enabled channels
109
+ */
110
+ async notify(event: NotificationEvent): Promise<void> {
111
+ const { telegram, line } = this.config;
112
+ const promises: Promise<void>[] = [];
113
+
114
+ if (telegram?.enabled && telegram.botToken && telegram.chatId) {
115
+ promises.push(this.sendTelegram(event, telegram.botToken, telegram.chatId));
116
+ }
117
+
118
+ if (line?.enabled && line.channelAccessToken && line.userId) {
119
+ promises.push(this.sendLINE(event, line.channelAccessToken, line.userId));
120
+ }
121
+
122
+ await Promise.allSettled(promises);
123
+ }
124
+
125
+ /**
126
+ * Send notification with action buttons
127
+ */
128
+ async notifyWithButtons(
129
+ event: NotificationEvent,
130
+ buttons: NotificationButtons[]
131
+ ): Promise<void> {
132
+ const { telegram, line } = this.config;
133
+
134
+ if (telegram?.enabled && telegram.botToken && telegram.chatId) {
135
+ await this.sendTelegramWithButtons(event, buttons, telegram.botToken, telegram.chatId);
136
+ }
137
+
138
+ if (line?.enabled && line.channelAccessToken && line.userId) {
139
+ await this.sendLINEWithButtons(event, buttons, line.channelAccessToken, line.userId);
140
+ }
141
+ }
142
+
143
+ /**
144
+ * Send to Telegram
145
+ */
146
+ private async sendTelegram(
147
+ event: NotificationEvent,
148
+ botToken: string,
149
+ chatId: string
150
+ ): Promise<void> {
151
+ const text = `${event.emoji} ${event.title}\n\n${event.message}`;
152
+
153
+ await this.telegramRequest(botToken, "sendMessage", {
154
+ chat_id: chatId,
155
+ text,
156
+ parse_mode: "Markdown",
157
+ });
158
+ }
159
+
160
+ /**
161
+ * Send to Telegram with inline buttons
162
+ */
163
+ private async sendTelegramWithButtons(
164
+ event: NotificationEvent,
165
+ buttons: NotificationButtons[],
166
+ botToken: string,
167
+ chatId: string
168
+ ): Promise<void> {
169
+ const text = `${event.emoji} ${event.title}\n\n${event.message}`;
170
+ const inlineButtons = buttons.map((btn) => ({
171
+ text: btn.label,
172
+ callback_data: btn.action,
173
+ }));
174
+
175
+ await this.telegramRequest(botToken, "sendMessage", {
176
+ chat_id: chatId,
177
+ text,
178
+ parse_mode: "Markdown",
179
+ reply_markup: {
180
+ inline_keyboard: [inlineButtons],
181
+ },
182
+ });
183
+ }
184
+
185
+ /**
186
+ * Telegram API request
187
+ */
188
+ private telegramRequest(botToken: string, method: string, body: Record<string, unknown>): Promise<void> {
189
+ return new Promise((resolve, _reject) => {
190
+ const data = JSON.stringify(body);
191
+ const options = {
192
+ hostname: "api.telegram.org",
193
+ path: `/bot${botToken}/${method}`,
194
+ method: "POST",
195
+ headers: {
196
+ "Content-Type": "application/json",
197
+ "Content-Length": Buffer.byteLength(data),
198
+ },
199
+ };
200
+
201
+ const req = https.request(options, (res) => {
202
+ let response = "";
203
+ res.on("data", (chunk) => (response += chunk));
204
+ res.on("end", () => {
205
+ try {
206
+ const parsed = JSON.parse(response);
207
+ if (!parsed.ok) {
208
+ console.error(`Telegram API error: ${parsed.description}`);
209
+ }
210
+ } catch (e) {
211
+ console.error(`JSON parse error: ${e}`);
212
+ }
213
+ resolve();
214
+ });
215
+ });
216
+
217
+ req.on("error", (err: Error) => {
218
+ console.error(`Telegram API request error: ${err.message}`);
219
+ resolve();
220
+ });
221
+ req.write(data);
222
+ req.end();
223
+ });
224
+ }
225
+
226
+ /**
227
+ * Send to LINE
228
+ */
229
+ private async sendLINE(
230
+ event: NotificationEvent,
231
+ accessToken: string,
232
+ userId: string
233
+ ): Promise<void> {
234
+ const text = `${event.emoji} ${event.title}\n\n${event.message}`;
235
+
236
+ await this.lineRequest(accessToken, "push", {
237
+ to: userId,
238
+ messages: [{ type: "text", text }],
239
+ });
240
+ }
241
+
242
+ /**
243
+ * Send to LINE with quick reply buttons
244
+ */
245
+ private async sendLINEWithButtons(
246
+ event: NotificationEvent,
247
+ buttons: NotificationButtons[],
248
+ accessToken: string,
249
+ userId: string
250
+ ): Promise<void> {
251
+ const text = `${event.emoji} ${event.title}\n\n${event.message}`;
252
+
253
+ const actions = buttons.map((btn) => ({
254
+ type: "message" as const,
255
+ label: btn.label,
256
+ text: btn.action,
257
+ }));
258
+
259
+ await this.lineRequest(accessToken, "push", {
260
+ to: userId,
261
+ messages: [
262
+ { type: "text", text },
263
+ {
264
+ type: "text",
265
+ text: "Quick actions:",
266
+ quickReply: {
267
+ items: actions.map((action) => ({
268
+ type: "action",
269
+ action,
270
+ })),
271
+ },
272
+ },
273
+ ],
274
+ });
275
+ }
276
+
277
+ /**
278
+ * LINE API request
279
+ */
280
+ private lineRequest(accessToken: string, method: string, body: Record<string, unknown>): Promise<void> {
281
+ return new Promise((resolve, reject) => {
282
+ const data = JSON.stringify(body);
283
+ const options = {
284
+ hostname: "api.line.me",
285
+ path: `/v2/bot/message/${method}`,
286
+ method: "POST",
287
+ headers: {
288
+ "Content-Type": "application/json",
289
+ "Authorization": `Bearer ${accessToken}`,
290
+ "Content-Length": Buffer.byteLength(data),
291
+ },
292
+ };
293
+
294
+ const req = https.request(options, (res) => {
295
+ let response = "";
296
+ res.on("data", (chunk) => (response += chunk));
297
+ res.on("end", () => {
298
+ if (res.statusCode !== 200) {
299
+ console.error(`LINE API error: ${res.statusCode} ${response}`);
300
+ }
301
+ resolve();
302
+ });
303
+ });
304
+
305
+ req.on("error", reject);
306
+ req.write(data);
307
+ req.end();
308
+ });
309
+ }
310
+
311
+ /**
312
+ * Toggle Telegram notifications
313
+ */
314
+ toggleTelegram(enabled: boolean): void {
315
+ if (!this.config.telegram) {
316
+ this.config.telegram = { botToken: "", chatId: "", enabled };
317
+ } else {
318
+ this.config.telegram.enabled = enabled;
319
+ }
320
+ saveConfig(this.config);
321
+ }
322
+
323
+ /**
324
+ * Toggle LINE notifications
325
+ */
326
+ toggleLINE(enabled: boolean): void {
327
+ if (!this.config.line) {
328
+ this.config.line = { channelAccessToken: "", userId: "", enabled };
329
+ } else {
330
+ this.config.line.enabled = enabled;
331
+ }
332
+ saveConfig(this.config);
333
+ }
334
+
335
+ /**
336
+ * Check if Telegram is enabled
337
+ */
338
+ isTelegramEnabled(): boolean {
339
+ return this.config.telegram?.enabled ?? false;
340
+ }
341
+
342
+ /**
343
+ * Check if LINE is enabled
344
+ */
345
+ isLINEEnabled(): boolean {
346
+ return this.config.line?.enabled ?? false;
347
+ }
348
+ }
349
+
350
+ // Export singleton
351
+ let center: NotificationCenter | null = null;
352
+
353
+ export function getNotificationCenter(): NotificationCenter {
354
+ if (!center) {
355
+ center = new NotificationCenter();
356
+ }
357
+ return center;
358
+ }
359
+
360
+ export function initNotificationCenter(config?: Partial<NotificationConfig>): NotificationCenter {
361
+ center = new NotificationCenter(config);
362
+ return center;
363
+ }
package/index.ts CHANGED
@@ -1078,16 +1078,17 @@ async function advanceCodexTask(
1078
1078
  async function initTelegram(pi: ExtensionAPI): Promise<void> {
1079
1079
  addHarnessMessage("Telegram", "initializing", "wait");
1080
1080
  try {
1081
- const {
1082
- NotificationCenter,
1083
- createConversationBridge,
1084
- } = await import("./packages/notification/dist/index.js");
1081
+ const notifModule = await import("./packages/notification/dist/index.js");
1082
+ const NotificationCenter = notifModule.NotificationCenter;
1083
+ const createConversationBridge = notifModule.createConversationBridge;
1085
1084
  const { readFileSync, existsSync } = await import("node:fs");
1086
1085
  const home = process.env.HOME || process.env.USERPROFILE || "/home/frappe";
1087
1086
  const keysDir = `${home}/.pi-harness-runtime/keys`;
1088
1087
 
1089
1088
  const botTokenPath = `${keysDir}/telegram-bot-token.txt`;
1090
1089
  const chatIdPath = `${keysDir}/telegram-chat-id.txt`;
1090
+ const lineTokenPath = `${keysDir}/line-access-token.txt`;
1091
+ const lineUserIdPath = `${keysDir}/line-user-id.txt`;
1091
1092
 
1092
1093
  if (!existsSync(botTokenPath) || !existsSync(chatIdPath)) {
1093
1094
  logStartup("[pi-harness] Telegram (@PiHarnessRuntimeBot) not configured:");
@@ -1107,6 +1108,11 @@ async function initTelegram(pi: ExtensionAPI): Promise<void> {
1107
1108
  const botToken = readFileSync(botTokenPath, "utf8").trim();
1108
1109
  const chatId = readFileSync(chatIdPath, "utf8").trim();
1109
1110
 
1111
+ // Load LINE credentials
1112
+ const hasLineCredentials = existsSync(lineTokenPath) && existsSync(lineUserIdPath);
1113
+ const lineAccessToken = hasLineCredentials ? readFileSync(lineTokenPath, "utf8").trim() : null;
1114
+ const lineUserId = hasLineCredentials ? readFileSync(lineUserIdPath, "utf8").trim() : null;
1115
+
1110
1116
  if (!botToken || !chatId) {
1111
1117
  logStartup("[pi-harness] Telegram: bot token or chat ID is empty — skipping");
1112
1118
  addHarnessMessage("Telegram", "bot token or chat ID is empty; notifications unavailable", "warn", [
@@ -1115,16 +1121,35 @@ async function initTelegram(pi: ExtensionAPI): Promise<void> {
1115
1121
  return;
1116
1122
  }
1117
1123
 
1124
+ const channels: Array<{
1125
+ id: string;
1126
+ type: string;
1127
+ enabled: boolean;
1128
+ config: Record<string, unknown>;
1129
+ }> = [
1130
+ {
1131
+ id: "telegram",
1132
+ type: "telegram",
1133
+ enabled: true,
1134
+ config: { botToken, chatId },
1135
+ },
1136
+ ];
1137
+
1138
+ // Add LINE channel if credentials exist
1139
+ if (hasLineCredentials && lineAccessToken && lineUserId) {
1140
+ channels.push({
1141
+ id: "line",
1142
+ type: "line" as const,
1143
+ enabled: true,
1144
+ config: { channelAccessToken: lineAccessToken, userId: lineUserId },
1145
+ });
1146
+ addHarnessMessage("LINE", "configured and enabled", "ok");
1147
+ }
1148
+
1149
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
1118
1150
  const center = new NotificationCenter({
1119
1151
  enabled: true,
1120
- channels: [
1121
- {
1122
- id: "telegram",
1123
- type: "telegram",
1124
- enabled: true,
1125
- config: { botToken, chatId },
1126
- },
1127
- ],
1152
+ channels: channels as any,
1128
1153
  });
1129
1154
 
1130
1155
  await center.initialize();
@@ -1187,9 +1212,22 @@ async function initTelegram(pi: ExtensionAPI): Promise<void> {
1187
1212
  (sharedState.todoContinuationController as any)?.explicitPause?.();
1188
1213
  break;
1189
1214
  default:
1190
- logToFile("[TelegramCallback]", `Unknown action: ${parsed.action}`);
1191
- }
1192
- });
1215
+ // Check for channel toggle actions
1216
+ if (parsed.action === "toggle_telegram") {
1217
+ const telegramEnabled = (center as any).isChannelEnabled?.("telegram") ?? true;
1218
+ (center as any).setChannelEnabled?.("telegram", !telegramEnabled);
1219
+ logToFile("[TelegramCallback]", `Telegram ${!telegramEnabled ? "enabled" : "disabled"}`);
1220
+ await acknowledge(`Telegram notifications ${!telegramEnabled ? "enabled" : "disabled"}`);
1221
+ } else if (parsed.action === "toggle_line") {
1222
+ const lineEnabled = (center as any).isChannelEnabled?.("line") ?? true;
1223
+ (center as any).setChannelEnabled?.("line", !lineEnabled);
1224
+ logToFile("[TelegramCallback]", `LINE ${!lineEnabled ? "enabled" : "disabled"}`);
1225
+ await acknowledge(`LINE notifications ${!lineEnabled ? "enabled" : "disabled"}`);
1226
+ } else {
1227
+ logToFile("[TelegramCallback]", `Unknown action: ${parsed.action}`);
1228
+ }
1229
+ }
1230
+ });
1193
1231
 
1194
1232
  // Register message handler to forward Telegram messages to Pi
1195
1233
  center.setMessageHandler(async (text: string, _chatId: string) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "pi-harness-runtime",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "[BETA] Codex-style /usage status + autonomous coding harness for pi. Not production ready — expect breaking changes.",
5
5
  "type": "module",
6
6
  "scripts": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/a2a-adapter",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "Google Agent-to-Agent (A2A) protocol adapter for pi-harness",
6
6
  "main": "dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/agent-policy",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Agent policy runtime for pi-harness - enforces mandatory rule delivery and mutation gating",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi-harness/architecture-generator",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Generate ADR and Mermaid diagrams from project analysis",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi-harness/auth",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "pi-harness-runtime — auth",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/autonomous-refactor",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "Autonomous refactoring engine",
6
6
  "main": "dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/autonomous-runtime",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Autonomous Operations Runtime — task inbox, lease management, and worker lifecycle (RFC-0101)",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/cache-strategy",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "Smart caching with TTL and invalidation strategies (RFC-0022)",
6
6
  "main": "dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi-harness/capability-registry",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Capability Registry for pi-harness-runtime — tracks model capabilities and enables capability-based routing",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/checkpoint",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Enhanced checkpoint system with incremental snapshots, diff-based storage, and recovery strategies",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/cli-plugin-sdk",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "CLI Plugin SDK for pi-harness — install, list, remove, update, invoke plugins",
6
6
  "main": "dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/clipboard",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "main": "src/index.ts",
6
6
  "exports": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/clipboard-plugin",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "main": "src/index.ts",
6
6
  "exports": {
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/code-generation",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Code generation pipeline for pi-harness-runtime",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/code-review",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Automated code review engine for pi-harness-runtime",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/codex-adapter",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "OpenAI Codex provider adapter for pi-harness",
6
6
  "main": "dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi-harness/codex-watcher",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Watches Codex CLI sessions and emits visible messages for PING-PONG monitoring",
5
5
  "type": "module",
6
6
  "main": "./dist/src/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@moocoding/config-capture",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Auto-capture API-fetched configuration values to AGENTS.md",
5
5
  "type": "module",
6
6
  "main": "src/index.ts",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi-harness/connection-runtime",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "description": "Connection management with jittered exponential backoff for pi-harness",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/context-compiler",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "description": "Bounded context selection engine for pi-harness-runtime",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@pi/context-discovery",
3
- "version": "1.1.342",
3
+ "version": "1.1.343",
4
4
  "type": "module",
5
5
  "main": "src/index.ts",
6
6
  "exports": {