> ## Documentation Index
> Fetch the complete documentation index at: https://docs.houdiniswap.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Split

> Create and manage multiple swaps in a single batch with Split — supports CEX and anonymous routing

## Overview

Split lets partners create multiple independent swap orders in a single API call, grouped under a shared `multiId`. Each order is individually priced and executed, but they can all be tracked together via a single status endpoint.

> [!NOTE]
>
> Split was previously called Multi-Swap. The API keeps the original names: endpoints live under `/exchanges/multi` and orders are grouped by `multiId`.

> [!NOTE]
>
> **Best For**: Platforms distributing payouts to multiple recipients, batch airdrop tools, or any use case requiring several simultaneous swaps from the same source token.

> [!WARNING]
>
> Split supports **CEX and anonymous routing only** — DEX orders are not supported. Each order in the batch is created using the standard `from`/`to`/`amount`/`addressTo` fields — no `quoteId` is needed.

> [!NOTE]
>
> **Fixed rate** is supported per order — set `fixed: true` on the order and include a `refundAddress`. **Reverse quotes are not**: there is no `amountType` field on a batch order, so every order is quoted from the send amount. See [Fixed Rate & Reverse Quote](https://docs.houdiniswap.com/developer-hub/swap-flows/fixed-rate-swap.md).

## Key Features

> [card] Single Request, Multiple Orders
>
> Create up to many orders in one request, all linked by a shared `multiId`

> [card] CEX & Anonymous Routing
>
> Supports standard (CEX) and private (anonymous) routing per order

> [card] Per-Order Status
>
> Track all orders in the group with a single `GET /exchanges/multi/{multiId}` call

> [card] Solana Batch Transaction
>
> Fund all deposit addresses in the group with a single signed transaction via `GET /exchanges/multi/{multiId}/tx`. Up to 10 orders per transaction.

## How It Works

**1. Get Tokens**

Fetch CEX-supported tokens and note each token's `id`.

**2. Create a Split**

Call `POST /exchanges/multi` with an array of orders. Each order specifies token IDs, amount, destination address, and optional routing flags.

**3. Monitor Status**

Poll `GET /exchanges/multi/{multiId}` to track all orders in the group together.

**4. Generate Batch Transaction (Solana only)**

For Solana source tokens, call `GET /exchanges/multi/{multiId}/tx?sender={senderAddress}` to get pre-built batched transactions. Each transaction covers up to 10 deposit addresses — if your batch has more than 10 orders, the response returns multiple transactions to submit separately.

## Integration Guide

### Step 1: Get Tokens

Use token IDs (not symbols) when building your orders. Fetch and cache the token list from `/tokens`:

> [tab] Bulk Fetch + Cache
>
> > [!WARNING]
> >
> > Cache the token list in your backend database. Never call `/tokens` on every user request — load on server startup or via a scheduled job and refresh every 24 hours.
>
> ```javascript JavaScript theme={null}
> async function fetchAllCexTokens() {
>   let page = 1;
>   let allTokens = [];
>
>   while (true) {
>     const response = await fetch(
>       `https://api-partner.houdiniswap.com/v2/tokens?hasCex=true&pageSize=20&page=${page}`,
>       {
>         headers: { 'Authorization': `${API_KEY}:${API_SECRET}` }
>       }
>     );
>
>     const { tokens, totalPages } = await response.json();
>     allTokens = allTokens.concat(tokens);
>
>     if (page >= totalPages) break;
>     page++;
>   }
>
>   return allTokens; // save to your DB
> }
> ```
>
> ```bash cURL theme={null}
> curl -X GET "https://api-partner.houdiniswap.com/v2/tokens?hasCex=true&pageSize=20&page=1" \
>   -H "Authorization: your_api_key:your_api_secret"
> ```

> [tab] Token Search
>
> ```javascript JavaScript theme={null}
> async function searchTokens(query) {
>   const params = new URLSearchParams({
>     term: query,
>     hasCex: 'true',
>     pageSize: '20',
>     page: '1'
>   });
>
>   const response = await fetch(
>     `https://api-partner.houdiniswap.com/v2/tokens?${params}`,
>     { headers: { 'Authorization': `${API_KEY}:${API_SECRET}` } }
>   );
>
>   const { tokens } = await response.json();
>   return tokens;
> }
> ```
>
> ```bash cURL theme={null}
> curl -X GET "https://api-partner.houdiniswap.com/v2/tokens?term=solana&hasCex=true&pageSize=20&page=1" \
>   -H "Authorization: your_api_key:your_api_secret"
> ```

### Step 2: Create a Split

Call `POST /exchanges/multi` with an `orders` array. Each order is independent — different token pairs, amounts, and destination addresses are all supported in the same batch. Set `anonymous: true` on any order to enable private routing for that order.

```javascript JavaScript theme={null}
const response = await fetch('https://api-partner.houdiniswap.com/v2/exchanges/multi', {
  method: 'POST',
  headers: {
    'Authorization': `${API_KEY}:${API_SECRET}`,
    'Content-Type': 'application/json'
  },
  body: JSON.stringify({
    orders: [
      {
        from: '6689b73ec90e45f3b3e51577',       // SOL token id
        to:   '6689b73ec90e45f3b3e51566',       // ETH token id
        amount: 10,
        addressTo: '0x742d35Cc6634C0532925a3b844Bc454e4438f44e'
      },
      {
        from: '6689b73ec90e45f3b3e51577',       // SOL token id
        to:   '6689b73ec90e45f3b3e51558',       // USDC token id
        amount: 25,
        addressTo: '0xABcD1234abcd1234ABCD1234abcd1234ABCD1234',
        anonymous: true                          // enable private routing for this order
      },
      {
        from: '6689b73ec90e45f3b3e51577',       // SOL token id
        to:   '6689b73ec90e45f3b3e51577',       // SOL token id
        amount: 5,
        addressTo: 'RecipientSolanaAddressHere1111111111111111',
        anonymous: true,
        useXmr: true                            // force XMR as anonymous bridge
      }
    ]
  })
});

