@ebowwa/glm-daemon 0.4.6 → 0.4.7

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.
@@ -92156,7 +92156,86 @@ var require_src2 = __commonJS((exports) => {
92156
92156
  __exportStar(require_dist3(), exports);
92157
92157
  __exportStar(require_dist11(), exports);
92158
92158
  });
92159
-
92159
+ // ../channel-types/dist/plugins/registry.js
92160
+ class PluginRegistryImpl {
92161
+ channels = new Map;
92162
+ channelOrder = [];
92163
+ registerChannel(registration) {
92164
+ const id = registration.plugin.id;
92165
+ if (typeof id !== "string") {
92166
+ throw new Error("Channel plugin id must be a string");
92167
+ }
92168
+ const normalizedId = id.trim().toLowerCase();
92169
+ if (this.channels.has(normalizedId)) {
92170
+ console.warn(`[PluginRegistry] Channel "${normalizedId}" already registered, replacing`);
92171
+ }
92172
+ this.channels.set(normalizedId, registration);
92173
+ if (!this.channelOrder.includes(normalizedId)) {
92174
+ this.channelOrder.push(normalizedId);
92175
+ }
92176
+ console.log(`[PluginRegistry] Registered channel: ${normalizedId} (source: ${registration.source})`);
92177
+ }
92178
+ unregisterChannel(channelId) {
92179
+ const normalizedId = channelId.trim().toLowerCase();
92180
+ const existed = this.channels.delete(normalizedId);
92181
+ if (existed) {
92182
+ this.channelOrder = this.channelOrder.filter((id) => id !== normalizedId);
92183
+ }
92184
+ return existed;
92185
+ }
92186
+ getChannel(channelId) {
92187
+ const normalizedId = this.normalizeChannelId(channelId);
92188
+ const registration = this.channels.get(normalizedId);
92189
+ return registration?.plugin;
92190
+ }
92191
+ getChannelRegistration(channelId) {
92192
+ const normalizedId = this.normalizeChannelId(channelId);
92193
+ return this.channels.get(normalizedId);
92194
+ }
92195
+ getChannels() {
92196
+ return this.channelOrder.map((id) => this.channels.get(id)?.plugin).filter((p) => p !== undefined);
92197
+ }
92198
+ getChannelRegistrations() {
92199
+ return this.channelOrder.map((id) => this.channels.get(id)).filter((r) => r !== undefined);
92200
+ }
92201
+ getChannelOrder() {
92202
+ return [...this.channelOrder];
92203
+ }
92204
+ setChannelOrder(order) {
92205
+ this.channelOrder = order.map((id) => id.toLowerCase().trim());
92206
+ }
92207
+ getChannelsByCapability(capability) {
92208
+ return this.getChannels().filter((plugin) => plugin.capabilities.supports[capability] === true);
92209
+ }
92210
+ getChannelsByChatType(chatType) {
92211
+ return this.getChannels().filter((plugin) => plugin.capabilities.chatTypes?.includes(chatType));
92212
+ }
92213
+ hasChannel(channelId) {
92214
+ return this.channels.has(this.normalizeChannelId(channelId));
92215
+ }
92216
+ normalizeChannelId(channelId) {
92217
+ const id = channelId.trim().toLowerCase();
92218
+ const aliases = {
92219
+ tg: "telegram",
92220
+ imsg: "imessage",
92221
+ wa: "whatsapp",
92222
+ dc: "discord",
92223
+ sl: "slack"
92224
+ };
92225
+ return aliases[id] || id;
92226
+ }
92227
+ clear() {
92228
+ this.channels.clear();
92229
+ this.channelOrder = [];
92230
+ }
92231
+ getStats() {
92232
+ return {
92233
+ channelCount: this.channels.size,
92234
+ channels: this.getChannelOrder()
92235
+ };
92236
+ }
92237
+ }
92238
+ var pluginRegistry = new PluginRegistryImpl;
92160
92239
  // ../channel-types/dist/index.js
