@pixelbyte-software/pixcode 1.36.2 → 1.36.4

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 (41) hide show
  1. package/dist/assets/index-CgF0-_6Z.css +32 -0
  2. package/dist/assets/{index-B1PlYTuj.js → index-D-YjltED.js} +182 -182
  3. package/dist/index.html +2 -2
  4. package/dist-server/server/daemon-manager.js +18 -12
  5. package/dist-server/server/daemon-manager.js.map +1 -1
  6. package/dist-server/server/database/db.js +49 -0
  7. package/dist-server/server/database/db.js.map +1 -1
  8. package/dist-server/server/index.js +8 -4
  9. package/dist-server/server/index.js.map +1 -1
  10. package/dist-server/server/modules/orchestration/workflows/workflow-runner.js +17 -3
  11. package/dist-server/server/modules/orchestration/workflows/workflow-runner.js.map +1 -1
  12. package/dist-server/server/routes/telegram.js +16 -2
  13. package/dist-server/server/routes/telegram.js.map +1 -1
  14. package/dist-server/server/services/telegram/bot.js +48 -6
  15. package/dist-server/server/services/telegram/bot.js.map +1 -1
  16. package/dist-server/server/services/telegram/control-center.js +761 -0
  17. package/dist-server/server/services/telegram/control-center.js.map +1 -0
  18. package/dist-server/server/services/telegram/telegram-http-client.js +26 -4
  19. package/dist-server/server/services/telegram/telegram-http-client.js.map +1 -1
  20. package/dist-server/server/services/telegram/translations.js +138 -2
  21. package/dist-server/server/services/telegram/translations.js.map +1 -1
  22. package/package.json +5 -1
  23. package/scripts/smoke/chat-session-state.mjs +19 -0
  24. package/scripts/smoke/daemon-entrypoint.mjs +20 -0
  25. package/scripts/smoke/orchestration-user-facing-output.mjs +25 -0
  26. package/scripts/smoke/shell-manual-disconnect.mjs +30 -0
  27. package/scripts/smoke/side-panel-editor-layout.mjs +34 -0
  28. package/scripts/smoke/static-root-routing.mjs +21 -0
  29. package/scripts/smoke/telegram-control.mjs +242 -0
  30. package/scripts/smoke/update-ux.mjs +55 -0
  31. package/scripts/smoke/version-modal-autoshow.mjs +29 -0
  32. package/server/daemon-manager.js +17 -12
  33. package/server/database/db.js +52 -0
  34. package/server/index.js +9 -5
  35. package/server/modules/orchestration/workflows/workflow-runner.ts +18 -3
  36. package/server/routes/telegram.js +17 -2
  37. package/server/services/telegram/bot.js +58 -6
  38. package/server/services/telegram/control-center.js +814 -0
  39. package/server/services/telegram/telegram-http-client.js +25 -4
  40. package/server/services/telegram/translations.js +138 -2
  41. package/dist/assets/index-Dx7QyTSN.css +0 -32
@@ -2,6 +2,13 @@ import { EventEmitter } from 'node:events';
2
2
 
3
3
  import { telegramConfigDb, telegramLinksDb } from '../../database/db.js';
4
4
 
5
+ import {
6
+ getTelegramControlCommand,
7
+ handleTelegramControlCallback,
8
+ handleTelegramControlMessage,
9
+ isTelegramControlCommand,
10
+ showMainMenu,
11
+ } from './control-center.js';
5
12
  import { t } from './translations.js';
6
13
  // Swapped in v1.32: previously `node-telegram-bot-api` which carried the
7
14
  // deprecated `request`/`har-validator`/`uuid@3` chain. TelegramHttpBot is
@@ -21,6 +28,10 @@ let bot = null;
21
28
  let botInfo = null; // { id, username, first_name }
22
29
  let lastError = null;
23
30
 
31
+ export const setTelegramBotForTesting = (nextBot) => {
32
+ bot = nextBot;
33
+ };
34
+
24
35
  // Subscribers (notification-orchestrator, future session bridge) use this to
25
36
  // react to events without importing the bot module directly.
26
37
  export const telegramEvents = new EventEmitter();
@@ -64,14 +75,14 @@ const parseMaybeCode = (text) => {
64
75
  return /^\d{6}$/.test(trimmed) ? trimmed : null;
65
76
  };
66
77
 
