## 架构:影子发信号,实盘执行,两个进程
不让实盘自己算信号。前两个理由是资源与隔离(2 核上再来一份十币计算会把清空
从 247ms 推到 500ms+;实盘崩溃不该影响正在采的数据集),第三个最要紧:
**实盘交易的必须是影子测量的那一个信号**。各算一份会让两边悄悄分叉,之后就
没法把实盘实际成交和影子测的滑点曲线对照——而那个对照是整件事的目的。
总线用 append-only JSONL + fsync:崩溃安全,且「影子在跑、实盘没在跑」会表现
为信号在攒着,而不是静默丢弃。
## 出场结构精确分解成两个半仓
TripleBarrierConfig 只有单级止盈,装不下 3ATR 减半 + 8ATR 目标。但已核实
exit_model.py:151 的 runner_stops 是从**入场价**算的(ret = (entry-low)/a),
且 RUNNER_STOP == SL == 2.0,所以两半共用同一个不动的止损,可精确分解为:
半仓 A 市价入场 · TP 3ATR · SL 2ATR · 48min
半仓 B 市价入场 · TP 8ATR · SL 2ATR · 48min
止损先到则两半都在 -2ATR 出场;3ATR 先到则 A 出场、B 继续且止损仍在 2ATR。
与回测逐情形一致。assert_decomposable() 在启动时挡住 RUNNER_STOP != SL 的
改动,否则实盘会跑另一个收益结构且不报错。
## 硬约束是这个文件的重点
一笔止损只亏约 1 USDT,所以「亏损可控」对单笔成立。但三类故障的代价**不随
仓位缩小**,必须显式封住:失控下单(MAX_OPEN=3 / MAX_DAY=15)、亏损累积
(MAX_DAY_LOSS=20)、裸仓(重启对账)。状态落盘且原子替换——不落盘的话反复
重启就等于反复重置日上限,而失控下单恰好常伴随反复重启。
已验:幂等去重、并发上限、日开仓上限、日亏损上限、跨日归零且保留 done 键、
重启后计数不清零、状态文件损坏时不抛异常。
## 重启对账选择平掉而非接管
崩溃重启后交易所可能还有仓位,而 executor 全没了,那些仓位没有任何止损在盯。
接管需要重建入场价/ATR/剩余半仓状态/已过根数,任一项猜错就让出场结构变成
另一个东西;平掉的代价只是一笔小额亏损,且行为确定。
## 已知风险:止损在机器人侧
Bitget 连接器只支持 LIMIT / LIMIT_MAKER / MARKET,无触发单。
PositionExecutor.control_stop_loss() 是本地盯价、触发时才发市价单,所以进程
一死仓位就是裸的。10x 下强平需逆向 10%(约 100 个 ATR),48 分钟内极不可能,
单次代价仍封在保证金内。下一步用 Bitget 服务端 TP/SL 计划单做兜底。
Co-authored-by: Cursor <cursoragent@cursor.com>
39 lines
2.0 KiB
Bash
39 lines
2.0 KiB
Bash
# 复制成 tg.env 再填。tg.env 已在 .gitignore 里,不会被提交。
|
||
#
|
||
# 拿 token:Telegram 里找 @BotFather → /newbot → 按提示起名
|
||
# 拿 chat id:给你的 bot 随便发一句,然后打开
|
||
# https://api.telegram.org/bot<TOKEN>/getUpdates
|
||
# 返回的 result[0].message.chat.id 就是
|
||
export TG_TOKEN=""
|
||
export TG_CHAT=""
|
||
# 每笔名义额(USDT)。杠杆**不改**手续费与滑点(都按名义额收),所以抬名义额
|
||
# 是有真实成本的;抬它的唯一理由是压掉步长取整:实测最差币的偏差
|
||
# 100U → 6.7%(SOL)、500U → 1.8%、1000U → 0.6%。
|
||
export TG_NOTIONAL="500"
|
||
# 杠杆只影响占用保证金,不影响名义敞口/手续费/滑点/盈亏绝对值。
|
||
# 名义 500 在 10x 下占 50 USDT 保证金;止损在 2 ATR ≈ 0.2%,而 10x 强平约需
|
||
# 逆向 10% = 100 个 ATR,差 50 倍,所以这里的杠杆几乎不引入强平风险。
|
||
# 交易所侧记得设**逐仓**,让每笔最大损失被保证金封住。
|
||
export TG_LEVERAGE="10"
|
||
# 距「参考价成立」超过这么多秒就标为已失效。参考价是次根开盘价,
|
||
# 过了就不是回测那个成交价了
|
||
export TG_STALE_S="90"
|
||
|
||
# ── 自动化实盘(live_exec.py)──────────────────────────────────
|
||
# 只读+交易权限,**不要开提币权限**
|
||
export BITGET_API_KEY=""
|
||
export BITGET_API_SECRET=""
|
||
export BITGET_PASSPHRASE=""
|
||
# 名义额与杠杆。理由同 TG_NOTIONAL:抬名义额是为了压步长取整,不是为了赚更多
|
||
export LIVE_NOTIONAL="500"
|
||
export LIVE_LEVERAGE="10"
|
||
# 硬约束。这三条封住的是「代价不随仓位缩小」的那几类故障:
|
||
# MAX_OPEN 失控下单(单笔小但笔数无界)
|
||
# MAX_DAY 同上,日维度
|
||
# MAX_DAY_LOSS 策略真的不行但没人盯着
|
||
export LIVE_MAX_OPEN="3"
|
||
export LIVE_MAX_DAY="15"
|
||
export LIVE_MAX_DAY_LOSS="20"
|
||
# 信号超过这么久就不做。参考成交价是次根开盘价,过期后跑的不是回测那个价
|
||
export LIVE_STALE_S="20"
|