クリプトのクオンツトレーディングやマーケットマイクロストラクチャ分析において、取引所ごとの板情報(Order Book)スナップショットを統一スキーマで扱えるかどうかは、バックテストの精度と速度に直結します。私はこれまで複数の暗号資産取引所で L2 スナップショットを収集・正規化するパイプラインを構築してきましたが、商用データプロバイダである Tardis と Amberdata はその「正解」を提供してくれる存在です。本記事では、両社の正規化済みブックスナップショット スキーマを実機で叩き比べ、HolySheep AI の LLM API と組み合わせた分析ワークフローを紹介します。
まず、ブックスナップショットを LLM に流し込みたい読者向けに、主要モデルの 2026 年 output 価格を整理しておきます。
| モデル | 2026 output (/MTok) | 主な用途 |
|---|---|---|
| GPT-4.1 | $8.00 | 関数呼び出し・構造化出力 |
| Claude Sonnet 4.5 | $15.00 | 長文脈の板解析 |
| Gemini 2.5 Flash | $2.50 | コスト重視のバッチ処理 |
| DeepSeek V3.2 | $0.42 | 最安、バルク要約に最適 |
1. Normalized Book Snapshot Schema とは何か
ブックスナップショットとは、ある時刻 t における板の買い側/売り側の注文の並びを L2 レベルで記録したものです。これを「正規化(normalized)」するとは、取引所ごとに異なる JSON / CSV / バイナリ形式を、共通カラム(exchange、symbol、timestamp、bids、asks)に統一することを意味します。
// 正規化済みブックスナップショットの代表スキーマ
{
"exchange": "binance",
"symbol": "BTC-USDT",
"timestamp": "2026-01-15T03:22:14.123Z",
"local_timestamp": "2026-01-15T03:22:14.187Z",
"bids": [
["67231.40", "0.512"], // [price, size]
["67231.30", "1.200"],
["67231.20", "0.085"]
],
"asks": [
["67231.50", "0.300"],
["67231.60", "0.800"],
["67231.70", "2.150"]
]
}
Tardis も Amberdata も、おおむね上記のようなスキーマを採用していますが、細部で明確な差があります。
2. Tardis の正規化ブックスナップショット
Tardis(tardis.dev)は、ティックレベル/板レベル履歴データの保存とリプレイに特化したプロバイダです。私は Binance の BTC-USDT perpetual で 2025 年 12 月の約 1 ヶ月間、Replay API 経由で 1 分足のスナップショットを取得し、約 44,640 レコードをローカルに蓄積しました。
Tardis の特徴
- CSV / JSON 両形式で生データをエクスポート可能
- exchange / symbol / timestamp のスキーマが固定で扱いやすい
- bids / asks は価格文字列(文字列)として格納されるため、float 変換が必要
- Streaming Replay では
book_snapshotチャンネルを提供
# Tardis Replay API クライアント例(公式Python SDK ベース)
from tardis_client import TardisClient
tardis = TardisClient(api_key="YOUR_TARDIS_API_KEY")
messages = tardis.replay(
exchange="binance",
from_date="2026-01-15",
to_date="2026-01-15",
filters=[{"channel": "book_snapshot", "symbols": ["BTCUSDT"]}],
)
for msg in messages:
snap = msg["data"]
best_bid = float(snap["bids"][0][0]) # "67231.40" -> 67231.40
best_ask = float(snap["asks"][0][0])
mid = (best_bid + best_ask) / 2.0
spread_bps = (best_ask - best_bid) / mid * 1e4
print(f"{snap['timestamp']} mid={mid:.2f} spread={spread_bps:.2f}bps")