Skip to main content

Requirements

  • Node.js 18 or higher
  • npm

Installation

1

Install the dependency

The SDK uses eventsource-client for SSE streaming with auto-reconnect and async iterator support.
npm install eventsource-client
2

Copy the SDK files

Download polyedge.js and parser_compact_tx.js from the PolyEdge examples repository and copy them into your project directory.

Instantiation

Import PolyEdgeClient and pass your API key. The base URL defaults to https://api.polyedge.dev/v1.
import PolyEdgeClient from './polyedge.js';

const client = new PolyEdgeClient('your_api_key_here');
You can also pass a custom base URL as the second argument:
const client = new PolyEdgeClient('your_api_key_here', 'https://api.polyedge.dev/v1');
Your API key is sent on every request via the X-PolyEdge-Key header.

Methods

Retrieve the trader leaderboard, optionally filtered and sorted.
const data = await client.getLeaderboard(params);
Parameters — all optional:
ParameterTypeDescription
limitnumberNumber of results to return. Default: 50, max: 100.
offsetnumberPagination offset. Default: 0.
time_framestring'1H', '4H', '1D', '3D', '7D', '30D'. Default: '30D'.
sort_bystring'pnl', 'roi', 'win_rate', 'market_count'. Default: 'pnl'.
tagstringFilter by market tag, e.g. 'crypto', 'sports'.
min_win_ratenumberMinimum win rate (0–100).
max_win_ratenumberMaximum win rate (0–100).
min_roinumberMinimum ROI percentage.
max_roinumberMaximum ROI percentage.
last_active_hoursnumberOnly include traders active in the last N hours.
min_market_countnumberMinimum number of markets traded.
max_market_countnumberMaximum number of markets traded.
Returns a Promise<Object>.
Get a trader’s detailed profile including tags, stats, and metadata.
const data = await client.getTraderProfile('0xabc…');
ParameterTypeDescription
addressstringThe EVM wallet address of the trader.
Returns a Promise<Object>.
Retrieve a trader’s trading history aggregated by market.
const data = await client.getTraderMarkets('0xabc…', params);
ParameterTypeDescription
addressstringThe EVM wallet address of the trader.
limitnumberNumber of markets to return. Default: 20, max: 100.
offsetnumberPagination offset. Default: 0.
is_activebooleanFilter by active (unresolved) markets only.
Returns a Promise<Object>.
Retrieve a specific trader’s order history within a specific market.
const data = await client.getTraderMarketOrders('0xabc…', 12345);
ParameterTypeDescription
addressstringThe EVM wallet address of the trader.
marketIdstring | numberThe specific market ID.
Returns a Promise<Object>.
Retrieve detailed information about a specific market.
const data = await client.getMarketDetail(12345);
ParameterTypeDescription
marketIdstring | numberThe unique numeric ID of the market.
Returns a Promise<Object>.
Subscribe to live mempool orders via SSE. Returns an async generator that yields parsed order objects.
for await (const order of client.streamOrders(params)) {
  console.log(order);
}
Break out of the loop at any time — the underlying SSE connection is closed automatically in the generator’s finally block.Parameters — all optional:
ParameterTypeDescription
tradersstringComma-separated list of trader addresses to follow.
tagsstringComma-separated list of market tags to filter by.
seriesstringComma-separated list of series slugs.
min_usdcnumberMinimum USDC trade size.
max_usdcnumberMaximum USDC trade size.
min_sharesnumberMinimum shares amount.
max_sharesnumberMaximum shares amount.
min_pricenumberMinimum price (0–100).
max_pricenumberMaximum price (0–100).
formatstringSet to 'json' for structured JSON. Omit for compact array format (recommended).
Returns AsyncGenerator<Object, void, unknown>.
When format is omitted, each yielded value is the output of parseCompactTx — a fully structured JavaScript object. See Compact format parsing below.

Compact format parsing

