DEV Community

dead1786
dead1786

Posted on

How to Build a Funding Rate Arbitrage Bot with Python

How to Build a Funding Rate Arbitrage Bot with Python

A step-by-step guide to earning passive income from cryptocurrency funding rates — with zero directional risk.


What is Funding Rate Arbitrage?

Perpetual futures contracts have no expiry date. To keep their price aligned with spot, exchanges use a funding rate — a fee paid between longs and shorts every 8 hours.

When the market is bullish (most of the time), longs pay shorts. This creates a structural opportunity: go long on spot, short on perpetual, and collect the funding rate with zero price risk.

This is called delta-neutral funding rate arbitrage, and it's one of the lowest-risk strategies in crypto.

How Much Can You Earn?

Based on 2024-2025 data:

Asset Avg 8h Rate Annual Return
BTC 0.01% ~11%
ETH 0.008% ~8.7%
Altcoins 0.02-0.05% ~22-55%

That's 10-15% annually on a delta-neutral position — significantly better than most savings accounts, with much lower risk than directional trading.

The Strategy

  1. Scan all perpetual contracts for positive funding rates
  2. Buy spot (e.g., 1 BTC on spot market)
  3. Short perpetual (e.g., short 1 BTC perpetual contract)
  4. Collect funding rate every 8 hours
  5. Rotate when funding rate turns negative — close position, find the next best coin

Your total exposure is zero — if BTC goes up $1,000, your spot gains $1,000 and your short loses $1,000. Net effect: $0. You only care about the funding rate.

Building the Bot

Prerequisites

pip install ccxt
Enter fullscreen mode Exit fullscreen mode

We'll use ccxt — a unified API for 100+ cryptocurrency exchanges.

Step 1: Scan Funding Rates

import ccxt

exchange = ccxt.okx({
    'apiKey': 'YOUR_KEY',
    'secret': 'YOUR_SECRET',
    'password': 'YOUR_PASSPHRASE',
})

markets = exchange.load_markets()
perp_symbols = [
    s for s in markets
    if markets[s]['swap'] and markets[s]['quote'] == 'USDT'
]

rates = []
for symbol in perp_symbols:
    info = exchange.fetch_funding_rate(symbol)
    rate = info['fundingRate']
    if rate and rate > 0.0001:  # > 0.01%
        rates.append({
            'symbol': symbol,
            'rate': rate,
            'annual': rate * 3 * 365,
        })

# Sort by rate descending
rates.sort(key=lambda x: x['rate'], reverse=True)
for r in rates[:10]:
    print(f"{r['symbol']}: {r['rate']*100:.4f}% per 8h ({r['annual']*100:.1f}% annual)")
Enter fullscreen mode Exit fullscreen mode

Step 2: Open Delta-Neutral Position

def open_position(exchange, symbol, usdt_amount):
    spot_symbol = symbol.split(':')[0]  # BTC/USDT:USDT -> BTC/USDT

    # Get price
    ticker = exchange.fetch_ticker(spot_symbol)
    price = ticker['last']
    amount = usdt_amount / price

    # Round to exchange precision
    amount = float(exchange.amount_to_precision(symbol, amount))

    # Set leverage to 1x (no leverage!)
    exchange.set_leverage(1, symbol)

    # Buy spot
    exchange.create_market_buy_order(spot_symbol, amount)

    # Short perpetual
    exchange.create_market_sell_order(symbol, amount)

    print(f"Opened: long {amount} {spot_symbol} + short {amount} {symbol}")
Enter fullscreen mode Exit fullscreen mode

Step 3: Monitor and Rotate

def check_and_rotate(exchange, positions):
    for symbol, info in positions.items():
        rate = exchange.fetch_funding_rate(symbol)['fundingRate']

        if rate < -0.0001:  # Negative rate threshold
            # Close both positions
            close_position(exchange, symbol, info['amount'])

            # Find new best rate
            new_rates = scan_funding_rates(exchange)
            if new_rates:
                open_position(exchange, new_rates[0]['symbol'], info['usdt_value'])
Enter fullscreen mode Exit fullscreen mode

Step 4: Risk Management

Key rules:

  • Never use leverage — 1x only
  • Keep 20% reserve — don't deploy all capital
  • Max 30-40% per coin — diversify across 2-3 coins
  • Close on sustained negative rates — 2 consecutive negative periods = close
  • Monitor margin ratio — alert if below 300%

What About Fees?

Each open+close cycle costs ~0.20-0.28% in trading fees. This means:

  • Only open positions when funding rate > 0.01% per 8h
  • Don't rotate too frequently (wait for 2+ negative periods before closing)
  • Higher-rate coins are more profitable after fees

Running It 24/7

The bot runs as a scheduled task, checking every 8 hours:

while True:
    check_and_rotate(exchange, state['positions'])
    time.sleep(8 * 3600)  # Check every 8 hours
Enter fullscreen mode Exit fullscreen mode

Add Telegram notifications for:

  • New positions opened
  • Positions closed (with PnL)
  • Negative funding rate alerts
  • Daily summary report

Results

With $5,000 deployed across 2-3 coins:

  • Conservative (BTC/ETH only): ~$40-60/month
  • Aggressive (including altcoins): ~$60-100/month
  • Bull market peaks: 2-3x these numbers

It's not get-rich-quick money, but it's genuinely passive — the bot runs itself, you just top up capital and collect.

Get the Code

Full source code and setup instructions: GitHub - funding-arb

Follow our live signals: Telegram - @PERMAFROSTK


Built with Permafrost AI — an open-source AI brain framework.

Top comments (0)