Skip to main content
Glama
handlers.tsβ€’14.3 kB
import TelegramBot from 'node-telegram-bot-api'; import { Client } from '@modelcontextprotocol/sdk/client/index.js'; interface UserSession { mcpClient: Client; transport: any; availableTools: any[]; } // Execute MCP tool with parameters export async function executeMCPTool( session: UserSession, toolName: string, parameters: Record<string, any> = {} ): Promise<any> { try { const result = await session.mcpClient.callTool({ name: toolName, arguments: parameters, }); return result; } catch (error) { throw new Error(`Failed to execute ${toolName}: ${error}`); } } // Wallet command handlers export function setupWalletHandlers(bot: TelegramBot, userSessions: Map<number, UserSession>) { // /wallet create bot.onText(/\/wallet create/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'create_wallet'); bot.sendMessage(chatId, `βœ… *Wallet Created Successfully!*\n\nπŸ”‘ *Address:* \`${result.content[0]?.text || 'N/A'}\`\n\n⚠️ *Important:* Save your private key securely!`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error creating wallet: ${error}`); } }); // /wallet address bot.onText(/\/wallet address/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } try { const result = await executeMCPTool(session, 'get_current_wallet'); const walletText = result.content[0]?.text || ''; // Extract address from response const addressMatch = walletText.match(/Address:\s*(0x[a-fA-F0-9]{40})/i); if (addressMatch) { bot.sendMessage(chatId, `🏦 *Your Wallet Address:*\n\n\`${addressMatch[1]}\``, { parse_mode: 'Markdown' }); } else { bot.sendMessage(chatId, '❌ No wallet found. Please create or import a wallet first using `/wallet create` or `/wallet import <mnemonic>`', { parse_mode: 'Markdown' }); } } catch (error) { bot.sendMessage(chatId, '❌ No wallet found. Please create or import a wallet first using `/wallet create` or `/wallet import <mnemonic>`', { parse_mode: 'Markdown' }); } } catch (error) { bot.sendMessage(chatId, `❌ Error getting wallet address: ${error}`); } }); // /wallet import <mnemonic or private key> bot.onText(/\/wallet import (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const input = match?.[1]?.trim(); if (!input) { bot.sendMessage(chatId, '❌ Please provide a mnemonic phrase or private key:\n\n`/wallet import your mnemonic phrase here`\nor\n`/wallet import 0xYourPrivateKey`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } // Detect if it's a private key (starts with 0x and is 66 chars) or mnemonic const isPrivateKey = input.startsWith('0x') && input.length === 66; const params = isPrivateKey ? { privateKey: input } : { mnemonic: input }; const result = await executeMCPTool(session, 'import_wallet', params); bot.sendMessage(chatId, `βœ… *Wallet Imported Successfully!*\n\n${result.content[0]?.text || 'Wallet imported'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error importing wallet: ${error}`); } }); // /wallet list - List all wallets bot.onText(/\/wallet list$/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'list_wallets'); bot.sendMessage(chatId, `πŸ‘› *Your Wallets:*\n\n${result.content[0]?.text || 'No wallets found'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error listing wallets: ${error}`); } }); // /wallet set <address> - Set current wallet bot.onText(/\/wallet set (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const address = match?.[1]?.trim(); if (!address) { bot.sendMessage(chatId, '❌ Please provide a wallet address:\n\n`/wallet set 0xYourAddress`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'set_current_wallet', { address }); bot.sendMessage(chatId, `βœ… *Current Wallet Set!*\n\n${result.content[0]?.text || 'Wallet set successfully'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error setting wallet: ${error}`); } }); // /wallet current - Get current wallet bot.onText(/\/wallet current$/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'get_current_wallet'); bot.sendMessage(chatId, `πŸ‘› *Current Wallet:*\n\n${result.content[0]?.text || 'No current wallet'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting current wallet: ${error}`); } }); } // Balance command handlers export function setupBalanceHandlers(bot: TelegramBot, userSessions: Map<number, UserSession>) { // /balance bot.onText(/\/balance$/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } // Try to list wallets first try { const walletsResult = await executeMCPTool(session, 'list_wallets'); const walletsText = walletsResult.content[0]?.text || ''; // Extract first wallet address const addressMatch = walletsText.match(/(?:β†’\s+|\s{2})(0x[a-fA-F0-9]+)/); if (!addressMatch) { bot.sendMessage(chatId, '❌ No wallet found. Please create or import a wallet first using `/wallet create` or `/wallet import <mnemonic>`', { parse_mode: 'Markdown' }); return; } const walletAddress = addressMatch[1]; // Get balance for the wallet address const result = await executeMCPTool(session, 'get_balance', { address: walletAddress }); bot.sendMessage(chatId, `πŸ’° *Your Balance:*\n\n${result.content[0]?.text || 'Unable to fetch balance'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, '❌ No wallet found. Please create or import a wallet first using `/wallet create` or `/wallet import <mnemonic>`', { parse_mode: 'Markdown' }); } } catch (error) { bot.sendMessage(chatId, `❌ Error getting balance: ${error}`); } }); // /balance <address> bot.onText(/\/balance (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const address = match?.[1]; if (!address) { bot.sendMessage(chatId, '❌ Please provide an address: `/balance 0x...`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'get_balance', { address }); bot.sendMessage(chatId, `πŸ’° *Balance for ${address}:*\n\n${result.content[0]?.text || 'Unable to fetch balance'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting balance: ${error}`); } }); } // Network command handlers export function setupNetworkHandlers(bot: TelegramBot, userSessions: Map<number, UserSession>) { // /gas - Get current gas prices bot.onText(/\/gas$/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'get_network_info'); const networkText = result.content[0]?.text || ''; // Extract gas price from network info const gasPriceMatch = networkText.match(/Gas Price:\s*([^\n]+)/i); const blockMatch = networkText.match(/Latest Block:\s*([^\n]+)/i); const chainMatch = networkText.match(/Chain ID:\s*([^\n]+)/i); let response = 'β›½ *Current Gas Information:*\n\n'; if (gasPriceMatch) { response += `πŸ’¨ **Gas Price:** ${gasPriceMatch[1]}\n`; } if (blockMatch) { response += `πŸ”— **Latest Block:** ${blockMatch[1]}\n`; } if (chainMatch) { response += `🌐 **Chain ID:** ${chainMatch[1]}\n`; } response += '\nπŸ’‘ *Tip: Lower gas prices mean cheaper transactions!*'; bot.sendMessage(chatId, response, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting gas information: ${error}`); } }); // /network - Get full network information bot.onText(/\/network$/, async (msg) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'get_network_info'); bot.sendMessage(chatId, `🌐 *Network Information:*\n\n${result.content[0]?.text || 'Unable to fetch network info'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting network information: ${error}`); } }); } // Transaction query handlers export function setupTransactionQueryHandlers(bot: TelegramBot, userSessions: Map<number, UserSession>) { // /tx <hash> - Get transaction details bot.onText(/\/tx (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const txHash = match?.[1]?.trim(); if (!txHash) { bot.sendMessage(chatId, '❌ Please provide a transaction hash:\n\n`/tx 0xYourTransactionHash`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'get_transaction', { hash: txHash }); bot.sendMessage(chatId, `πŸ“œ *Transaction Details:*\n\n${result.content[0]?.text || 'Transaction not found'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting transaction: ${error}`); } }); // /block <number or hash> - Get block information bot.onText(/\/block (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const blockId = match?.[1]?.trim(); if (!blockId) { bot.sendMessage(chatId, '❌ Please provide a block number or hash:\n\n`/block 12345` or `/block 0xBlockHash`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } // Check if it's a number or hash const params = blockId.startsWith('0x') ? { hash: blockId } : { number: parseInt(blockId) }; const result = await executeMCPTool(session, 'get_block', params); bot.sendMessage(chatId, `🧱 *Block Information:*\n\n${result.content[0]?.text || 'Block not found'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error getting block: ${error}`); } }); // /estimate <to> <amount> - Estimate gas for transaction bot.onText(/\/estimate (.+) (.+)/, async (msg, match) => { const chatId = msg.chat.id; const userId = msg.from?.id || 0; const to = match?.[1]?.trim(); const amount = match?.[2]?.trim(); if (!to || !amount) { bot.sendMessage(chatId, '❌ Please provide recipient and amount:\n\n`/estimate 0xRecipient 1.5`', { parse_mode: 'Markdown' }); return; } try { const session = userSessions.get(userId); if (!session) { bot.sendMessage(chatId, '❌ Please start the bot first with /start'); return; } const result = await executeMCPTool(session, 'estimate_gas', { to, amount }); bot.sendMessage(chatId, `β›½ *Gas Estimation:*\n\n${result.content[0]?.text || 'Unable to estimate gas'}`, { parse_mode: 'Markdown' }); } catch (error) { bot.sendMessage(chatId, `❌ Error estimating gas: ${error}`); } }); }

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/cuongpo/hyperion-mcp-server'

If you have feedback or need assistance with the MCP directory API, please join our Discord server