1.0.40 • Published 11 months ago

blockend_sdk_test v1.0.40

Weekly downloads
-
License
ISC
Repository
-
Last release
11 months ago

Compass SDK

Compass SDK is a powerful cross-chain transaction SDK that provides a unified liquidity layer by aggregating multiple liquidity sources across blockchain networks. It seamlessly integrates DEXs (Decentralized Exchanges), Cross-chain Bridges, RFQ (Request for Quote) systems, and Intent Protocols into a single, reliable interface. This enables developers to easily implement cross-chain token swaps, transfers, and complex DeFi operations across EVM chains, Solana, and Cosmos ecosystems.

The SDK automatically optimizes routes for the best rates and lowest fees by splitting transactions across multiple liquidity sources, handling complex cross-chain operations, and managing transaction sequences. It provides real-time price quotes, gas estimations, and transaction status tracking while abstracting away the complexity of cross-chain interactions.

Features

  • Cross-chain token swaps and transfers with optimal routing
  • Unified access to multiple liquidity sources:
    • DEXs (Uniswap, PancakeSwap, etc.)
    • Cross-chain bridges (Wormhole, LayerZero, etc.)
    • RFQ systems for better pricing on large trades
    • Intent Protocols for complex DeFi operations
  • Support for multiple blockchain networks:
    • EVM chains (Ethereum, BSC, Polygon, etc.)
    • Solana
    • Cosmos ecosystem
  • Real-time transaction status tracking and notifications
  • Comprehensive token and chain information with metadata
  • Advanced gas fee estimation and optimization
  • Built-in caching system for improved performance
  • Flexible configuration options for different environments
  • Robust error handling and transaction recovery

Installation

npm install @blockend/compass-sdk
# or
yarn add @blockend/compass-sdk

Quick Start

import {
  initializeSDK,
  getQuotes,
  executeTransaction,
  createTransaction,
  getNextTxn,
  checkStatus,
} from "@blockend/compass-sdk";

// Initialize the SDK with your API key
initializeSDK({
  apiKey: "YOUR_API_KEY",
  integratorId: "YOUR_INTEGRATOR_ID",
});

// Get quotes for a token swap
const quotes = await getQuotes({
  fromChainId: "ethereum",
  fromAssetAddress: "0x...",
  toChainId: "solana",
  toAssetAddress: "...",
  inputAmount: "1000000000000000000", // Amount in wei
  inputAmountDisplay: "1.0", // Human readable amount
  userWalletAddress: "0x...",
  recipient: "0x...",
});

// Execute the transaction with the best quote
const result = await executeTransaction({
  quote: quotes.data.quotes[0],
  provider: ethersProvider, // For EVM chains
  walletAdapter: solanaWallet, // For Solana
  cosmosClient: cosmosClient, // For Cosmos
  onStatusUpdate: (status, data) => {
    console.log(`Transaction status: ${status}`, data);
  },
});

// Check transaction status, poll the status until the status is "success" or "failed" or "partial-success". "in-progress" means the transaction is still being processed. [See example implementation below](#checkstatus-example).
const status = await checkStatus({
  routeId: transaction.routeId,
  stepId: transaction.steps[0].id,
  txnHash: result.hash,
});

API Reference

Configuration

initializeSDK(config)

Initialize the SDK with your credentials and configuration.

initializeSDK({
  apiKey: string;
  integratorId: string;
  baseURL?: string;
  enableCache?: boolean;
  cacheTimeout:number;
});

To get config, use the getConfig() method.

const config = getConfig();

To update config, use the updateConfig() method. You can update one or more parameters mentioned in the Configuration Parameters section.

updateConfig({
  apiKey: "YOUR_API_KEY",
});

Configuration Parameters

apiKey (required)

  • Your unique API key for authentication with the Blockend API
  • Must be obtained through the Blockend platform
  • Used to track API usage and enforce rate limits

integratorId (required)

  • A unique identifier for your integration/application
  • Used for analytics, tracking, and support purposes
  • Helps identify your specific implementation when interacting with Blockend services

errorHandler (optional)

  • A callback function to handle SDK errors globally
  • Receives a BlockendError object with properties:
    • message: Description of the error
    • code: Error code (e.g., "CONFIGURATION_ERROR", "NETWORK_ERROR", "VALIDATION_ERROR")
    • data: Additional error context (if available)
  • Useful for centralized error handling, logging, and error reporting
  • Example usage:
