Skip to main content
Glama

deBridge MCP Server

by RookieCol
debridgeClient.ts8.6 kB
import type { deBridgeOrderResponse } from "./types/deBridge"; /** * DeBridge DLN API Client * * Client for interacting with deBridge DLN cross-chain swap API. * * @see https://api.dln.trade/v1.0/ * * @example * ```ts * const client = new DeBridgeClient(); * const quote = await client.fetchQuote({ * srcChainId: "42161", * srcToken: "0xaf88d065e77c8cC2239327C5EDb3A432268e5831", * amount: "1000000", * dstChainId: "1", * dstToken: "0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48" * }); * ``` */ export class DeBridgeClient { private readonly baseUrl: string; /** * Creates a new DeBridge API client. * * @param options - Client configuration options * @param options.baseUrl - Base URL for deBridge API (default: from env or production URL) */ constructor(options?: { baseUrl?: string }) { this.baseUrl = options?.baseUrl || process.env.DLN_API_BASE || "https://deswap.debridge.finance/v1.0"; } /** * Fetches a cross-chain swap quote from deBridge DLN API. * * @param params - Quote parameters * @param params.srcChainId - Source blockchain ID (e.g., "42161" for Arbitrum) * @param params.srcToken - Source token contract address * @param params.amount - Amount in token's smallest unit (wei/decimals) * @param params.dstChainId - Destination blockchain ID (e.g., "1" for Ethereum) * @param params.dstToken - Destination token contract address * @param params.senderAddress - Optional wallet address (enables transaction data generation) * @param params.dstChainTokenOutRecipient - Optional recipient address on destination chain * @param params.dstChainTokenOutAmount - Optional output amount (default: "auto") * @param params.referralCode - Optional referral code for rewards * @param params.affiliateFeePercent - Optional affiliate fee in basis points * @param params.affiliateFeeRecipient - Optional affiliate fee recipient address * * @returns Promise resolving to quote estimation and optional transaction data * @throws Error if source and destination chains are the same * @throws Error if API request fails */ async fetchQuote(params: { srcChainId: string; srcToken: string; amount: string; dstChainId: string; dstToken: string; senderAddress?: string; dstChainTokenOutRecipient?: string; dstChainTokenOutAmount?: string; referralCode?: string; affiliateFeePercent?: number; affiliateFeeRecipient?: string; }): Promise<deBridgeOrderResponse> { this.validateChains(params.srcChainId, params.dstChainId); const queryParams = this.buildQueryParams(params); const url = `${this.baseUrl}/dln/order/create-tx?${queryParams}`; const response = await fetch(url); if (!response.ok) { const errorText = await response.text(); throw new Error( `Failed to create bridge order: ${response.statusText}. ${errorText}`, ); } const data: any = await response.json(); if (data.error) { throw new Error(`DeBridge API Error: ${data.error}`); } if (data.tx?.data) { data.tx.data = data.tx.data.toString(); } return data as deBridgeOrderResponse; } /** * Fetches list of supported blockchain networks. * * @returns Promise resolving to list of supported chains * @throws Error if API request fails */ async getSupportedChains(): Promise<{ chains: Array<{ chainId: number; originalChainId: number; chainName: string }>; totalChains: number; }> { const response = await fetch(`${this.baseUrl}/supported-chains-info`); if (!response.ok) { throw new Error(`Failed to fetch supported chains: ${response.statusText}`); } const data: any = await response.json(); return { chains: data.chains || [], totalChains: data.chains?.length || 0 }; } /** * Fetches token information for a specific blockchain. * * @param chainId - Blockchain ID (e.g., "1" for Ethereum) * @returns Promise resolving to tokens list and count * @throws Error if API request fails */ async getTokensInfo(chainId: string): Promise<{ chainId: string; tokens: Record<string, any>; tokenCount: number; }> { const response = await fetch(`${this.baseUrl}/token-list?chainId=${chainId}`); if (!response.ok) { throw new Error(`Failed to fetch tokens for chain ${chainId}: ${response.statusText}`); } const data: any = await response.json(); return { chainId, tokens: data.tokens || {}, tokenCount: Object.keys(data.tokens || {}).length }; } /** * Fetches the status of a cross-chain order. * * @param orderId - Unique order identifier * @returns Promise resolving to order status details * @throws Error if API request fails */ async getOrderStatus(orderId: string): Promise<{ orderId: string; status: string; srcChainTxHash: string | null; dstChainTxHash: string | null; orderLink: string | null; error: string | null; fullData: any; }> { const response = await fetch(`${this.baseUrl}/dln/order/${orderId}/status`); if (!response.ok) { throw new Error(`Failed to fetch order status: ${response.statusText}`); } const data: any = await response.json(); return { orderId, status: data.status, srcChainTxHash: data.srcChainTxHash || null, dstChainTxHash: data.dstChainTxHash || null, orderLink: data.orderLink || null, error: data.error || null, fullData: data }; } /** * Validates that source and destination chains are different. * * @param srcChainId - Source chain ID * @param dstChainId - Destination chain ID * @throws Error if chains are the same */ private validateChains(srcChainId: string, dstChainId: string): void { if (srcChainId === dstChainId) { throw new Error("Source and destination chains must be different"); } } /** * Builds URL query parameters for the API request. * * @param params - Quote parameters * @returns URLSearchParams object */ private buildQueryParams(params: { srcChainId: string; srcToken: string; amount: string; dstChainId: string; dstToken: string; senderAddress?: string; dstChainTokenOutRecipient?: string; dstChainTokenOutAmount?: string; referralCode?: string; affiliateFeePercent?: number; affiliateFeeRecipient?: string; }): URLSearchParams { const queryParams = new URLSearchParams({ srcChainId: params.srcChainId, srcChainTokenIn: params.srcToken, srcChainTokenInAmount: params.amount, dstChainId: params.dstChainId, dstChainTokenOut: params.dstToken, dstChainTokenOutAmount: params.dstChainTokenOutAmount || "auto", prependOperatingExpenses: "true" }); if (params.senderAddress) { this.addAddressParams(queryParams, params); } if (params.referralCode) { queryParams.set("referralCode", params.referralCode); } if (this.shouldAddAffiliateFee(params)) { queryParams.set("affiliateFeePercent", params.affiliateFeePercent!.toString()); queryParams.set("affiliateFeeRecipient", params.affiliateFeeRecipient!); } return queryParams; } /** * Adds address-related parameters for full mode (with wallet). * * @param queryParams - URLSearchParams to modify * @param params - Quote parameters with senderAddress */ private addAddressParams( queryParams: URLSearchParams, params: { senderAddress?: string; dstChainTokenOutRecipient?: string; } ): void { if (!params.senderAddress) return; const recipient = params.dstChainTokenOutRecipient || params.senderAddress; queryParams.set("dstChainTokenOutRecipient", recipient); queryParams.set("senderAddress", params.senderAddress); queryParams.set("srcChainOrderAuthorityAddress", params.senderAddress); queryParams.set("srcChainRefundAddress", params.senderAddress); queryParams.set("dstChainOrderAuthorityAddress", recipient); } /** * Checks if affiliate fee parameters should be added. * * @param params - Quote parameters * @returns True if affiliate fee should be added */ private shouldAddAffiliateFee(params: { affiliateFeePercent?: number; affiliateFeeRecipient?: string; }): boolean { return params.affiliateFeePercent !== undefined && params.affiliateFeePercent > 0 && !!params.affiliateFeeRecipient; } }

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/RookieCol/debridge-mcp'

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