Features

Binance data

Download Binance spot and futures klines with trade counts and taker volume

How do you get Binance historical data into Python? vbt.BinanceData downloads klines for spot and futures markets from Binance's public API, including trade counts and taker volume, and returns them as one data object ready for indicators and backtests.

Pull a year of hourly spot and perpetual futures bars for BTCUSDT
kwargs = dict(start="2024-01-01", end="2025-01-01", timeframe="1h")
spot = vbt.BinanceData.pull("BTCUSDT", **kwargs)
perp = vbt.BinanceData.pull("BTCUSDT", klines_type="futures", **kwargs)  
spot.features[5:]  
['Quote volume', 'Trade count', 'Taker base volume', 'Taker quote volume']
def summarize(d):
    return {
        "volume (M BTC)": d.volume.sum() / 1e6,
        "trades (M)": d.get("Trade count").sum() / 1e6,
        "taker buys": d.get("Taker base volume").sum() / d.volume.sum(),
    }

pd.DataFrame({"spot": summarize(spot), "perpetual": summarize(perp)}).T.round(3)
           volume (M BTC)  trades (M)  taker buys
spot               12.931    1015.161       0.497
perpetual         100.355    1365.867       0.497
basis_bps = (perp.close / spot.close - 1) * 10_000  
basis_bps.describe().round(2)
count    8784.00
mean       -0.29
std         5.25
min       -20.76
25%        -4.44
50%        -2.76
75%         4.70
max        28.88
Name: Close, dtype: float64

All 8,784 hours of 2024 came back for both markets. The perpetual contract traded 7.8 times the spot volume, and its hourly closing price stayed within 29 basis points of spot. In both markets, takers bought almost exactly half the volume over the year. Each hour's share can be calculated from its taker buy volume and total volume.

From Binance candles to strategy research

The extra fields let you ask questions that prices alone cannot answer. Does a breakout behave differently when it comes with more trades? Does a larger share of taker buying help filter an entry signal? How does a strategy perform on spot compared with the perpetual contract? You can calculate these features alongside your indicators and test them with Signal backtesting.

The example above compares the two markets on matching hourly bars. Use the same approach to study when the perpetual trades above or below spot, or compare activity across several coins. The prices and extra fields stay together in the data object, so you can select a symbol or a period without rebuilding the dataset. See Data pipelines for working with the downloaded data.

Spot and futures

klines_type selects the market and price series:

Dataklines_typeUseful for
Spot"spot" (default)Coin prices, traded volume, and activity
USD-margined futures"futures"Contract prices and spot versus futures comparisons
Coin-margined futures"futures_coin"Research on contracts margined in the underlying coin
Futures mark price"futures_mark_price" or "futures_coin_mark_price"Comparing traded prices with the mark price
Futures index price"futures_index_price" or "futures_coin_index_price"Comparing contracts with their reference index

Spot and USD-margined trade candles include open, high, low, close, and volume, plus quote volume, the number of trades, and the base and quote volume bought by takers. These taker fields measure buying initiated by traders taking liquidity, which OHLC bars alone cannot show.

Choose trade candles for volume research. Mark and index candles provide reference prices, with placeholders in the activity fields, as shown in Binance's market data reference.

Downloading and updating historical data

Timeframes run from one minute to one month, as in "1m", "1h", or "1d", and dates accept strings such as "2024-01-01" or "1 year ago". A pull starting before a symbol's first trade begins at its first available candle, so a long range is safe to request. The end date is exclusive: the example stops before January 1, 2025, covering the full calendar year of 2024.

Requests are split into batches of 1,000 klines with a 0.5-second pause between them by default. Each batch starts where the previous one ended, so one symbol downloads sequentially: a year of one-minute bars is about 530 requests and several minutes. Many symbols can be pulled in parallel threads with execute_kwargs=dict(engine="threadpool"), as long as the total stays within Binance's rate limits.

Assign the result of data.update() to keep the latest data. Updates fetch from the last stored candle, refreshing that candle and adding newer bars. For a pull with a fixed end date, supply a later end date when updating. To keep a large history on disk and update it on a schedule, see Data storage and databases.

Finding symbols

vbt.BinanceData.list_symbols lists spot symbols, filtered with a glob or a regular expression:

List Binance symbols that match a pattern
vbt.BinanceData.list_symbols("BTC*USDT")
['BTCDOWNUSDT', 'BTCSTUSDT', 'BTCUPUSDT', 'BTCUSDT']

Pulling many symbols at once returns one data object with a column per symbol, aligned on one index.

Accounts and regions

The class uses the python-binance client, installed with pip install python-binance, not the unrelated binance package. Historical klines are public, so no API key is needed. Keys and other client options go into client_config, and client_config=dict(tld="us") connects to Binance.US. If you already use python-binance, pass your existing client through client to reuse its configuration across pulls. For data from many other exchanges, vbt.CCXTData offers the same interface through CCXT, as the Market data sources page shows.

Copyright © 2021–2026 Oleg Polakow. All rights reserved.

Site content and documentation are provided for using and evaluating VectorBT PRO and for educational purposes. Any other use, including building or supporting competing products or services, requires prior written consent.