initializeSDK({
  apiKey: "YOUR_API_KEY",
  integratorId: "YOUR_INTEGRATOR_ID",
  errorHandler: (error) => {
    console.error(
      `[Compass SDK Error] ${error.code}: ${error.message}`,
      error.data
    );
    // Custom error handling logic (e.g., reporting to monitoring service)
  },
});

baseURL (optional)

  • The base URL endpoint for the Blockend API
  • Defaults to https://api2.blockend.com/v1
  • Can be modified for different environments (staging, testing, etc.)
  • Should include the version prefix (/v1)

enableCache (optional)

  • Boolean flag to enable/disable SDK's built-in caching mechanism
  • When enabled, caches API responses to reduce network requests
  • Particularly useful for frequently accessed data like token lists and chain information
  • Defaults to false if not specified

cacheTimeout (optional)

  • Duration in milliseconds for how long cached items should remain valid
  • Only applies when enableCache is true
  • Defaults to 1 hour (3600000 milliseconds)
  • Can be adjusted based on your application's needs and data freshness requirements

Core Methods

getQuotes

Gets quotes for cross-chain token swaps or transfers by aggregating liquidity from multiple sources including DEXs, Bridges, RFQs, and Intent Protocols.

interface QuoteParams {
  // Chain ID of the source blockchain (e.g., "ethereum", "solana", "bsc")
  fromChainId: string;

  // Token contract address on source chain (use native token address for chain's native currency)
  fromAssetAddress: string;

  // Chain ID of the destination blockchain
  toChainId: string;

  // Token contract address on destination chain
  toAssetAddress: string;

  // Amount in smallest unit (wei, lamports, etc.)
  inputAmount: string;

  // Human readable amount (e.g., "1.0" ETH)
  inputAmountDisplay: string;

  // Source wallet address that will initiate the transaction
  userWalletAddress: string;

  // Optional: Destination wallet address (defaults to userWalletAddress if not specified)
  recipient?: string;

  // Optional: Solana priority fee in lamports or predefined level ("LOW" | "MEDIUM" | "HIGH")
  solanaPriorityFee?: number | PriorityLevel;

  // Optional: Solana Jito MEV tip in lamports or predefined level
  solanaJitoTip?: number | PriorityLevel;

  // Optional: EVM priority fee in gwei or predefined level
  evmPriorityFee?: number | PriorityLevel;

  // Optional: Maximum allowed slippage percentage (default: 1.0)
  slippage?: number;

  // Optional: Skip certain validation checks for faster response
  skipChecks?: boolean;

  // Optional: Comma-separated list of preferred liquidity sources
  include?: string;

  // Optional: Comma-separated list of liquidity sources to exclude
  exclude?: string;

  // Optional: Use recommended liquidity provider
  recommendedProvider?: boolean;
}

//Example implementation
const quotes = await getQuotes({
  fromChainId: "evm",
  fromAssetAddress: "0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee",
  toChainId: "evm",
  toAssetAddress: "0xc2132d05d31c914a87c6611c10748aeb04b58e8f.",
  inputAmountDisplay: "1.0",
  userWalletAddress: "0x...",
  recipient: "0x...",
});

// Example Response (shortened)
{
  "status": "success",
  "data": {
    "quotes": [{
      "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
      "from": {
        "chainId": "1",
        "symbol": "ETH",
        // ... other token details
      },
      "to": {
        "chainId": "sol",
        "symbol": "USDC",
        // ... other token details
      },
      "outputAmountDisplay": "1459.244847",
      "estimatedTimeInSeconds": 900
    }]
  }
}

View full quotes response example

createTransaction(params)

Creates a transaction from a selected quote, preparing all necessary steps for the cross-chain transfer.

interface CreateTransactionParams {
  // Route ID obtained from getQuotes response
  routeId: string;
}

//Example implementation
const transaction = await createTransaction({
  routeId: quotes.data.quotes[0].routeId,
});

// Example Response (shortened)
{
  "status": "success",
  "data": {
    "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
    "steps": [{
      "stepId": "01J2WB1NY64MKVCM8FM994WMZV",
      "stepType": "bridge",
      "chainId": "1"
    }]
  }
}

View full createTransaction response example

getNextTxn(params)

Retrieves the raw transaction data for the next pending step in the transaction sequence. The response format varies based on the blockchain network:

interface TransactionDataParams {
  routeId: string; // Route ID from createTransaction
  stepId: string; // Step ID from the transaction steps array
}

//Example implementation
const nextTxn = await getNextTxn({
  routeId: transaction.routeId,
  stepId: transaction.steps[0].id,
});

