Level2 数据获取与接口:主流数据供应商与调用方式

在量化交易中,Level2 行情数据的获取是策略模拟与收益评估的基础。不同数据供应商在接口协议、数据频率、延迟特征及费用结构上存在显著差异。本章系统梳理国内主流 Level2 数据供应商(万得、聚宽、通联等)的 API 调用方式、数据频率与延迟指标,以及权限与费用模型,帮助学员建立数据获取层的完整认知。

3.1 主流数据供应商对比

国内 Level2 行情数据供应商主要分为三类:传统金融终端型(万得)、量化平台型(聚宽、优矿)、专业数据服务型(通联数据、恒生聚源)。下表从接口协议、数据覆盖、更新频率、适用场景四个维度进行对比:

供应商 接口协议 数据覆盖 更新频率 适用场景
万得 (Wind) COM / .NET / Python API 沪深 Level2、期货、期权、港股 3 秒快照 / 逐笔推送 机构投研、回测、实时监控
聚宽 (JoinQuant) RESTful API / WebSocket 沪深 Level2、指数、ETF 3 秒快照 / Tick 级推送 量化策略开发、模拟交易
通联数据 (DataAPI) HTTP / Python SDK 沪深 Level2、期货、期权 3 秒快照 / 逐笔成交 学术研究、因子挖掘
优矿 (UQER) RESTful API / WebSocket 沪深 Level2、指数 3 秒快照 / Tick 级 策略回测、在线研究
恒生聚源 JAVA / C++ SDK 沪深 Level2、期货、债券 逐笔推送 / 实时快照 高频交易、机构系统
选型建议: 对于个人量化研究者,聚宽和通联数据的 Python SDK 上手成本最低;机构用户若需深度数据清洗与历史快照,万得 WindPy 是行业标准。高频策略建议优先选择支持 WebSocket 逐笔推送的供应商。

3.2 API 接口调用方式

Level2 数据接口主要分为两类:RESTful HTTP 轮询 和 WebSocket 实时推送。前者适合定时获取快照数据,后者适合逐笔成交与订单簿实时更新。以下以聚宽和通联为例展示典型调用方式。

3.2.1 聚宽 WebSocket 订阅示例

import websocket
import json

def on_message(ws, message):
    data = json.loads(message)
    # 处理 Level2 逐笔成交数据
    print(f"股票代码: {data['code']}, 成交价: {data['price']}, 成交量: {data['volume']}")

def on_error(ws, error):
    print(f"WebSocket 错误: {error}")

def on_close(ws, close_status_code, close_msg):
    print("连接关闭")

def on_open(ws):
    # 订阅深交所 Level2 逐笔成交
    subscribe_msg = {
        "cmd": "subscribe",
        "channels": ["szse.level2.trade"]
    }
    ws.send(json.dumps(subscribe_msg))

ws = websocket.WebSocketApp("wss://data.joinquant.com/ws",
                            on_open=on_open,
                            on_message=on_message,
                            on_error=on_error,
                            on_close=on_close)
ws.run_forever()

3.2.2 通联数据 RESTful 快照获取示例

import requests
import json

# 通联数据 API 端点
url = "https://api.tonglian.com/v1/level2/snapshot"
headers = {
    "Authorization": "Bearer YOUR_API_KEY",
    "Content-Type": "application/json"
}
params = {
    "symbol": "000001.SZ",
    "type": "snapshot",
    "date": "2025-03-21"
}

response = requests.get(url, headers=headers, params=params)
if response.status_code == 200:
    snapshot = response.json()
    print(f"最新价: {snapshot['last_price']}")
    print(f"委买一档: {snapshot['bid1_price']} x {snapshot['bid1_volume']}")
    print(f"委卖一档: {snapshot['ask1_price']} x {snapshot['ask1_volume']}")
else:
    print(f"请求失败: {response.status_code}")