92161
92240
  function createChannelId(platform, accountId, instanceId) {
92162
92241
  return { platform, accountId, instanceId };
@@ -98838,6 +98917,222 @@ function registerAllCommands(bot, memory, tools) {
98838
98917
  registerInnerthoughtsCommand(bot, memory, tools);
98839
98918
  register(bot, tools);
98840
98919
  }
98920
+
98921
+ // ../channel-telegram/dist/plugin.js
98922
+ var telegramMeta = {
98923
+ label: "Telegram",
98924
+ blurb: "Telegram Bot API for direct and group chats",
98925
+ icon: "\uD83D\uDCF1",
98926
+ docsPath: "/docs/channels/telegram",
98927
+ quickstartAllowFrom: true
98928
+ };
98929
+ var telegramConfigAdapter = {
98930
+ listAccountIds: async (config) => {
98931
+ const botToken = config.botToken;
98932
+ if (!botToken)
98933
+ return [];
98934
+ return ["default"];
98935
+ },
98936
+ resolveAccount: async (config, accountId) => {
98937
+ return {
98938
+ botToken: config.botToken,
98939
+ allowedUsers: config.allowedUsers,
98940
+ allowedChats: config.allowedChats,
98941
+ pollingInterval: config.pollingInterval || 1000
98942
+ };
98943
+ },
98944
+ validateAccount: async (account) => {
98945
+ if (!account.botToken)
98946
+ return false;
98947
+ return true;
98948
+ }
98949
+ };
98950
+ var createOutboundAdapter = (getBot) => ({
98951
+ deliveryMode: "direct",
98952
+ textChunkLimit: 4096,
98953
+ chunker: (text, limit) => {
98954
+ const chunks = [];
98955
+ for (let i = 0;i < text.length; i += limit) {
98956
+ chunks.push(text.slice(i, i + limit));
98957
+ }
98958
+ return { chunks, totalChunks: chunks.length };
98959
+ },
98960
+ sendText: async ({ to, text, accountId, account, replyToId, threadId }) => {
98961
+ const bot = getBot();
98962
+ if (!bot) {
98963
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
98964
+ }
98965
+ try {
98966
+ const chatId = parseInt(to, 10);
98967
+ const options = {
98968
+ parse_mode: "Markdown"
98969
+ };
98970
+ if (replyToId) {
98971
+ options.reply_to_message_id = parseInt(replyToId, 10);
98972
+ }
98973
+ if (threadId) {
98974
+ options.message_thread_id = parseInt(threadId, 10);
98975
+ }
98976
+ const result = await bot.sendMessage(chatId, text, options);
98977
+ return {
98978
+ success: true,
98979
+ messageId: result.message_id.toString(),
98980
+ timestamp: new Date
98981
+ };
98982
+ } catch (error) {
98983
+ return {
98984
+ success: false,
98985
+ error: error.message,
98986
+ timestamp: new Date
98987
+ };
98988
+ }
98989
+ },
98990
+ sendMedia: async ({ to, text, mediaUrl, mediaType, accountId, account }) => {
98991
+ const bot = getBot();
98992
+ if (!bot) {
98993
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
98994
+ }
98995
+ try {
98996
+ const chatId = parseInt(to, 10);
98997
+ let result;
98998
+ if (mediaType === "image") {
98999
+ result = await bot.sendPhoto(chatId, mediaUrl, { caption: text });
99000
+ } else if (mediaType === "video") {
99001
+ result = await bot.sendVideo(chatId, mediaUrl, { caption: text });
99002
+ } else if (mediaType === "audio") {
99003
+ result = await bot.sendAudio(chatId, mediaUrl, { caption: text });
99004
+ } else {
99005
+ result = await bot.sendDocument(chatId, mediaUrl, { caption: text });
99006
+ }
99007
+ return {
99008
+ success: true,
99009
+ messageId: result.message_id.toString(),
99010
+ timestamp: new Date
99011
+ };
99012
+ } catch (error) {
99013
+ return {
99014
+ success: false,
99015
+ error: error.message,
99016
+ timestamp: new Date
99017
+ };
99018
+ }
99019
+ }
99020
+ });
99021
+ var telegramThreadingAdapter = {
99022
+ replyModes: ["quote", "thread"],
99023
+ defaultReplyMode: "quote"
99024
+ };
99025
+ var createGatewayAdapter = (createBot) => {
99026
+ const activeBots = new Map;
99027
+ const messageHandlers = new Map;
99028
+ return {
99029
+ startAccount: async ({ accountId, account, onMessage }) => {
99030
+ const bot = createBot(account.botToken);
99031
+ const handler = (msg) => {
99032
+ if (account.allowedUsers?.length && !account.allowedUsers.includes(msg.from?.id || 0)) {
99033
+ return;
99034
+ }
99035
+ if (account.allowedChats?.length && !account.allowedChats.includes(msg.chat.id)) {
99036
+ return;
99037
+ }
99038
+ const channelId = {
99039
+ platform: "telegram",
99040
+ accountId: msg.chat.id.toString()
99041
+ };
99042
+ const channelMessage = {
99043
+ messageId: msg.message_id.toString(),
99044
+ channelId,
99045
+ timestamp: new Date(msg.date * 1000),
99046
+ sender: {
99047
+ id: msg.from?.id.toString() || "unknown",
99048
+ username: msg.from?.username,
99049
+ displayName: msg.from?.first_name,
99050
+ isBot: msg.from?.is_bot || false
99051
+ },
99052
+ text: msg.text || "",
99053
+ context: {
99054
+ isDM: msg.chat.type === "private",
99055
+ groupName: msg.chat.title,
99056
+ threadId: msg.message_thread_id?.toString()
99057
+ },
99058
+ replyTo: msg.reply_to_message ? {
99059
+ messageId: msg.reply_to_message.message_id.toString(),
99060
+ channelId
99061
+ } : undefined
99062
+ };
99063
+ onMessage(channelMessage);
99064
+ };
99065
+ bot.on("message", handler);
99066
+ activeBots.set(accountId, bot);
99067
+ messageHandlers.set(accountId, handler);
99068
+ },
99069
+ stopAccount: async ({ accountId, account }) => {
99070
+ const bot = activeBots.get(accountId);
99071
+ const handler = messageHandlers.get(accountId);
99072
+ if (bot && handler) {
99073
+ bot.off("message", handler);
99074
+ if (bot.isPolling()) {
99075
+ await bot.stopPolling();
99076
+ }
99077
+ activeBots.delete(accountId);
99078
+ messageHandlers.delete(accountId);
99079
+ }
99080
+ },
99081
+ isAccountActive: (accountId) => {
99082
+ return activeBots.has(accountId);
99083
+ }
99084
+ };
99085
+ };
99086
+ function createTelegramPlugin(config = {}, TelegramBotClass) {
99087
+ let bot = null;
99088
+ const createBot = (token) => {
99089
+ if (!TelegramBotClass) {
99090
+ throw new Error("TelegramBot class not provided");
99091
+ }
99092
+ return new TelegramBotClass(token, { polling: true });
99093
+ };
99094
+ return {
99095
+ id: "telegram",
99096
+ meta: telegramMeta,
99097
+ capabilities: {
99098
+ chatTypes: ["direct", "group", "channel", "thread"],
99099
+ supports: {
99100
+ text: true,
99101
+ media: true,
99102
+ replies: true,
99103
+ threads: true,
99104
+ reactions: true,
99105
+ editing: true,
99106
+ streaming: false,
99107
+ buttons: true
99108
+ },
99109
+ nativeCommands: true,
99110
+ rateLimits: {
99111
+ messagesPerMinute: 30,
99112
+ charactersPerMessage: 4096
99113
+ },
99114
+ media: {
99115
+ maxFileSize: 50 * 1024 * 1024,
99116
+ supportedMimeTypes: ["image/*", "video/*", "audio/*", "application/pdf"]
99117
+ }
99118
+ },
99119
+ config: telegramConfigAdapter,
99120
+ outbound: createOutboundAdapter(() => bot),
99121
+ gateway: createGatewayAdapter((token) => {
99122
+ bot = createBot(token);
99123
+ return bot;
99124
+ }),
99125
+ threading: telegramThreadingAdapter
99126
+ };
99127
+ }
99128
+ var telegramPlugin = createTelegramPlugin();
99129
+ if (process.env.TELEGRAM_BOT_TOKEN) {
99130
+ pluginRegistry.registerChannel({
99131
+ pluginId: "telegram",
99132
+ plugin: telegramPlugin,
99133
+ source: "core"
99134
+ });
99135
+ }
98841
99136
  // ../channel-telegram/dist/utils/normalize.js
98842
99137
  function normalizeTelegramMessagingTarget(raw) {
98843
99138
  const trimmed = raw.trim();
@@ -92156,7 +92156,86 @@ var require_src2 = __commonJS((exports) => {
92156
92156
  __exportStar(require_dist3(), exports);
92157
92157
  __exportStar(require_dist11(), exports);
92158
92158
  });
92159
-
92159
+ // ../channel-types/dist/plugins/registry.js
92160
+ class PluginRegistryImpl {
92161
+ channels = new Map;
92162
+ channelOrder = [];
92163
+ registerChannel(registration) {
92164
+ const id = registration.plugin.id;
92165
+ if (typeof id !== "string") {
92166
+ throw new Error("Channel plugin id must be a string");
92167
+ }
92168
+ const normalizedId = id.trim().toLowerCase();
92169
+ if (this.channels.has(normalizedId)) {
92170
+ console.warn(`[PluginRegistry] Channel "${normalizedId}" already registered, replacing`);
92171
+ }
92172
+ this.channels.set(normalizedId, registration);
92173
+ if (!this.channelOrder.includes(normalizedId)) {
92174
+ this.channelOrder.push(normalizedId);
92175
+ }
92176
+ console.log(`[PluginRegistry] Registered channel: ${normalizedId} (source: ${registration.source})`);
92177
+ }
92178
+ unregisterChannel(channelId) {
92179
+ const normalizedId = channelId.trim().toLowerCase();
92180
+ const existed = this.channels.delete(normalizedId);
92181
+ if (existed) {
92182
+ this.channelOrder = this.channelOrder.filter((id) => id !== normalizedId);
92183
+ }
92184
+ return existed;
92185
+ }
92186
+ getChannel(channelId) {
92187
+ const normalizedId = this.normalizeChannelId(channelId);
92188
+ const registration = this.channels.get(normalizedId);
92189
+ return registration?.plugin;
92190
+ }
92191
+ getChannelRegistration(channelId) {
92192
+ const normalizedId = this.normalizeChannelId(channelId);
92193
+ return this.channels.get(normalizedId);
92194
+ }
92195
+ getChannels() {
92196
+ return this.channelOrder.map((id) => this.channels.get(id)?.plugin).filter((p) => p !== undefined);
92197
+ }
92198
+ getChannelRegistrations() {
92199
+ return this.channelOrder.map((id) => this.channels.get(id)).filter((r) => r !== undefined);
92200
+ }
92201
+ getChannelOrder() {
92202
+ return [...this.channelOrder];
92203
+ }
92204
+ setChannelOrder(order) {
92205
+ this.channelOrder = order.map((id) => id.toLowerCase().trim());
92206
+ }
92207
+ getChannelsByCapability(capability) {
92208
+ return this.getChannels().filter((plugin) => plugin.capabilities.supports[capability] === true);
92209
+ }
92210
+ getChannelsByChatType(chatType) {
92211
+ return this.getChannels().filter((plugin) => plugin.capabilities.chatTypes?.includes(chatType));
92212
+ }
92213
+ hasChannel(channelId) {
92214
+ return this.channels.has(this.normalizeChannelId(channelId));
92215
+ }
92216
+ normalizeChannelId(channelId) {
92217
+ const id = channelId.trim().toLowerCase();
92218
+ const aliases = {
92219
+ tg: "telegram",
92220
+ imsg: "imessage",
92221
+ wa: "whatsapp",
92222
+ dc: "discord",
92223
+ sl: "slack"
92224
+ };
92225
+ return aliases[id] || id;
92226
+ }
92227
+ clear() {
92228
+ this.channels.clear();
92229
+ this.channelOrder = [];
92230
+ }
92231
+ getStats() {
92232
+ return {
92233
+ channelCount: this.channels.size,
92234
+ channels: this.getChannelOrder()
92235
+ };
92236
+ }
92237
+ }
92238
+ var pluginRegistry = new PluginRegistryImpl;
92160
92239
  // ../channel-types/dist/index.js
92161
92240
  function createChannelId(platform, accountId, instanceId) {
92162
92241
  return { platform, accountId, instanceId };
@@ -98838,6 +98917,222 @@ function registerAllCommands(bot, memory, tools) {
98838
98917
  registerInnerthoughtsCommand(bot, memory, tools);
98839
98918
  register(bot, tools);
98840
98919
  }
98920
+
98921
+ // ../channel-telegram/dist/plugin.js
98922
+ var telegramMeta = {
98923
+ label: "Telegram",
98924
+ blurb: "Telegram Bot API for direct and group chats",
98925
+ icon: "\uD83D\uDCF1",
98926
+ docsPath: "/docs/channels/telegram",
98927
+ quickstartAllowFrom: true
98928
+ };
98929
+ var telegramConfigAdapter = {
98930
+ listAccountIds: async (config) => {
98931
+ const botToken = config.botToken;
98932
+ if (!botToken)
98933
+ return [];
98934
+ return ["default"];
98935
+ },
98936
+ resolveAccount: async (config, accountId) => {
98937
+ return {
98938
+ botToken: config.botToken,
98939
+ allowedUsers: config.allowedUsers,
98940
+ allowedChats: config.allowedChats,
98941
+ pollingInterval: config.pollingInterval || 1000
98942
+ };
98943
+ },
98944
+ validateAccount: async (account) => {
98945
+ if (!account.botToken)
98946
+ return false;
98947
+ return true;
98948
+ }
98949
+ };
98950
+ var createOutboundAdapter = (getBot) => ({
98951
+ deliveryMode: "direct",
98952
+ textChunkLimit: 4096,
98953
+ chunker: (text, limit) => {
98954
+ const chunks = [];
98955
+ for (let i = 0;i < text.length; i += limit) {
98956
+ chunks.push(text.slice(i, i + limit));
98957
+ }
98958
+ return { chunks, totalChunks: chunks.length };
98959
+ },
98960
+ sendText: async ({ to, text, accountId, account, replyToId, threadId }) => {
98961
+ const bot = getBot();
98962
+ if (!bot) {
98963
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
98964
+ }
98965
+ try {
98966
+ const chatId = parseInt(to, 10);
98967
+ const options = {
98968
+ parse_mode: "Markdown"
98969
+ };
98970
+ if (replyToId) {
98971
+ options.reply_to_message_id = parseInt(replyToId, 10);
98972
+ }
98973
+ if (threadId) {
98974
+ options.message_thread_id = parseInt(threadId, 10);
98975
+ }
98976
+ const result = await bot.sendMessage(chatId, text, options);
98977
+ return {
98978
+ success: true,
98979
+ messageId: result.message_id.toString(),
98980
+ timestamp: new Date
98981
+ };
98982
+ } catch (error) {
98983
+ return {
98984
+ success: false,
98985
+ error: error.message,
98986
+ timestamp: new Date
98987
+ };
98988
+ }
98989
+ },
98990
+ sendMedia: async ({ to, text, mediaUrl, mediaType, accountId, account }) => {
98991
+ const bot = getBot();
98992
+ if (!bot) {
98993
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
98994
+ }
98995
+ try {
98996
+ const chatId = parseInt(to, 10);
98997
+ let result;
98998
+ if (mediaType === "image") {
98999
+ result = await bot.sendPhoto(chatId, mediaUrl, { caption: text });
99000
+ } else if (mediaType === "video") {
99001
+ result = await bot.sendVideo(chatId, mediaUrl, { caption: text });
99002
+ } else if (mediaType === "audio") {
99003
+ result = await bot.sendAudio(chatId, mediaUrl, { caption: text });
99004
+ } else {
99005
+ result = await bot.sendDocument(chatId, mediaUrl, { caption: text });
99006
+ }
99007
+ return {
99008
+ success: true,
99009
+ messageId: result.message_id.toString(),
99010
+ timestamp: new Date
99011
+ };
99012
+ } catch (error) {
99013
+ return {
99014
+ success: false,
99015
+ error: error.message,
99016
+ timestamp: new Date
99017
+ };
99018
+ }
99019
+ }
99020
+ });
99021
+ var telegramThreadingAdapter = {
99022
+ replyModes: ["quote", "thread"],
99023
+ defaultReplyMode: "quote"
99024
+ };
99025
+ var createGatewayAdapter = (createBot) => {
99026
+ const activeBots = new Map;
99027
+ const messageHandlers = new Map;
99028
+ return {
99029
+ startAccount: async ({ accountId, account, onMessage }) => {
99030
+ const bot = createBot(account.botToken);
99031
+ const handler = (msg) => {
99032
+ if (account.allowedUsers?.length && !account.allowedUsers.includes(msg.from?.id || 0)) {
99033
+ return;
99034
+ }
99035
+ if (account.allowedChats?.length && !account.allowedChats.includes(msg.chat.id)) {
99036
+ return;
99037
+ }
99038
+ const channelId = {
99039
+ platform: "telegram",
99040
+ accountId: msg.chat.id.toString()
99041
+ };
99042
+ const channelMessage = {
99043
+ messageId: msg.message_id.toString(),
99044
+ channelId,
99045
+ timestamp: new Date(msg.date * 1000),
99046
+ sender: {
99047
+ id: msg.from?.id.toString() || "unknown",
99048
+ username: msg.from?.username,
99049
+ displayName: msg.from?.first_name,
99050
+ isBot: msg.from?.is_bot || false
99051
+ },
99052
+ text: msg.text || "",
99053
+ context: {
99054
+ isDM: msg.chat.type === "private",
99055
+ groupName: msg.chat.title,
99056
+ threadId: msg.message_thread_id?.toString()
99057
+ },
99058
+ replyTo: msg.reply_to_message ? {
99059
+ messageId: msg.reply_to_message.message_id.toString(),
99060
+ channelId
99061
+ } : undefined
99062
+ };
99063
+ onMessage(channelMessage);
99064
+ };
99065
+ bot.on("message", handler);
99066
+ activeBots.set(accountId, bot);
99067
+ messageHandlers.set(accountId, handler);
99068
+ },
99069
+ stopAccount: async ({ accountId, account }) => {
99070
+ const bot = activeBots.get(accountId);
99071
+ const handler = messageHandlers.get(accountId);
99072
+ if (bot && handler) {
99073
+ bot.off("message", handler);
99074
+ if (bot.isPolling()) {
99075
+ await bot.stopPolling();
99076
+ }
99077
+ activeBots.delete(accountId);
99078
+ messageHandlers.delete(accountId);
99079
+ }
99080
+ },
99081
+ isAccountActive: (accountId) => {
99082
+ return activeBots.has(accountId);
99083
+ }
99084
+ };
99085
+ };
99086
+ function createTelegramPlugin(config = {}, TelegramBotClass) {
99087
+ let bot = null;
99088
+ const createBot = (token) => {
99089
+ if (!TelegramBotClass) {
99090
+ throw new Error("TelegramBot class not provided");
99091
+ }
99092
+ return new TelegramBotClass(token, { polling: true });
99093
+ };
99094
+ return {
99095
+ id: "telegram",
99096
+ meta: telegramMeta,
99097
+ capabilities: {
99098
+ chatTypes: ["direct", "group", "channel", "thread"],
99099
+ supports: {
99100
+ text: true,
99101
+ media: true,
99102
+ replies: true,
99103
+ threads: true,
99104
+ reactions: true,
99105
+ editing: true,
99106
+ streaming: false,
99107
+ buttons: true
99108
+ },
99109
+ nativeCommands: true,
99110
+ rateLimits: {
99111
+ messagesPerMinute: 30,
99112
+ charactersPerMessage: 4096
99113
+ },
99114
+ media: {
99115
+ maxFileSize: 50 * 1024 * 1024,
99116
+ supportedMimeTypes: ["image/*", "video/*", "audio/*", "application/pdf"]
99117
+ }
99118
+ },
99119
+ config: telegramConfigAdapter,
99120
+ outbound: createOutboundAdapter(() => bot),
99121
+ gateway: createGatewayAdapter((token) => {
99122
+ bot = createBot(token);
99123
+ return bot;
99124
+ }),
99125
+ threading: telegramThreadingAdapter
99126
+ };
99127
+ }
99128
+ var telegramPlugin = createTelegramPlugin();
99129
+ if (process.env.TELEGRAM_BOT_TOKEN) {
99130
+ pluginRegistry.registerChannel({
99131
+ pluginId: "telegram",
99132
+ plugin: telegramPlugin,
99133
+ source: "core"
99134
+ });
99135
+ }
98841
99136
  // ../channel-telegram/dist/utils/normalize.js
98842
99137
  function normalizeTelegramMessagingTarget(raw) {
98843
99138
  const trimmed = raw.trim();
package/dist/index.js CHANGED
@@ -97992,6 +97992,86 @@ class StringConversationMemory extends ConversationMemory {
97992
97992
  super(config);
97993
97993
  }
97994
97994
  }
97995
+ // ../channel-types/dist/plugins/registry.js
97996
+ class PluginRegistryImpl {
97997
+ channels = new Map;
97998
+ channelOrder = [];
97999
+ registerChannel(registration) {
98000
+ const id = registration.plugin.id;
98001
+ if (typeof id !== "string") {
98002
+ throw new Error("Channel plugin id must be a string");
98003
+ }
98004
+ const normalizedId = id.trim().toLowerCase();
98005
+ if (this.channels.has(normalizedId)) {
98006
+ console.warn(`[PluginRegistry] Channel "${normalizedId}" already registered, replacing`);
98007
+ }
98008
+ this.channels.set(normalizedId, registration);
98009
+ if (!this.channelOrder.includes(normalizedId)) {
98010
+ this.channelOrder.push(normalizedId);
98011
+ }
98012
+ console.log(`[PluginRegistry] Registered channel: ${normalizedId} (source: ${registration.source})`);
98013
+ }
98014
+ unregisterChannel(channelId) {
98015
+ const normalizedId = channelId.trim().toLowerCase();
98016
+ const existed = this.channels.delete(normalizedId);
98017
+ if (existed) {
98018
+ this.channelOrder = this.channelOrder.filter((id) => id !== normalizedId);
98019
+ }
98020
+ return existed;
98021
+ }
98022
+ getChannel(channelId) {
98023
+ const normalizedId = this.normalizeChannelId(channelId);
98024
+ const registration = this.channels.get(normalizedId);
98025
+ return registration?.plugin;
98026
+ }
98027
+ getChannelRegistration(channelId) {
98028
+ const normalizedId = this.normalizeChannelId(channelId);
98029
+ return this.channels.get(normalizedId);
98030
+ }
98031
+ getChannels() {
98032
+ return this.channelOrder.map((id) => this.channels.get(id)?.plugin).filter((p) => p !== undefined);
98033
+ }
98034
+ getChannelRegistrations() {
98035
+ return this.channelOrder.map((id) => this.channels.get(id)).filter((r) => r !== undefined);
98036
+ }
98037
+ getChannelOrder() {
98038
+ return [...this.channelOrder];
98039
+ }
98040
+ setChannelOrder(order) {
98041
+ this.channelOrder = order.map((id) => id.toLowerCase().trim());
98042
+ }
98043
+ getChannelsByCapability(capability) {
98044
+ return this.getChannels().filter((plugin) => plugin.capabilities.supports[capability] === true);
98045
+ }
98046
+ getChannelsByChatType(chatType) {
98047
+ return this.getChannels().filter((plugin) => plugin.capabilities.chatTypes?.includes(chatType));
98048
+ }
98049
+ hasChannel(channelId) {
98050
+ return this.channels.has(this.normalizeChannelId(channelId));
98051
+ }
98052
+ normalizeChannelId(channelId) {
98053
+ const id = channelId.trim().toLowerCase();
98054
+ const aliases = {
98055
+ tg: "telegram",
98056
+ imsg: "imessage",
98057
+ wa: "whatsapp",
98058
+ dc: "discord",
98059
+ sl: "slack"
98060
+ };
98061
+ return aliases[id] || id;
98062
+ }
98063
+ clear() {
98064
+ this.channels.clear();
98065
+ this.channelOrder = [];
98066
+ }
98067
+ getStats() {
98068
+ return {
98069
+ channelCount: this.channels.size,
98070
+ channels: this.getChannelOrder()
98071
+ };
98072
+ }
98073
+ }
98074
+ var pluginRegistry = new PluginRegistryImpl;
97995
98075
  // ../channel-types/dist/index.js
97996
98076
  function createChannelId(platform, accountId, instanceId) {
97997
98077
  return { platform, accountId, instanceId };
@@ -99032,6 +99112,222 @@ function registerAllCommands(bot, memory, tools) {
99032
99112
  registerInnerthoughtsCommand(bot, memory, tools);
99033
99113
  register(bot, tools);
99034
99114
  }
99115
+
99116
+ // ../channel-telegram/dist/plugin.js
99117
+ var telegramMeta = {
99118
+ label: "Telegram",
99119
+ blurb: "Telegram Bot API for direct and group chats",
99120
+ icon: "\uD83D\uDCF1",
99121
+ docsPath: "/docs/channels/telegram",
99122
+ quickstartAllowFrom: true
99123
+ };
99124
+ var telegramConfigAdapter = {
99125
+ listAccountIds: async (config) => {
99126
+ const botToken = config.botToken;
99127
+ if (!botToken)
99128
+ return [];
99129
+ return ["default"];
99130
+ },
99131
+ resolveAccount: async (config, accountId) => {
99132
+ return {
99133
+ botToken: config.botToken,
99134
+ allowedUsers: config.allowedUsers,
99135
+ allowedChats: config.allowedChats,
99136
+ pollingInterval: config.pollingInterval || 1000
99137
+ };
99138
+ },
99139
+ validateAccount: async (account) => {
99140
+ if (!account.botToken)
99141
+ return false;
99142
+ return true;
99143
+ }
99144
+ };
99145
+ var createOutboundAdapter = (getBot) => ({
99146
+ deliveryMode: "direct",
99147
+ textChunkLimit: 4096,
99148
+ chunker: (text, limit) => {
99149
+ const chunks = [];
99150
+ for (let i = 0;i < text.length; i += limit) {
99151
+ chunks.push(text.slice(i, i + limit));
99152
+ }
99153
+ return { chunks, totalChunks: chunks.length };
99154
+ },
99155
+ sendText: async ({ to, text, accountId, account, replyToId, threadId }) => {
99156
+ const bot = getBot();
99157
+ if (!bot) {
99158
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
99159
+ }
99160
+ try {
99161
+ const chatId = parseInt(to, 10);
99162
+ const options = {
99163
+ parse_mode: "Markdown"
99164
+ };
99165
+ if (replyToId) {
99166
+ options.reply_to_message_id = parseInt(replyToId, 10);
99167
+ }
99168
+ if (threadId) {
99169
+ options.message_thread_id = parseInt(threadId, 10);
99170
+ }
99171
+ const result = await bot.sendMessage(chatId, text, options);
99172
+ return {
99173
+ success: true,
99174
+ messageId: result.message_id.toString(),
99175
+ timestamp: new Date
99176
+ };
99177
+ } catch (error) {
99178
+ return {
99179
+ success: false,
99180
+ error: error.message,
99181
+ timestamp: new Date
99182
+ };
99183
+ }
99184
+ },
99185
+ sendMedia: async ({ to, text, mediaUrl, mediaType, accountId, account }) => {
99186
+ const bot = getBot();
99187
+ if (!bot) {
99188
+ return { success: false, error: "Bot not initialized", timestamp: new Date };
99189
+ }
99190
+ try {
99191
+ const chatId = parseInt(to, 10);
99192
+ let result;
99193
+ if (mediaType === "image") {
99194
+ result = await bot.sendPhoto(chatId, mediaUrl, { caption: text });
99195
+ } else if (mediaType === "video") {
99196
+ result = await bot.sendVideo(chatId, mediaUrl, { caption: text });
99197
+ } else if (mediaType === "audio") {
99198
+ result = await bot.sendAudio(chatId, mediaUrl, { caption: text });
99199
+ } else {
99200
+ result = await bot.sendDocument(chatId, mediaUrl, { caption: text });
99201
+ }
99202
+ return {
99203
+ success: true,
99204
+ messageId: result.message_id.toString(),
99205
+ timestamp: new Date
99206
+ };
99207
+ } catch (error) {
99208
+ return {
99209
+ success: false,
99210
+ error: error.message,
99211
+ timestamp: new Date
99212
+ };
99213
+ }
99214
+ }
99215
+ });
99216
+ var telegramThreadingAdapter = {
99217
+ replyModes: ["quote", "thread"],
99218
+ defaultReplyMode: "quote"
99219
+ };
99220
+ var createGatewayAdapter = (createBot) => {
99221
+ const activeBots = new Map;
99222
+ const messageHandlers = new Map;
99223
+ return {
99224
+ startAccount: async ({ accountId, account, onMessage }) => {
99225
+ const bot = createBot(account.botToken);
99226
+ const handler = (msg) => {
99227
+ if (account.allowedUsers?.length && !account.allowedUsers.includes(msg.from?.id || 0)) {
99228
+ return;
99229
+ }
99230
+ if (account.allowedChats?.length && !account.allowedChats.includes(msg.chat.id)) {
99231
+ return;
99232
+ }
99233
+ const channelId = {
99234
+ platform: "telegram",
99235
+ accountId: msg.chat.id.toString()
99236
+ };
99237
+ const channelMessage = {
99238
+ messageId: msg.message_id.toString(),
99239
+ channelId,
99240
+ timestamp: new Date(msg.date * 1000),
99241
+ sender: {
99242
+ id: msg.from?.id.toString() || "unknown",
99243
+ username: msg.from?.username,
99244
+ displayName: msg.from?.first_name,
99245
+ isBot: msg.from?.is_bot || false
99246
+ },
99247
+ text: msg.text || "",
99248
+ context: {
99249
+ isDM: msg.chat.type === "private",
99250
+ groupName: msg.chat.title,
99251
+ threadId: msg.message_thread_id?.toString()
99252
+ },
99253
+ replyTo: msg.reply_to_message ? {
99254
+ messageId: msg.reply_to_message.message_id.toString(),
99255
+ channelId
99256
+ } : undefined
99257
+ };
99258
+ onMessage(channelMessage);
99259
+ };
99260
+ bot.on("message", handler);
99261
+ activeBots.set(accountId, bot);
99262
+ messageHandlers.set(accountId, handler);
99263
+ },
99264
+ stopAccount: async ({ accountId, account }) => {
99265
+ const bot = activeBots.get(accountId);
99266
+ const handler = messageHandlers.get(accountId);
99267
+ if (bot && handler) {
99268
+ bot.off("message", handler);
99269
+ if (bot.isPolling()) {
99270
+ await bot.stopPolling();
99271
+ }
99272
+ activeBots.delete(accountId);
99273
+ messageHandlers.delete(accountId);
99274
+ }
99275
+ },
99276
+ isAccountActive: (accountId) => {
99277
+ return activeBots.has(accountId);
99278
+ }
99279
+ };
99280
+ };
99281
+ function createTelegramPlugin(config = {}, TelegramBotClass) {
99282
+ let bot = null;
99283
+ const createBot = (token) => {
99284
+ if (!TelegramBotClass) {
99285
+ throw new Error("TelegramBot class not provided");
99286
+ }
99287
+ return new TelegramBotClass(token, { polling: true });
99288
+ };
99289
+ return {
99290
+ id: "telegram",
99291
+ meta: telegramMeta,
99292
+ capabilities: {
99293
+ chatTypes: ["direct", "group", "channel", "thread"],
99294
+ supports: {
99295
+ text: true,
99296
+ media: true,
99297
+ replies: true,
99298
+ threads: true,
99299
+ reactions: true,
99300
+ editing: true,
99301
+ streaming: false,
99302
+ buttons: true
99303
+ },
99304
+ nativeCommands: true,
99305
+ rateLimits: {
99306
+ messagesPerMinute: 30,
99307
+ charactersPerMessage: 4096
99308
+ },
99309
+ media: {
99310
+ maxFileSize: 50 * 1024 * 1024,
99311
+ supportedMimeTypes: ["image/*", "video/*", "audio/*", "application/pdf"]
99312
+ }
99313
+ },
99314
+ config: telegramConfigAdapter,
99315
+ outbound: createOutboundAdapter(() => bot),
99316
+ gateway: createGatewayAdapter((token) => {
99317
+ bot = createBot(token);
99318
+ return bot;
99319
+ }),
99320
+ threading: telegramThreadingAdapter
99321
+ };
99322
+ }
99323
+ var telegramPlugin = createTelegramPlugin();
99324
+ if (process.env.TELEGRAM_BOT_TOKEN) {
99325
+ pluginRegistry.registerChannel({
99326
+ pluginId: "telegram",
99327
+ plugin: telegramPlugin,
99328
+ source: "core"
99329
+ });
99330
+ }
99035
99331
  // ../channel-telegram/dist/utils/normalize.js
99036
99332
  function normalizeTelegramMessagingTarget(raw) {
99037
99333
  const trimmed = raw.trim();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ebowwa/glm-daemon",
3
- "version": "0.4.6",
3
+ "version": "0.4.7",
4
4
  "description": "Autonomous GLM 4.7 daemon with hooks, tools, teammates, and communication channels (Telegram, Discord)",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -63,10 +63,10 @@
63
63
  "zod": "^4.3.5"
64
64
  },
65
65
  "devDependencies": {
66
- "@types/bun": "catalog:dev",
67
- "@types/node": "catalog:dev",
68
- "typescript": "catalog:",
69
- "bun-types": "catalog:dev"
66
+ "@types/bun": "latest",
67
+ "@types/node": "latest",
68
+ "typescript": "latest",
69
+ "bun-types": "latest"
70
70
  },
71
71
  "files": [
72
72
  "dist",