// Example Response (shortened)
{
  "status": "success",
  "data": {
    "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
    "stepId": "01J2WB1NY64MKVCM8FM994WMZV",
    "networkType": "evm",
    "txnData": {
      "txnEvm": {
        "to": "0x...",
        "value": "420000000000000000",
        // ... other transaction details
      }
    }
  }
};

Transaction Data Response Examples

EVM Chain Response

{
  "status": "success",
  "data": {
    "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
    "stepId": "01J2WB1NY64MKVCM8FM994WMZV",
    "networkType": "evm",
    "txnData": {
      "txnEvm": {
        "from": "0x17e7c3DD600529F34eFA1310f00996709FfA8d5c",
        "to": "0x1234567890abcdef1234567890abcdef12345678",
        "value": "420000000000000000",
        "data": "0x095ea7b3...",
        "gasPrice": "30000000000",
        "gasLimit": "250000"
      }
    }
  }
}

Solana Chain Response

{
  "status": "success",
  "data": {
    "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
    "stepId": "01J2WB1NY64MKVCM8FM994WMZV",
    "networkType": "sol",
    "txnData": {
      "txnSol": {
        "data": "base64EncodedTransactionData...",
      }
    }
  }
}

Cosmos Chain Response

{
  "status": "success",
  "data": {
    "routeId": "01J2WB1NY6MD3F25CJTTB01D8F",
    "stepId": "01J2WB1NY64MKVCM8FM994WMZV",
    "networkType": "cosmos",
    "txnData": {
      "txnCosmos": {
        "data": "{"typeUrl":"/ibc.applications.trans"}",
        "value": "0",
        "gasLimit": "250000",
        "gasPrice": "0.025",
      }
    }
  }
}

View full getNextTxn response example

checkStatus(params)

Monitors the status of a transaction step, providing detailed information about its progress.

interface StatusCheckParams {
  // Route ID of the transaction
  routeId: string;

  // Step ID being checked
  stepId: string;

  // Transaction hash from the blockchain
  txnHash: string;
}

//Example implementation
const status = await checkStatus({
  routeId: transaction.routeId,
  stepId: transaction.steps[0].id,
  txnHash: result.hash,
});

// Example Response (shortened)
{
  "status": "success",
  "data": {
    "status": "success",
    "outputAmount": "1459244847",
    "outputAmountDisplay": "1459.244847"
  }
}
type TransactionStatus = "not-started" | "in-progress" | "success" | "failed";

View full checkStatus response example

Here's a simpler example to poll the transaction status:

async function pollWithWhileLoop(
  routeId: string,
  stepId: string,
  txnHash: string
) {
  const POLLING_INTERVAL = 3000; // 3 seconds
  const MAX_ATTEMPTS = 200; // Maximum number of attempts (10 minutes with 3s interval)
  let attempts = 0;

  while (attempts < MAX_ATTEMPTS) {
    try {
      const response = await checkStatus({ routeId, stepId, txnHash });
      const status = response.data.status;

      console.log(`Current status: ${status}`);

      if (["success", "failed", "partial-success"].includes(status)) {
        return response.data;
      }

      // Wait for the polling interval
      await new Promise((resolve) => setTimeout(resolve, POLLING_INTERVAL));
      attempts++;
    } catch (error) {
      console.error("Error checking status:", error);
      throw error;
    }
  }

  throw new Error("Polling timeout: Maximum attempts reached");
}

// Usage example:
try {
  const result = await pollWithWhileLoop(
    "your-route-id",
    "your-step-id",
    "your-transaction-hash"
  );
  console.log("Final result:", result);
} catch (error) {
  console.error("Polling failed:", error);
}

pollTransactionStatus(params)

Continuously monitors a transaction's status by polling at regular intervals until a final state is reached or timeout occurs. This method provides a convenient way to track cross-chain transactions through their entire lifecycle.

interface PollTransactionStatusParams {
  // Route ID of the transaction
  routeId: string;

  // Step ID being monitored
  stepId: string;

  // Transaction hash from the blockchain
  txnHash: string;

  // Optional: Interval between status checks in milliseconds (default: 2000ms)
  pollingIntervalMs?: number;

  // Optional: Maximum time to poll before timing out in milliseconds (default: 600000ms / 10 minutes)
  timeoutMs?: number;

  // Optional: Callback function for real-time status updates
  onStatusUpdate?: (status: TransactionStatus, data?: ExecuteTransactionResult) => void;
}

