Skip to main content
Glama

ZBD MCP Server

Official
by zbdpay
zbd.ts12.3 kB
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js"; import { StdioServerTransport } from "@modelcontextprotocol/sdk/server/stdio.js"; import { z } from "zod"; import dotenv from 'dotenv'; // Load environment variables from .env file dotenv.config(); // Create an MCP server instance const server = new McpServer({ name: "zbd-mcp-server", version: "1.0.0", }); // Utility function for making ZBD API requests async function zbdRequest(endpoint: string, options: { method: 'GET' | 'POST', body?: any, urlParams?: string }) { try { const url = `https://api.zebedee.io/v0/${endpoint}${options.urlParams ? `/${options.urlParams}` : ''}`; const response = await fetch(url, { method: options.method, headers: { "Content-Type": "application/json", "apikey": process.env.ZBD_API_KEY || "1J4kYlF7XtvpSZTMVY4Tbk8vjcJ6EOsp" }, ...(options.body && { body: JSON.stringify(options.body) }) }); const data = await response.json(); return { content: [{ type: "text" as const, text: JSON.stringify(data, null, 2) }] }; } catch (error: any) { return { content: [{ type: "text" as const, text: `Error: ${error.message}` }] }; } } // Add Lightning payment tool server.tool( "send-lightning-payment", "Send a Bitcoin Lightning Network payment to a Lightning Address using ZBD", { lnAddress: z.string().describe("Lightning Address of the recipient (e.g. andre@zbd.gg)"), amount: z.string().describe("Amount in millisatoshis"), comment: z.string().optional().describe("Optional note or description"), internalId: z.string().optional().describe("Optional metadata string"), callbackUrl: z.string().optional().describe("Optional callback URL for payment updates") }, async (params) => zbdRequest("ln-address/send-payment", { method: "POST", body: params }) ); // Add ZBD Gamertag payment tool server.tool( "send-gamertag-payment", "Send a Bitcoin payment to a ZBD Gamertag", { gamertag: z.string().describe("Destination ZBD Gamertag"), amount: z.string().describe("Amount in millisatoshis"), description: z.string().describe("Note or comment for this Payment (visible to recipient)") }, async (params) => zbdRequest("gamertag/send-payment", { method: "POST", body: params }) ); // Add ZBD Gamertag charge creation tool server.tool( "create-gamertag-charge", "Generate a payment request for a ZBD User", { gamertag: z.string().describe("Destination ZBD Gamertag"), amount: z.string().describe("Amount in millisatoshis"), description: z.string().optional().describe("Note or comment for this Payment (visible to recipient)"), expiresIn: z.number().optional().describe("Time until Charge expiration -> in seconds"), internalId: z.string().optional().describe("Open metadata string property"), callbackUrl: z.string().optional().describe("The endpoint ZBD will POST Charge updates to") }, async (params) => zbdRequest("gamertag/charges", { method: "POST", body: params }) ); // Add Lightning Address validation tool server.tool( "validate-lightning-address", "Verify the validity of a Lightning Address", { address: z.string().describe("Lightning Address to be verified (e.g. user@domain.com)") }, async ({ address }) => zbdRequest("ln-address/validate", { method: "GET", urlParams: encodeURIComponent(address) }) ); // Add Lightning Address charge creation tool server.tool( "create-lightning-charge", "Generate a payment request for a Lightning Address", { lnaddress: z.string().describe("The Lightning Address of the intended recipient"), amount: z.string().describe("The amount for the Charge -> in millisatoshis"), description: z.string().optional().describe("Note or comment of this Charge") }, async (params) => zbdRequest("ln-address/fetch-charge", { method: "POST", body: params }) ); // Add Get User ID by Gamertag tool server.tool( "get-userid-by-gamertag", "Retrieve User ID from a ZBD Gamertag", { gamertag: z.string().describe("ZBD Gamertag") }, async ({ gamertag }) => zbdRequest("user-id/gamertag", { method: "GET", urlParams: encodeURIComponent(gamertag) }) ); // Add Get Gamertag by User ID tool server.tool( "get-gamertag-by-userid", "Retrieve ZBD Gamertag from a User ID", { id: z.string().describe("User ID") }, async ({ id }) => zbdRequest("gamertag/user-id", { method: "GET", urlParams: encodeURIComponent(id) }) ); // Add Email payment tool server.tool( "send-email-payment", "Send instant Bitcoin payments to any email", { email: z.string().describe("The Email of the intended recipient (e.g. info@zebedee.io)"), amount: z.string().describe("The amount for the Payment -> in millisatoshis"), comment: z.string().describe("Note / description of this Payment (may be shown to recipient)") }, async (params) => zbdRequest("email/send-payment", { method: "POST", body: params }) ); // Add Get Wallet Info tool server.tool( "get-wallet-info", "Retrieve all data about a ZBD Project's Wallet", {}, async () => zbdRequest("wallet", { method: "GET" }) ); // Add Region Check tool server.tool( "check-supported-region", "Verify if a user is coming from a supported region", { ipAddress: z.string().describe("IP address to check") }, async ({ ipAddress }) => zbdRequest("is-supported-region", { method: "GET", urlParams: encodeURIComponent(ipAddress) }) ); // Add ZBD IP Addresses tool server.tool( "get-zbd-ip-addresses", "Get the official IP addresses of ZBD servers", {}, async () => zbdRequest("prod-ips", { method: "GET" }) ); // Add Internal Transfer tool server.tool( "internal-transfer", "Performs a transfer of funds between two Projects", { amount: z.string().describe("The amount to be transferred -> in millisatoshis"), receiverWalletId: z.string().describe("The Wallet ID of the recipient Project") }, async (params) => zbdRequest("internal-transfer", { method: "POST", body: params }) ); // Add Create Withdrawal Request tool server.tool( "create-withdrawal-request", "Create a Bitcoin withdrawal QR code", { amount: z.string().describe("The amount for the Withdrawal Request -> in millisatoshis"), description: z.string().optional().describe("Note or comment for this Withdrawal Request"), expiresIn: z.number().optional().describe("Time until Withdrawal Request expiration -> in seconds"), internalId: z.string().optional().describe("Open metadata string property"), callbackUrl: z.string().optional().describe("The endpoint ZBD will POST updates to") }, async (params) => zbdRequest("withdrawal-requests", { method: "POST", body: params }) ); // Add Get Withdrawal Request tool server.tool( "get-withdrawal-request", "Retrieve all data about a single Withdrawal Request", { id: z.string().describe("Withdrawal Request ID") }, async ({ id }) => zbdRequest("withdrawal-requests", { method: "GET", urlParams: encodeURIComponent(id) }) ); // Add Send Payment tool server.tool( "send-payment", "Send a Bitcoin Lightning Network payment", { invoice: z.string().describe("Lightning Network Payment Request / Charge"), description: z.string().optional().describe("Note or comment for this Payment"), amount: z.string().optional().describe("Amount to be paid to this Charge/Invoice -> in millisatoshis (only valid if Amountless Invoice)"), internalId: z.string().optional().describe("Open metadata string property"), callbackUrl: z.string().optional().describe("The endpoint ZBD will POST Payment updates to") }, async (params) => zbdRequest("payments", { method: "POST", body: params }) ); // Add Get Payment tool server.tool( "get-payment", "Retrieve all data about a single Payment", { id: z.string().describe("Payment ID") }, async ({ id }) => zbdRequest("payments", { method: "GET", urlParams: encodeURIComponent(id) }) ); // Add Decode Charge tool server.tool( "decode-charge", "Understand the inner properties of a Charge QR code", { invoice: z.string().describe("The Charge or Invoice QR code contents") }, async (params) => zbdRequest("decode-invoice", { method: "POST", body: params }) ); // Add Create Charge tool server.tool( "create-charge", "Create a new Bitcoin Lightning Network charge", { amount: z.string().describe("The amount for the Charge -> in millisatoshis"), description: z.string().describe("Note or comment for this Charge (visible to payer)"), expiresIn: z.number().optional().describe("Time until Charge expiration -> in seconds"), callbackUrl: z.string().optional().describe("The endpoint ZBD will POST Charge updates to"), internalId: z.string().optional().describe("Open metadata string property") }, async (params) => zbdRequest("charges", { method: "POST", body: params }) ); // Add Get Charge tool server.tool( "get-charge", "Retrieve all data about a single Charge", { id: z.string().describe("Charge ID") }, async ({ id }) => zbdRequest("charges", { method: "GET", urlParams: encodeURIComponent(id) }) ); // Add Create Voucher tool server.tool( "create-voucher", "Create a single-use ZBD Voucher that can be redeemed by any ZBD user", { amount: z.string().describe("The amount for the Voucher -> in millisatoshis"), description: z.string().optional().describe("Note or comment for this Voucher") }, async (params) => zbdRequest("create-voucher", { method: "POST", body: params }) ); // Add Get Voucher tool server.tool( "get-voucher", "Retrieve details about a ZBD Voucher", { id: z.string().describe("ID of the Voucher") }, async ({ id }) => zbdRequest("vouchers", { method: "GET", urlParams: encodeURIComponent(id) }) ); // Add Redeem Voucher tool server.tool( "redeem-voucher", "Redeem a ZBD Voucher to credit your Project wallet", { code: z.string().describe("Valid 8-digit ZBD Voucher Code") }, async (params) => zbdRequest("redeem-voucher", { method: "POST", body: params }) ); // Add Revoke Voucher tool server.tool( "revoke-voucher", "Revoke a valid ZBD Voucher and reclaim the sats to your Project wallet", { code: z.string().describe("Valid 8-digit ZBD Voucher Code") }, async (params) => zbdRequest("revoke-voucher", { method: "POST", body: params }) ); // Add Batch Lightning Payment tool server.tool( "send-batch-lightning-payments", "Send multiple Bitcoin Lightning Network payments to Lightning Addresses in a single request", { payments: z.array(z.object({ lnAddress: z.string().describe("Lightning Address of the recipient (e.g. andre@zbd.gg)"), amount: z.string().describe("Amount in millisatoshis"), comment: z.string().optional().describe("Optional note or description"), internalId: z.string().optional().describe("Optional metadata string") })).max(10).describe("Array of payment requests (maximum 10)"), }, async ({ payments }) => { const results = []; for (const payment of payments) { try { const result = await zbdRequest("ln-address/send-payment", { method: "POST", body: payment }); results.push({ lnAddress: payment.lnAddress, status: "success", ...result }); } catch (error: any) { results.push({ lnAddress: payment.lnAddress, status: "failed", error: error.message }); } } return { content: [{ type: "text" as const, text: JSON.stringify({ totalPayments: payments.length, results }, null, 2) }] }; } ); // Start the server using stdio transport async function main() { const transport = new StdioServerTransport(); await server.connect(transport); console.error("MCP Server running on stdio"); } main().catch((error) => { console.error("Fatal error:", error); process.exit(1); });

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/zbdpay/zbd-mcp-server'

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