Align hedge UI/fees: drop 未启动, premium coin/U, equity incl perp margin, OKX option fees.

Option net uses Min(0.03%×coin, 7%×premium) with bid/ask fills (no slip); live PnL colors fixed.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
dekun
2026-10-14 17:12:10 +08:00
parent be00991568
commit 746655acba
12 changed files with 190 additions and 45 deletions
+22 -10
View File
@@ -1,8 +1,8 @@
"""成交价与手续费.
永续:滑点=1×fee_rate,手续费=名义×fee_rate.
期权(币本位):滑点仍按权利金价×fee_rate;手续费对齐 OKX=
Min(fee_rate×标的币数量, 权利金×7%).
期权(币本位):吃卖一/买一按报价成交(无额外滑点);手续费对齐 OKX=
Min(fee_rate×标的币数量, 权利金×7%);普通用户 taker 默认 0.03%.
"""
from __future__ import annotations
@@ -32,6 +32,20 @@ def sim_fee_rate(override: float | None = None) -> float:
return 0.0005
def sim_option_fee_rate(override: float | None = None) -> float:
"""OKX 币本位期权 taker 费率(默认 0.03%)."""
if override is not None:
return float(override)
try:
return float(
os.getenv("SIM_OPTION_FEE_RATE")
or os.getenv("OKX_OPTIONS_TAKER_FEE")
or "0.0003"
)
except (TypeError, ValueError):
return 0.0003
def perp_fill(
*,
side: str,
@@ -74,7 +88,7 @@ def option_fee_coin(
Min(费率 × 张数对应标的币数量, 权利金×封顶比例).
注意:费率作用在标的币面值上,不是权利金名义上.
"""
f = sim_fee_rate(fee_rate)
f = sim_option_fee_rate(fee_rate)
qty = abs(float(underlying_coin or 0.0))
prem = abs(float(premium_coin or 0.0))
if qty <= 0 and prem <= 0:
@@ -92,20 +106,19 @@ def option_fill(
bid: float,
ask: float,
qty: float,
fee_rate: float,
fee_rate: float | None = None,
) -> PriceResult:
"""开仓买入吃卖一; 平仓卖出吃买一.
qty = sheets × ct_mult(标的币数量).
滑点仍按权利金价×费率;手续费按 OKX 币本位公式(标的币×费率,权利金7%封顶).
成交价=买卖一(无额外滑点);手续费=OKX 币本位公式(标的币×费率,权利金7%封顶).
"""
f = float(fee_rate)
f = sim_option_fee_rate(fee_rate)
if action == "open":
base = float(ask)
fill = base * (1.0 + f)
else:
base = float(bid)
fill = base * (1.0 - f)
fill = base
qty_f = abs(float(qty))
notional = abs(fill * qty_f)
fee = option_fee_coin(
@@ -113,8 +126,7 @@ def option_fill(
premium_coin=notional,
fee_rate=f,
)
slip = abs(fill - base) * qty_f
return PriceResult(base_px=base, fill_px=fill, fee=fee, slip=slip, notional=notional)
return PriceResult(base_px=base, fill_px=fill, fee=fee, slip=0.0, notional=notional)
@dataclass(slots=True)