const result = await response.json();
console.log('Multi ID:', result.multiId);       // shared group identifier

result.orders.forEach((item, i) => {
  if (item.error) {
    console.error(`Order ${i} failed:`, item.error.message, item.error.code);
  } else {
    console.log(`Order ${i} ID:`, item.order.houdiniId);
    console.log(`  Deposit to:`, item.order.depositAddress);
    console.log(`  Send:`, item.order.inAmount, item.order.inSymbol);
    console.log(`  Expires:`, item.order.expires);
  }
});
```

```bash cURL theme={null}
curl -X POST "https://api-partner.houdiniswap.com/v2/exchanges/multi" \
  -H "Authorization: your_api_key:your_api_secret" \
  -H "Content-Type: application/json" \
  -d '{
    "orders": [
      {
        "from": "6689b73ec90e45f3b3e51577",
        "to": "6689b73ec90e45f3b3e51566",
        "amount": 10,
        "addressTo": "0x742d35Cc6634C0532925a3b844Bc454e4438f44e"
      },
      {
        "from": "6689b73ec90e45f3b3e51577",
        "to": "6689b73ec90e45f3b3e51558",
        "amount": 25,
        "addressTo": "0xABcD1234abcd1234ABCD1234abcd1234ABCD1234",
        "anonymous": true
      }
    ]
  }'