// Example usage:
const result = await pollTransactionStatus({
  routeId: "your-route-id",
  stepId: "your-step-id",
  txnHash: "your-transaction-hash",
  pollingIntervalMs: 3000, // Poll every 3 seconds, by default it's 2 seconds
  timeoutMs: 300000, // Timeout after 5 minutes, by default it's 10 minutes
  onStatusUpdate: (status, data) => {
    console.log(`Transaction status updated: ${status}`);
    if (data) {
      console.log("Transaction data:", data);
    }
  },
});

// Example Response
{
  "status": "success",
  "data": {
    "status": "success",
    "outputAmount": "1459244847",
    "outputAmountDisplay": "1459.244847",
    "srcTxnHash": "0x...",
    "dstTxnHash": "0x...",
  "srcTxnUrl": "https://etherscan.io/tx/0x...",
  "dstTxnUrl": "https://etherscan.io/tx/0x...",
  "points": 100,
  "warnings": [],
  }
}

The method will continue polling until one of these conditions is met:

  • Transaction reaches a final status ("success", "failed", or "partial-success")
  • Polling timeout is reached
  • An error occurs during status checking

Status Types:

  • "not-started": Transaction has not been initiated
  • "in-progress": Transaction is being processed
  • "success": Transaction completed successfully
  • "failed": Transaction failed
  • "partial-success": Transaction partially succeeded (some steps completed)

Error Handling:

  • Throws a timeout error if timeoutMs is exceeded
  • Throws any errors encountered during status checking
  • Provides detailed error information through the BlockendError class

Best Practices:

  1. Set appropriate pollingIntervalMs based on chain block times
  2. Configure reasonable timeoutMs for your use case
  3. Implement proper error handling
  4. Use the onStatusUpdate callback for real-time UI updates

executeTransaction(params)

Execute a transaction with the provided quote and wallet. This method handles the actual execution of the cross-chain transaction using the appropriate wallet/provider based on the chain type.

interface ExecuteTransactionParams {
  quote: Quote;
  // For EVM chains (Ethereum, BSC, Polygon, etc.)
  provider?: Provider | WalletClient; // Supports ethers.js BrowserProvider or viem WalletClient (including wagmi's getWalletClient)
  // For Solana chain
  walletAdapter?: WalletAdapter; // Compatible with @solana/web3.js and @solana/wallet-adapter-base wallets
  // For Cosmos-based chains
  cosmosClient?: any; // Compatible with @cosmjs/stargate and @cosmjs/cosmwasm-stargate clients
  // Optional callback for tracking transaction status
  onStatusUpdate?: (status: TransactionStatus, data?: any) => void;
  solanaRpcUrl?: string;
}

Examples for different chains:

// 1. EVM Chains Examples
// Using ethers.js BrowserProvider
import { BrowserProvider } from "ethers";
const provider = new BrowserProvider(window.ethereum);
const evmResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  provider: provider,
});

// Using viem WalletClient
import { createWalletClient, custom } from "viem";
const walletClient = createWalletClient({
  transport: custom(window.ethereum),
});
const evmViemResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  provider: walletClient,
});

// Using wagmi's getWalletClient
import { getWalletClient } from "@wagmi/core";
const wagmiClient = await getWalletClient();
const evmWagmiResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  provider: wagmiClient,
});

// 2. Solana Examples
// Using Phantom Wallet
import { PhantomWalletAdapter } from "@solana/wallet-adapter-phantom";
const phantomWallet = new PhantomWalletAdapter();
await phantomWallet.connect();
const solanaResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  walletAdapter: phantomWallet,
});

// Using Solana Wallet Adapter
import { useWallet } from "@solana/wallet-adapter-react";
const { wallet } = useWallet();
const solanaAdapterResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  walletAdapter: wallet,
});

// 3. Cosmos Examples
// Using CosmJS with Keplr
import { SigningStargateClient } from "@cosmjs/stargate";
import { SigningCosmWasmClient } from "@cosmjs/cosmwasm-stargate";

// For standard Cosmos chains
const getStargateClient = async () => {
  if (!window.keplr) throw new Error("Keplr not installed");
  await window.keplr.enable("cosmoshub-4"); // or your chain ID
  const offlineSigner = window.keplr.getOfflineSigner("cosmoshub-4");
  const client = await SigningStargateClient.connectWithSigner(
    "https://rpc.cosmos.network", // your RPC endpoint
    offlineSigner
  );
  return client;
};

const cosmosResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  cosmosClient: await getStargateClient(),
});