By default, streamOrders receives events in a compact array format optimised for low bandwidth. The parser_compact_tx.js utility converts each raw array into a structured object before yielding it. The parsed object has this shape:
{
  txHash: string,
  timestamp: string,
  market: {
    id: string,
    question: string,
    slug: string,
    start_date: string,
    end_date: string,
    icon: string,
    neg_risk: boolean,
    event_slug: string,
    series_slug: string,
    tags: string[],
    outcome_1: string,
    outcome_2: string,
    group_item_title: string,
    event_title: string,
    event_icon: string
  },
  takerOrder: {
    side: string,       // 'BUY' or 'SELL'
    trader: {
      address: string,
      name: string,
      x_username: string,
      profile_image: string,
      profile_created_at: string
    },
    outcome: string,
    tokenId: string,
    usdc: string,       // raw 1e6 format
    shares: string,     // raw 1e6 format
    fee: string,
    feeRateBps: string
  },
  makerOrders: [ /* same shape as takerOrder */ ]
}
USDC and shares values are returned as raw strings in 1e6 format. Divide by 1e6 to convert to human-readable amounts: Number(order.takerOrder.usdc) / 1e6.
If you prefer fully structured JSON from the API rather than parsing compact arrays yourself, pass format: 'json' to streamOrders — the raw response is yielded directly without calling the parser.

Complete example

The following example exercises every method in the SDK, then opens the SSE stream and prints the first three events.
import PolyEdgeClient from './polyedge.js';

const API_KEY = 'your_api_key_here';
const client = new PolyEdgeClient(API_KEY);

function formatAmount(rawStr) {
  if (!rawStr) return "0.00";
  const num = Number(rawStr) / 1e6;
  return num.toLocaleString(undefined, { minimumFractionDigits: 2, maximumFractionDigits: 2 });
}

async function main() {
  // 1. Get leaderboard — top 3 traders by PNL over the last 7 days
  const leaderboard = await client.getLeaderboard({ limit: 3, sort_by: 'pnl', time_frame: '7D' });
  let traderAddress = leaderboard.traders[0].profile.address;
  leaderboard.traders.forEach((t) => {
    console.log(`${t.rank}. ${t.profile.name} (${t.profile.address})`);
    console.log(`   PNL: $${formatAmount(t.total_pnl)} | ROI: ${t.roi}% | Win Rate: ${t.win_rate}%`);
  });

  // 2. Get trader profile
  const profileResponse = await client.getTraderProfile(traderAddress);
  const p = profileResponse.profile;
  console.log(`Name: ${p.name} | Address: ${p.address}`);

  // 3. Get trader markets
  const marketsResponse = await client.getTraderMarkets(traderAddress, { limit: 1 });
  const hm = marketsResponse.history[0];
  const marketId = hm.market.id;
  console.log(`Market: ${hm.market.question} (ID: ${marketId})`);

  // 4. Get trader market orders
  const ordersResponse = await client.getTraderMarketOrders(traderAddress, marketId);
  ordersResponse.orders.slice(0, 3).forEach((o, i) => {
    const price = (Number(o.price) / 1e6).toFixed(3);
    console.log(`[Order ${i + 1}] ${o.side} ${o.outcome} @ $${price}`);
  });

  // 5. Get market detail
  const marketDetail = await client.getMarketDetail(marketId);
  const md = marketDetail.market;
  console.log(`Question: ${md.question}`);
  console.log(`Total Volume: $${formatAmount(marketDetail.total_volume)}`);

  // 6. Stream live orders — exit after 3 events
  let eventCount = 0;
  for await (const order of client.streamOrders()) {
    eventCount++;
    const taker = order.takerOrder;
    const price = taker.shares !== "0"
      ? (Number(taker.usdc) / Number(taker.shares)).toFixed(3)
      : "0.000";

    console.log(`[Event #${eventCount}] ${order.timestamp}`);
    console.log(`  Market: ${order.market.question} (${order.market.id})`);
    console.log(`  Trader: ${taker.trader?.address ?? 'Unknown'}`);
    console.log(`  Action: ${taker.side} ${taker.outcome} @ ~$${price}`);
    console.log(`  Size: ${formatAmount(taker.shares)} shares ($${formatAmount(taker.usdc)})`);

    if (eventCount >= 3) break;
  }
}

main().catch(console.error);