```

### Create Split Response

```json theme={null}
{
  "multiId": "multi_a1b2c3d4e5f6",
  "orders": [
    {
      "order": {
        "houdiniId": "iBQMRX3xvXrFMGQi71ogo9",
        "multiId": "multi_a1b2c3d4e5f6",
        "created": "2025-12-25T06:13:46.673Z",
        "expires": "2025-12-25T06:43:46.673Z",
        "depositAddress": "SolDepositAddress111111111111111111111111111",
        "receiverAddress": "0x742d35Cc6634C0532925a3b844Bc454e4438f44e",
        "anonymous": false,
        "statusLabel": "NEW",
        "inAmount": 10,
        "inSymbol": "SOL",
        "outAmount": 0.0412,
        "outSymbol": "ETH",
        "eta": 15
      }
    },
    {
      "order": {
        "houdiniId": "kJRNSY4ywYsGNHRmO82ph0",
        "multiId": "multi_a1b2c3d4e5f6",
        "created": "2025-12-25T06:13:46.673Z",
        "expires": "2025-12-25T06:43:46.673Z",
        "depositAddress": "SolDepositAddress222222222222222222222222222",
        "receiverAddress": "0xABcD1234abcd1234ABCD1234abcd1234ABCD1234",
        "anonymous": true,
        "statusLabel": "NEW",
        "inAmount": 25,
        "inSymbol": "SOL",
        "outAmount": 2431.75,
        "outSymbol": "USDC",
        "eta": 35
      }
    },
    {
      "error": {
        "message": "Token pair not available",
        "code": "PAIR_UNAVAILABLE"
      }
    }
  ]
}
```

**Key Response Fields:**

* `multiId`: Shared identifier for the batch — use this to poll status for all orders
* `orders[].order`: Full order object for successfully created orders (see [Order Lifecycle](https://docs.houdiniswap.com/developer-hub/core-concepts/order-lifecycle.md))
* `orders[].error`: Per-order error if creation failed — the rest of the batch is unaffected
* `depositAddress`: Each order has its own unique deposit address
* `statusLabel`: Starts as `NEW` — orders are initialized asynchronously

> [!WARNING]
>
> Orders are created asynchronously. Some orders may return with `statusLabel: "INITIALIZING"` immediately after creation. Poll the Split status endpoint to confirm all orders reach `NEW` before proceeding.

### Order Fields Reference

| Field | Description |
| - | - |
| `from` | Token ID of input token (24-char MongoDB ObjectId) |
| `to` | Token ID of output token |
| `amount` | Input swap amount |
| `addressTo` | Destination wallet address for output funds |
| `anonymous` | `true` to enable private multi-hop routing |
| `destinationTag` | Memo/tag for chains that require it (e.g. XRP, XLM) — max 64 chars |
| `useXmr` | `true` to force XMR as the anonymous bridge layer |
| `walletInfo` | Additional wallet metadata — max 256 chars |
| `fixed` | `true` to lock the rate for this order. Requires `refundAddress` |
| `refundAddress` | Source-chain wallet for refunds. **Required when `fixed` is `true`** |
| `refundExtraId` | Memo/tag for `refundAddress` on memo-bearing chains (XRP, Stellar, TON) — max 64 chars |

### Step 3: Monitor Split Status

Poll `GET /exchanges/multi/{multiId}` to retrieve status for all orders in the group at once:

```javascript JavaScript theme={null}
async function pollSplitStatus(multiId) {
  const response = await fetch(
    `https://api-partner.houdiniswap.com/v2/exchanges/multi/${multiId}`,
    {
      headers: { 'Authorization': `${API_KEY}:${API_SECRET}` }
    }
  );

  const { orders } = await response.json();

  orders.forEach(order => {
    console.log(`${order.houdiniId}: ${order.statusLabel}`);
    // statusLabel values:
    // INITIALIZING  — order being set up
    // NEW / WAITING — awaiting deposit
    // CONFIRMING    — deposit detected, awaiting confirmations
    // EXCHANGING    — CEX is processing
    // ANONYMIZING   — routing through privacy layer (anonymous orders only)
    // FINISHED      — complete, funds sent
    // EXPIRED       — deposit not received in time
    // FAILED        — swap failed
    // REFUNDED      — funds returned to sender
  });

  const allDone = orders.every(o =>
    ['FINISHED', 'FAILED', 'EXPIRED', 'REFUNDED'].includes(o.statusLabel)
  );

  return { orders, allDone };
}