// For CosmWasm chains (e.g., Terra, Secret Network)
const getCosmWasmClient = async () => {
  if (!window.keplr) throw new Error("Keplr not installed");
  await window.keplr.enable("phoenix-1"); // or your chain ID
  const offlineSigner = window.keplr.getOfflineSigner("phoenix-1");
  const client = await SigningCosmWasmClient.connectWithSigner(
    "https://terra-rpc.example.com", // your RPC endpoint
    offlineSigner
  );
  return client;
};

const cosmWasmResult = await executeTransaction({
  quote: quotes.data.quotes[0],
  cosmosClient: await getCosmWasmClient(),
});

The provider, walletAdapter, and cosmosClient parameters are mutually exclusive - you should provide the appropriate one based on the chain you're interacting with:

  • For EVM chains: provide the provider parameter
  • For Solana: provide the walletAdapter parameter
  • For Cosmos chains: provide the cosmosClient parameter

The onStatusUpdate callback receives real-time updates about the transaction status and optional data payload.

Token and Chain Information

getTokens(chainId?)

Get a list of supported tokens, optionally filtered by chain ID.

interface TokensParams {
  chainId?: string;
}

//Example implementation
const tokens = await getTokens();// to fetch all tokens from all chains
const tokens = await getTokens("1");// to fetch all tokens from chain 1

//Example response
{
  "status": "success",
  "data":{
    "1":[
      {
    "networkType": "evm",
    "address": "0xeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeeee",
    "chainId": "1",
    "blockchain": "Ethereum",
    "decimals": 18,
    "name": "Ethereum",
    "symbol": "ETH",
    "image": "https://assets.coingecko.com/coins/images/279/standard/ethereum.png?1595348880",
    "lastPrice": 2703.62,
    "isEnabled": true,
    "isFlagged": false,
    "isNative": true,
    "isPopular": true
},
//other coins on chain 1
    ]
  }
}

getChains()

Get a list of supported blockchain networks.

interface Chain {
  id: string;
  name: string;
  networkType: "evm" | "sol" | "cosmos";
  nativeCurrency: {
    name: string;
    symbol: string;
    decimals: number;
  };
  blockExplorer: string;
  rpcUrls: string[];
}
//Example implementation
const chains = await getChains(); // to fetch all chains

//Example response
{
  "status": "success",
  "data": [
    {
  "chainId": "sol",
  "symbol": "sol",
  "name": "Solana",
  "networkType": "sol",
  "image": "https://assets.coingecko.com/coins/images/4128/large/solana.png?1696504756",
  "explorer": {
    "address": "https://solscan.io/account/{address}",
    "token": "https://solscan.io/token/{tokenAddress}",
    "txn": "https://solscan.io/tx/{txnHash}"
  },
  "isPopular": true,
  "tokenCount": 946,
  "isEnabled": true
},
//other supported chains
  ]
}

Error Handling

The SDK uses a custom BlockendError class for error handling. All errors will be instances of this class and include:

  • message: Human-readable error message
  • code: Error code for programmatic handling
  • data: Additional error context (if available)

Best Practices

  1. Always handle transaction status updates using the onStatusUpdate callback
  2. Implement proper error handling for failed transactions
  3. Use appropriate slippage tolerance for volatile tokens
  4. Cache chain and token information when possible
  5. Verify wallet connections before executing transactions

Network Support

  • EVM Chains (Ethereum, BSC, Polygon, etc.)
  • Solana
  • Cosmos-based chains
1.0.39

11 months ago

1.0.38

11 months ago

1.0.40

11 months ago

1.0.33

11 months ago

1.0.37

11 months ago

1.0.36

11 months ago

1.0.35

11 months ago

1.0.34

11 months ago

1.0.32

12 months ago

1.0.31

12 months ago

1.0.30

12 months ago

1.0.29

12 months ago

1.0.28

12 months ago

1.0.27

12 months ago

1.0.26

12 months ago

1.0.25

12 months ago

1.0.24

12 months ago

1.0.23

12 months ago

1.0.22

12 months ago

1.0.21

12 months ago

1.0.19

12 months ago

1.0.17

12 months ago

1.0.16

12 months ago

1.0.15

12 months ago

1.0.14

12 months ago

1.0.13

12 months ago

1.0.12

12 months ago

1.0.11

12 months ago

1.0.10

12 months ago

1.0.9

12 months ago

1.0.8

12 months ago

1.0.7

12 months ago

1.0.6

12 months ago

1.0.5

12 months ago

1.0.4

12 months ago

1.0.3

12 months ago

1.0.2

12 months ago

1.0.0

12 months ago