hpyhacking/peatio · error · RuntimeError

2002

2002

Error message

Market is not deep enough

What it means

Peatio error surfaced as APIv2 code 2002 (HTTP 400), "Failed to create order. Reason: Market is not deep enough". For a MARKET order, Ordering#submit computes locked funds via compute_locked, which calls estimate_required_funds (app/models/order.rb) to walk the opposite side of the shared order book — Global[currency].asks for a market buy (OrderBid), .bids for a market sell (OrderAsk) — consuming level volumes until the requested volume is covered. If the entire book holds less volume than requested, expected_volume never reaches zero and the method raises RuntimeError "Market is not deep enough", which the API helper rescues into CreateOrderError.

Source

Thrown at app/models/order.rb:153

  FUSE = '0.9'.to_d
  def estimate_required_funds(price_levels)
    required_funds = Account::ZERO
    expected_volume = volume

    start_from, _ = price_levels.first
    filled_at     = start_from

    until expected_volume.zero? || price_levels.empty?
      level_price, level_volume = price_levels.shift
      filled_at = level_price

      v = [expected_volume, level_volume].min
      required_funds += yield level_price, v
      expected_volume -= v
    end

    raise "Market is not deep enough" unless expected_volume.zero?
    raise "Volume too large" if (filled_at-start_from).abs/start_from > FUSE

    required_funds
  end

end

View on GitHub (pinned to dab8641137)

Solutions

  1. Fetch the depth first (GET /api/v2/order_book) and cap market-order volume below the counter side's total volume.
  2. Split the market order into smaller chunks spaced over time so the book can refill.
  3. Use ord_type=limit with an acceptable price — limit orders lock price*volume and never run the depth estimate.
  4. If you operate the exchange, verify the matching daemon has rebuilt its order books after a restart before accepting market orders.

Example fix

# before
post '/orders', market: 'btcusd', side: 'buy', ord_type: 'market', volume: '100'

# after: cap market-order volume to half the visible ask depth
depth  = get '/order_book', market: 'btcusd'
total  = depth['asks'].sum { |_p, v| v.to_d }
volume = [wanted, total / 2].min
post '/orders', market: 'btcusd', side: 'buy', ord_type: 'market', volume: volume.to_s('F')
Defensive patterns

Strategy: validation

Validate before calling

# Ruby: verify counter-side depth covers the market order before submitting
depth = client.get '/api/v2/order_book', market: 'btcusd'
asks = depth['asks']                            # [[price, volume], ...] for a buy
total = asks.sum { |_p, v| v.to_d }
raise "only #{total} available, wanted #{volume}" if total < volume.to_d
client.post '/api/v2/orders', market: 'btcusd', side: 'buy',
            ord_type: 'market', volume: volume.to_s('F')

Type guard

// TypeScript: shape guard for the order book before summing depth
const isOrderBookSide = (v: unknown): v is [string, string][] =>
  Array.isArray(v) && v.every(l => Array.isArray(l) && l.length === 2 &&
    typeof l[0] === 'string' && typeof l[1] === 'string');

Try / catch

On code 2002 whose Reason includes 'Market is not deep enough': fetch depth, cap volume below total counter-side volume (or switch to a limit order), and resubmit once; do not blind-retry the original volume.

Prevention

When it happens

Trigger: POST /api/v2/orders with ord_type=market and volume exceeding the counter side's total depth (buy 100 BTC when all asks sum to 10 BTC); a thin or newly listed market; the moments right after a matching-engine restart while order books are still being rebuilt from the database.

Common situations: Bots sizing positions from another exchange's liquidity; market orders on low-volume pairs; test environments with sparse seeded orders; confusion with the sibling 2002 error 'Volume too large' — that one means depth exists but the price walk exceeded the 90% FUSE.

Related errors


AI-assisted analysis of hpyhacking/peatio@dab8641137 (2026-08-23). Data as JSON: /api/errors/78f6db89500014ce. Report an issue: GitHub.