- OKX交易自动化 (okx-auto-position, okx-crypto, okx-exchange) - 交易信号处理 (signal-confirmation-templates, trading-signal-aggregator) - 量化因子挖掘 (quant-factor-mining) - 长桥集成 (longbridge-cli, longbridge-python-sdk) - 六合彩分析 (lottery-hk) - 股息投资 (dividend-investing, dividend-scanner) - 日内交易 (intraday-trading) - 同花顺 (tonghuashun)
4.8 KiB
OKX API 关键Pitfalls
1. posMode=net_mode vs long_short_mode
问题:账户可能是 net_mode(净头寸)而非 long_short_mode(多空分离)。
检查方法:
GET /api/v5/account/config
# 响应中 "posMode": "net_mode" 或 "long_short_mode"
影响:
net_mode:禁止传posSide参数,否则报错sCode=51000 "Parameter posSide error"long_short_mode:必须传posSide(long/short)
下单示例(net_mode):
{
"instId": "ETH-USDT-SWAP",
"tdMode": "cross",
"side": "buy", # buy=开多/平空, sell=开空/平多
"ordType": "market",
"sz": "1" # 不传posSide!
}
设置杠杆(net_mode):
{
"instId": "ETH-USDT-SWAP",
"lever": "25",
"mgnMode": "cross" # 不传posSide!
}
切换模式(需要主账户权限):
POST /api/v5/account/set-position-mode
{"posMode": "long_short_mode"} # 或 "net_mode"
2. OCO订单合并(加仓场景)
问题:加仓后,旧OCO只覆盖旧仓位,新OCO只覆盖新仓位,导致多个OCO并存。
错误示例:
- 持仓5张,OCO(sell 5, SL=1660, TP=1746)
- 加仓1张 → 持仓6张
- 新建OCO(sell 1, SL=1666.8, TP=1775.1)
- 结果:2个OCO并存,旧OCO触发只平5张,剩1张单独走
正确流程:
- 查现有OCO:
GET /api/v5/trade/orders-algo-pending?ordType=oco - 找到同instId的旧OCO algoId
- 删除旧OCO:
POST /api/v5/trade/cancel-algo→[{instId, algoId}] - 创建新OCO覆盖全部持仓
验证:
# 查pending OCO
curl -X GET "https://www.okx.com/api/v5/trade/orders-algo-pending?ordType=oco" \
-H "OK-ACCESS-KEY: $KEY" ...
# 应该只有一个OCO per instId
3. 补推信号必须先查持仓
场景:模型断线后补推积压信号。
错误做法:直接用历史信号数据推送推荐(如"4,290 ETH加仓到4,455")。
正确做法:
- 先查当前持仓:
GET /api/v5/account/positions - 再查当前algo orders:
GET /api/v5/trade/orders-algo-pending?ordType=oco - 用当前持仓数据而非历史信号数据生成推荐
案例:
- 历史信号说"4,290 ETH"
- 实际持仓已是5张(可能中间已有多次变动)
- 用历史数据推"加仓到4,455"是错误的
4. 遍历查询algo orders
问题:ordType 参数不能组合查询,需逐个类型查。
for algo_type in ["oco", "conditional", "trigger", "move_order_stop"]:
result = okx_get(f"/api/v5/trade/orders-algo-pending?ordType={algo_type}")
# 处理 result["data"]
注意:某些类型可能返回错误(如账户未开通该功能),需忽略错误继续。
5. 密码中含特殊字符
问题:OKX_PASSPHRASE 含 $ 等特殊字符时,bash 会尝试变量展开。
错误:export OKX_PASSPHRASE=mikeOkxID$1 → $1 展开为空
正确:
export OKX_PASSPHRASE='mikeOkxID$1' # 单引号
或从文件读取:
with open("~/.bashrc", "r") as f:
for line in f:
if "OKX_PASSPHRASE" in line:
passphrase = line.split("=", 1)[1].strip().strip('"').strip("'")
6. 凭证变量名:OKX_SECRET(不是OKX_SECRET_KEY)
bashrc里实际变量名是 OKX_SECRET,不是 OKX_SECRET_KEY。
脚本内部:load_credentials() 用 OKX_\w+ 正则匹配,自动兼容,不受影响。
手动ccxt初始化(agent写临时Python时):
# ❌ 错误 — 会 KeyError
creds['OKX_SECRET_KEY']
# ✅ 正确
creds['OKX_SECRET']
# ✅ 兼容写法
secret = creds.get('OKX_SECRET', '') or creds.get('OKX_SECRET_KEY', '')
三个变量:OKX_API_KEY、OKX_SECRET、OKX_PASSPHRASE
7. --execute 必须同时带 --rec-json
脚本代码 if args.execute and args.rec_json: 要求两个参数同时存在。
错误:只传 --execute 不传 --rec-json → 静默跳过执行,fall through到推荐流程
正确两步流程:
# 第1步:获取推荐JSON
python3 okx_position_advisor.py --symbol HYPE --side long --leverage 10 --json > /tmp/rec.json
# 第2步:执行下单(必须同时带 --execute 和 --rec-json)
python3 okx_position_advisor.py --symbol HYPE --side long --leverage 10 --execute --json --rec-json "$(cat /tmp/rec.json)"
8. 余额为零时ZeroDivisionError
问题:recommend_position() 函数在计算 margin_pct = total_margin / acct_info['usdt_free'] * 100 时,如果 usdt_free=0(用户满仓),会抛出 ZeroDivisionError。
修复:在调用 recommend_position() 前检查余额:
if acct_info['usdt_free'] < 0.01:
print("⚠️ 余额不足(可用0 USDT),无法开仓")
sys.exit(0)
format_signal.py 已加 try/except 处理此场景。