67
- const safeSend = async (chatId, text) => {
78
+ const safeSend = async (chatId, text, extra = {}) => {
68
79
  if (!bot) return;
69
80
  try {
70
- await bot.sendMessage(chatId, text, { parse_mode: 'Markdown' });
81
+ await bot.sendMessage(chatId, text, { parse_mode: 'Markdown', ...extra });
71
82
  } catch (err) {
72
83
  // Markdown parse errors from user input are common; retry plaintext.
73
84
  try {
74
- await bot.sendMessage(chatId, text);
85
+ await bot.sendMessage(chatId, text, extra);
75
86
  } catch (fallbackErr) {
76
87
  console.warn('[telegram] sendMessage failed:', fallbackErr?.message || fallbackErr);
77
88
  }
@@ -98,19 +109,21 @@ const handlePairing = async (msg, code) => {
98
109
  telegramEvents.emit('paired', { userId: link.user_id, chatId: String(msg.chat.id), username: telegramUsername });
99
110
 
100
111
  await safeSend(msg.chat.id, t(language, 'pairing.success'));
112
+ await safeSend(msg.chat.id, t(language, 'control.onboarding'));
113
+ await showMainMenu({ bot, chatId: msg.chat.id, link: telegramLinksDb.getByUserId(link.user_id) });
101
114
  };
102
115
 
103
116
  const handleBridgeMessage = async (msg, existing) => {
104
117
  const language = existing.language || 'en';
105
118
 
119
+ const handled = await handleTelegramControlMessage({ bot, msg, link: existing, safeSend });
120
+ if (handled) return;
121
+
106
122
  if (!existing.bridge_enabled) {
107
123
  await safeSend(msg.chat.id, t(language, 'bridge.disabled'));
108
124
  return;
109
125
  }
110
126
 
111
- // Fan out to subscribers (future: session-prompt bridge). We don't do the
112
- // actual agent dispatch here to keep the bot service narrowly focused on
113
- // Telegram I/O and let the rest of the server opt in.
114
127
  telegramEvents.emit('prompt', {
115
128
  userId: existing.user_id,
116
129
  chatId: String(msg.chat.id),
@@ -122,11 +135,43 @@ const handleBridgeMessage = async (msg, existing) => {
122
135
  await safeSend(msg.chat.id, t(language, 'bridge.queued'));
123
136
  };
124
137
 
138
+ const handleCallbackQuery = async (query) => {
139
+ const chatId = query?.message?.chat?.id;
140
+ if (!chatId) return;
141
+ const existing = telegramLinksDb.getByChatId(String(chatId));
142
+ if (!existing) {
143
+ await bot?.answerCallbackQuery(query.id, { text: 'Pair Pixcode first.' }).catch(() => {});
144
+ return;
145
+ }
146
+ await handleTelegramControlCallback({ bot, query, link: existing, safeSend });
147
+ };
148
+
125
149
  const handleMessage = async (msg) => {
126
150
  if (!msg?.chat?.id || !msg?.text) return;
127
151
 
128
152
  const existing = telegramLinksDb.getByChatId(String(msg.chat.id));
129
153
  if (existing) {
154
+ const language = existing.language || 'en';
155
+ const command = getTelegramControlCommand(msg.text);
156
+ if (command === '/start') {
157
+ await safeSend(msg.chat.id, t(language, 'control.onboarding'));
158
+ await showMainMenu({ bot, chatId: msg.chat.id, link: existing });
159
+ return;
160
+ }
161
+ if (command === '/help') {
162
+ await safeSend(msg.chat.id, t(language, 'control.help'));
163
+ return;
164
+ }
165
+ if (command === '/menu' || command === 'menu') {
166
+ await showMainMenu({ bot, chatId: msg.chat.id, link: existing });
167
+ return;
168
+ }
169
+
170
+ if (isTelegramControlCommand(msg.text)) {
171
+ await handleTelegramControlMessage({ bot, msg, link: existing });
172
+ return;
173
+ }
174
+
130
175
  // Paired user path: a 6-digit-only message is treated as noise (we keep
131
176
  // the already-paired binding); anything else is bridge traffic.
132
177
  const maybeCode = parseMaybeCode(msg.text);
@@ -157,6 +202,8 @@ const handleMessage = async (msg) => {
157
202
  await safeSend(msg.chat.id, t('en', 'pairing.stillNeeded'));
158
203
  };
159
204
 
205
+ export const handleIncomingTelegramMessage = handleMessage;
206
+
160
207
  const wirePollingErrors = () => {
161
208
  if (!bot) return;
162
209
  bot.on('polling_error', (err) => {
@@ -213,6 +260,11 @@ export const startBot = async ({ token, persist = true } = {}) => {
213
260
  console.error('[telegram] handleMessage crashed:', err);
214
261
  });
215
262
  });
263
+ bot.on('callback_query', (query) => {
264
+ handleCallbackQuery(query).catch((err) => {
265
+ console.error('[telegram] handleCallbackQuery crashed:', err);
266
+ });
267
+ });
216
268
  wirePollingErrors();
217
269
 
218
270
  console.log(`[telegram] bot started as @${me.username}`);