// Poll every 30 seconds until all orders are terminal
const interval = setInterval(async () => {
  const { orders, allDone } = await pollSplitStatus('multi_a1b2c3d4e5f6');
  if (allDone) clearInterval(interval);
}, 30_000);
```

```bash cURL theme={null}
curl -X GET "https://api-partner.houdiniswap.com/v2/exchanges/multi/multi_a1b2c3d4e5f6" \
  -H "Authorization: your_api_key:your_api_secret"
```

### Split Status Response

```json theme={null}
{
  "multiId": "multi_a1b2c3d4e5f6",
  "orders": [
    {
      "houdiniId": "iBQMRX3xvXrFMGQi71ogo9",
      "multiId": "multi_a1b2c3d4e5f6",
      "statusLabel": "WAITING",
      "displayStatus": "WAITING_FOR_DEPOSIT",
      "inAmount": 10,
      "inSymbol": "SOL",
      "outAmount": 0.0412,
      "outSymbol": "ETH",
      "depositAddress": "SolDepositAddress111111111111111111111111111",
      "receiverAddress": "0x742d35Cc6634C0532925a3b844Bc454e4438f44e",
      "eta": 15,
      "created": "2025-12-25T06:13:46.673Z",
      "modified": "2025-12-25T06:13:50.001Z"
    },
    {
      "houdiniId": "kJRNSY4ywYsGNHRmO82ph0",
      "multiId": "multi_a1b2c3d4e5f6",
      "statusLabel": "EXCHANGING",
      "displayStatus": "DEPOSIT_DETECTED",
      "inAmount": 25,
      "inSymbol": "SOL",
      "outAmount": 2431.75,
      "outSymbol": "USDC",
      "depositAddress": "SolDepositAddress222222222222222222222222222",
      "receiverAddress": "0xABcD1234abcd1234ABCD1234abcd1234ABCD1234",
      "eta": 20,
      "created": "2025-12-25T06:13:46.673Z",
      "modified": "2025-12-25T06:20:12.443Z"
    }
  ]
}
```

> [!TIP]
>
> Poll every 30 seconds. Track each order's `statusLabel` independently — orders in the same batch progress at different rates. For a full list of statuses and transitions, see the [Order Lifecycle](https://docs.houdiniswap.com/developer-hub/core-concepts/order-lifecycle.md) guide.

### Step 4: Generate Solana Batch Transaction

For Solana source tokens, you can fund all deposit addresses with pre-built transactions instead of sending separate transfers. Call `GET /exchanges/multi/{multiId}/tx?sender={senderAddress}`:

```javascript JavaScript theme={null}
const senderAddress = 'YourSolanaWalletAddressHere111111111111111111';

const response = await fetch(
  `https://api-partner.houdiniswap.com/v2/exchanges/multi/${multiId}/tx?sender=${senderAddress}`,
  {
    headers: { 'Authorization': `${API_KEY}:${API_SECRET}` }
  }
);

const { chain, transactions } = await response.json();

console.log('Chain:', chain); // "solana"
console.log('Transactions to submit:', transactions.length);

for (const batch of transactions) {
  console.log('Covers order IDs:', batch.houdiniIds); // up to 10 per batch

  // batch.txData.data is a base64-encoded serialized Solana transaction
  const txBytes = Buffer.from(batch.txData.data, 'base64');

  const { Transaction, Connection, clusterApiUrl } = require('@solana/web3.js');
  const connection = new Connection(clusterApiUrl('mainnet-beta'));
  const tx = Transaction.from(txBytes);

  // Sign with your keypair or wallet adapter, then submit
  const signature = await connection.sendRawTransaction(tx.serialize());
  console.log('Submitted batch tx:', signature);
}
```

```bash cURL theme={null}
curl -X GET "https://api-partner.houdiniswap.com/v2/exchanges/multi/multi_a1b2c3d4e5f6/tx?sender=YourSolanaWalletAddressHere111111111111111111" \
  -H "Authorization: your_api_key:your_api_secret"