接口调用要点:
  • 所有供应商均要求 API Key 或 Token 鉴权,请勿硬编码在公开代码中。
  • WebSocket 连接需实现心跳机制(通常每 30 秒发送 ping),防止连接超时断开。
  • RESTful 接口有频率限制(如万得限制每秒 5 次请求),超限会被封禁。

3.3 数据频率与延迟特征

Level2 行情数据频率分为三个层级:快照频率(3 秒/次)、逐笔频率(每笔成交/委托)、Tick 频率(交易所最小推送间隔)。延迟则受网络路径、供应商处理链路、本地解码速度三重影响。

Level2 数据频率与延迟层级图 Level2 数据频率与延迟层级 交易所撮合引擎 快照数据 (3秒/次) 逐笔数据 (实时推送) 供应商缓存 + 分发 WebSocket 实时推送 用户策略 / 数据库 延迟 ~1s 延迟 ~200ms 延迟 ~50ms

典型延迟数据如下(以深交所 Level2 为例,网络环境为 BGP 多线机房):

数据层级 交易所推送间隔 供应商处理延迟 用户端接收延迟 总端到端延迟
快照数据 3 秒 200-500 ms 50-100 ms ~3.3 秒
逐笔成交 实时(微秒级) 50-200 ms 10-50 ms ~200 ms
逐笔委托 实时(微秒级) 100-300 ms 20-80 ms ~350 ms
延迟陷阱: 部分供应商在行情峰值时段(如开盘前 15 分钟)会主动降级推送频率,导致快照间隔从 3 秒延长至 6 秒甚至更长。高频策略必须设计超时重连与数据补全机制,避免因数据缺失产生虚假信号。

3.4 数据权限与费用模型

Level2 行情数据并非免费开放,交易所向数据供应商收取授权费,供应商再向终端用户转嫁成本。费用结构通常包含:基础订阅费(按年/月)、数据品种费(沪深/期货/期权)、接口调用费(按请求次数或并发连接数)。

供应商 基础订阅费(年) 沪深 Level2 附加费 期货 Level2 附加费 接口调用限制
万得 ¥30,000 - ¥80,000 ¥10,000 / 年 ¥15,000 / 年 5 次/秒,无并发限制
聚宽 免费(个人版) ¥6,000 / 年 ¥8,000 / 年 100 次/分钟,10 并发
通联数据 ¥20,000 / 年 ¥8,000 / 年 ¥12,000 / 年 200 次/分钟,20 并发
优矿 免费(社区版) ¥4,800 / 年 ¥6,000 / 年 60 次/分钟,5 并发
费用优化策略:
  • 个人研究优先使用聚宽或优矿的免费版 + Level2 附加包,年费控制在 ¥5,000 以内。
  • 机构用户可考虑万得机构版 + 自建缓存层,减少重复请求,降低接口调用费。
  • 期货 Level2 数据授权费通常高于股票,且需要单独向交易所申请(如中金所、大商所)。

3.5 数据获取架构设计建议

在实际量化系统中,Level2 数据获取层通常采用“推拉结合”架构:实时行情通过 WebSocket 推送进入内存队列,历史快照通过 RESTful 接口定时拉取并存入本地数据库。以下架构图展示典型实现:

Level2 数据获取推拉结合架构 Level2 数据获取推拉结合架构 交易所 Level2 网关 WebSocket 实时推送 RESTful 定时拉取 内存队列 (Kafka/Redis) 本地数据库 (InfluxDB) 策略引擎 / 回测系统 推模式 拉模式
架构要点:
  • 实时推送数据直接进入内存队列,保证低延迟;历史拉取数据写入时序数据库,用于回测与复盘。
  • 建议对 WebSocket 连接设置自动重连机制(指数退避),并记录断连期间的数据缺口,后续通过 RESTful 补拉。
  • 数据落地时按“日期 + 股票代码”分区存储,便于后续批量读取与因子计算。