How to Automate Hyperliquid Trading with Python in 2026
Hyperliquid is the fastest-growing perpetuals DEX, processing $5B+ daily volume fully on-chain. Learn how to build automated trading bots using Hyperliquid's Python SDK and WebSocket API.
Builder of AI agents, crypto trading bots, and open-source automation tools. Sharing practical guides on how to build, deploy, and profit from AI and DeFi technology.
Why Hyperliquid Is Different
Hyperliquid is not just another DEX. It's a fully on-chain order book perpetuals exchange built on its own L1 blockchain (Hyperliquid L1). Everything that happens on a centralized exchange โ order placement, matching, liquidations โ happens on-chain with sub-second finality.
For bot builders, this means:
- CEX-like UX with on-chain transparency
- No KYC required for trading
- Full on-chain order book โ you can read every order
- Maker rebates of up to 0.02% (you get paid to provide liquidity)
- No gas fees for trading (network fees covered by protocol)
Setting Up Hyperliquid Python SDK
pip install hyperliquid-python-sdk
import eth_account
from eth_account.signers.local import LocalAccount
from hyperliquid.info import Info
from hyperliquid.exchange import Exchange
from hyperliquid.utils import constants
import json
# Setup account (Arbitrum EVM address)
private_key = "YOUR_PRIVATE_KEY"
account: LocalAccount = eth_account.Account.from_key(private_key)
print(f"Trading address: {account.address}")
# Connect to Hyperliquid
info = Info(constants.MAINNET_API_URL, skip_ws=True)
exchange = Exchange(account, constants.MAINNET_API_URL)
# Check account state
user_state = info.user_state(account.address)
print(f"USDC Balance: ${float(user_state['marginSummary']['accountValue']):.2f}")
Getting Market Data
def get_market_info(coin: str = "BTC") -> dict:
"""Get current price and market data for a coin"""
# Get all mid prices
all_mids = info.all_mids()
mid_price = float(all_mids.get(coin, 0))
# Get order book
l2_snapshot = info.l2_snapshot(coin)
best_bid = float(l2_snapshot['levels'][0][0]['px'])
best_ask = float(l2_snapshot['levels'][1][0]['px'])
spread = best_ask - best_bid
spread_bps = (spread / mid_price) * 10000
# Get recent trades
recent_trades = info.recent_trades(coin)
return {
'coin': coin,
'mid': mid_price,
'bid': best_bid,
'ask': best_ask,
'spread_bps': spread_bps,
'last_trade_side': recent_trades[0]['side'] if recent_trades else None,
}
# Example
btc_data = get_market_info("BTC")
print(f"BTC: ${btc_data['mid']:,.2f} | Spread: {btc_data['spread_bps']:.2f}bps")
Placing Orders
def place_limit_order(coin: str, is_buy: bool, sz: float, limit_px: float) -> dict:
"""Place a limit order on Hyperliquid"""
order_result = exchange.order(
coin,
is_buy,
sz, # Size in coin units
limit_px, # Limit price
{"limit": {"tif": "Gtc"}} # Good till cancelled
)
if order_result["status"] == "ok":
statuses = order_result["response"]["data"]["statuses"]
for status in statuses:
if "resting" in status:
oid = status["resting"]["oid"]
print(f"โ
Order placed: {'BUY' if is_buy else 'SELL'} {sz} {coin} @ ${limit_px:,.2f}")
print(f" Order ID: {oid}")
return {'success': True, 'oid': oid}
print(f"โ Order failed: {order_result}")
return {'success': False}
def place_market_order(coin: str, is_buy: bool, sz: float) -> dict:
"""Place a market order (uses aggressive limit with slippage)"""
mid = float(info.all_mids()[coin])
# Market order = limit at 3% slippage tolerance
slippage = 1.03 if is_buy else 0.97
limit_px = round(mid * slippage, 2)
order_result = exchange.order(
coin,
is_buy,
sz,
limit_px,
{"limit": {"tif": "Ioc"}} # Immediate or Cancel for market-like execution
)
return order_result
def close_position(coin: str) -> dict:
"""Close open position for a coin"""
user_state = info.user_state(account.address)
positions = user_state.get('assetPositions', [])
for pos in positions:
if pos['position']['coin'] == coin:
size = float(pos['position']['szi'])
if size != 0:
is_buy = size < 0 # Short position needs a buy to close
result = place_market_order(coin, is_buy, abs(size))
print(f"Closed {coin} position: {size} units")
return result
print(f"No position found for {coin}")
return {}
Building a Simple Trend-Following Bot
import time
import pandas as pd
def get_candles(coin: str, interval: str = "1h", lookback: int = 100) -> pd.DataFrame:
"""Fetch candlestick data from Hyperliquid"""
import time
end_time = int(time.time() * 1000)
start_time = end_time - (lookback * 3600 * 1000) # lookback hours ago
candles = info.candles_snapshot(coin, interval, start_time, end_time)
df = pd.DataFrame(candles, columns=['t', 'T', 'o', 'h', 'l', 'c', 'v', 'n'])
df = df.rename(columns={'o': 'open', 'h': 'high', 'l': 'low', 'c': 'close', 'v': 'volume'})
df[['open', 'high', 'low', 'close']] = df[['open', 'high', 'low', 'close']].astype(float)
return df
class HyperliquidTrendBot:
def __init__(self, coins: list[str], position_size_usd: float = 100):
self.coins = coins
self.position_size_usd = position_size_usd
self.open_positions = {}
def get_ema_signal(self, coin: str) -> str:
df = get_candles(coin, '1h', 100)
df['ema12'] = df['close'].ewm(span=12).mean()
df['ema26'] = df['close'].ewm(span=26).mean()
latest = df.iloc[-1]
prev = df.iloc[-2]
if prev['ema12'] <= prev['ema26'] and latest['ema12'] > latest['ema26']:
return 'BUY'
elif prev['ema12'] >= prev['ema26'] and latest['ema12'] < latest['ema26']:
return 'SELL'
elif latest['ema12'] > latest['ema26']:
return 'HOLD_LONG'
else:
return 'HOLD_SHORT'
def run_cycle(self):
for coin in self.coins:
signal = self.get_ema_signal(coin)
mid = float(info.all_mids()[coin])
size = self.position_size_usd / mid
in_position = coin in self.open_positions
if signal == 'BUY' and not in_position:
result = place_market_order(coin, True, round(size, 4))
if result.get('status') == 'ok':
self.open_positions[coin] = {'side': 'long', 'entry': mid}
print(f"๐ OPENED LONG {coin} @ ${mid:,.2f}")
elif signal == 'SELL' and in_position and self.open_positions[coin]['side'] == 'long':
close_position(coin)
del self.open_positions[coin]
print(f"๐ CLOSED LONG {coin} @ ${mid:,.2f}")
# Run bot
bot = HyperliquidTrendBot(['BTC', 'ETH', 'SOL'])
while True:
bot.run_cycle()
time.sleep(3600) # Check every hour
Real-Time WebSocket Feed
from hyperliquid.info import Info
def handle_price_update(data):
"""Handle real-time price updates"""
print(f"Price update: {data}")
# Subscribe to live data
info_ws = Info(constants.MAINNET_API_URL)
info_ws.subscribe(
{"type": "allMids"},
handle_price_update
)
Why Hyperliquid for Bots in 2026
- No gas fees: Execute thousands of orders without gas costs
- Maker rebates: Earn -0.02% on limit orders (unusual for DEX)
- On-chain transparency: All data publicly readable โ no proprietary APIs needed
- $5B+ daily volume: Deep enough liquidity for meaningful position sizes
- No withdrawal restrictions: It's your keys, your crypto
Hyperliquid represents the best of both worlds โ CEX performance on a decentralized protocol. For bot builders willing to learn the SDK, it's one of the most exciting trading environments available.
Tagged in
Related Articles
Crypto Bot Risk Management: The 10 Rules That Separate Winners From Losers
7 min read
Crypto BotsHow to Build a Self-Healing Trading Bot That Fixes Its Own Errors
5 min read
Crypto BotsPump.fun and Solana Meme Coin Bots: How to Automate the Hottest Trend
5 min read
Crypto BotsHow to Build a Crypto Portfolio Auto-Rebalancing Bot
5 min read