```

### Batch Transaction Response

```json theme={null}
{
  "multiId": "multi_a1b2c3d4e5f6",
  "chain": "solana",
  "transactions": [
    {
      "houdiniIds": [
        "iBQMRX3xvXrFMGQi71ogo9",
        "kJRNSY4ywYsGNHRmO82ph0"
      ],
      "txData": {
        "data": "AQAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABAAEDa2V5..."
      }
    }
  ]
}
```

**Key Fields:**

* `chain`: Always `"solana"` — only Solana is supported for batch transactions
* `transactions`: Array of `TxBatch` objects — each covers up to 10 orders. Batches with more than 10 orders return multiple items; submit each transaction separately
* `houdiniIds`: The order IDs funded by this specific transaction
* `txData.data`: Base64-encoded serialized Solana transaction — deserialize, sign, and submit

> [!WARNING]
>
> Batch transactions are only supported when all orders in the Split share the same **Solana** source token.

## Best Practices

> [accordion] Handle Per-Order Errors
>
> `POST /exchanges/multi` returns a partial success response — some orders may fail while others succeed. Always check each item in `orders[]` for an `error` field before proceeding, and handle failed orders independently without canceling the batch.

> [accordion] Wait for INITIALIZING to Resolve
>
> Orders returned with `statusLabel: "INITIALIZING"` are still being set up. Poll `GET /exchanges/multi/{multiId}` until all orders reach `NEW` or `WAITING` before sending deposits.

> [accordion] Expiry Windows
>
> Each order has its own `expires` timestamp (typically 30 minutes from creation). For Solana batch transactions, sign and submit all transactions promptly — if any order expires before confirmation, that order will not be funded.

> [accordion] Submitting Multiple Batch Transactions
>
> If your Split has more than 10 Solana orders, the `transactions` array will contain multiple items. Submit each transaction independently — they are not dependent on each other and can be submitted in parallel.

> [accordion] Security
>
> Never expose API keys in frontend code. Validate all `addressTo` values before submission. Store `multiId` and each `houdiniId` for audit trails and support lookups.

## Common Issues

> [accordion] Some Orders Return Errors
>
> **Cause**: Individual orders can fail validation (unsupported pair, amount out of range, invalid address) while the rest of the batch succeeds.
>
> **Solution**: Check each `orders[].error` in the response. Re-submit failed orders individually with corrected parameters. The valid orders in the batch are unaffected.

> [accordion] Batch Transaction Not Available
>
> **Cause**: Batch transactions require all orders to share the same Solana source token.
>
> **Solution**: Use separate individual deposits for non-Solana source tokens.

> [accordion] Order Expired Before Deposit
>
> **Cause**: The 30-minute deposit window elapsed before funds were sent.
>
> **Solution**: Re-create the expired orders in a new Split. Deposit promptly after creation.

> [accordion] Orders Stuck at INITIALIZING
>
> **Cause**: Order setup is asynchronous and may take a few seconds.
>
> **Solution**: Poll `GET /exchanges/multi/{multiId}` every 5–10 seconds until all orders leave the `INITIALIZING` state before proceeding.

> [accordion] Anonymous Order Taking Longer
>
> **Cause**: Private routing passes through an additional `ANONYMIZING` stage.
>
> **Solution**: This is expected. Monitor `statusLabel` per order — anonymous orders typically complete in 15–45 minutes.

## Next Steps

> [card] [Standard Swap](https://docs.houdiniswap.com/developer-hub/swap-flows/standard-swap.md)
>
> Single-order CEX swaps

> [card] [Private Swap](https://docs.houdiniswap.com/developer-hub/swap-flows/private-swap.md)
>
> Multi-hop anonymous swaps

> [card] [Order Lifecycle](https://docs.houdiniswap.com/developer-hub/core-concepts/order-lifecycle.md)
>
> Understand all order statuses

> [card] [Error Handling](https://docs.houdiniswap.com/developer-hub/troubleshooting/errors.md)
>
> Handle errors and edge cases


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.