Align position margin with account balance and show deducted open commission only.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
dekun
2026-06-26 11:26:41 +08:00
parent 038eb9a403
commit 9a55c61678
3 changed files with 130 additions and 6 deletions
+37 -1
View File
@@ -251,7 +251,21 @@ class CtpBridge:
except ImportError:
return
def _on_position(_event) -> None:
def _on_position(event) -> None:
try:
pos = event.data
vol = int(getattr(pos, "volume", 0) or 0)
if vol <= 0:
return
sym = getattr(pos, "symbol", "") or ""
d = "long" if _is_long_direction(getattr(pos, "direction", None)) else "short"
for attr in ("margin", "use_margin", "UseMargin"):
raw = float(getattr(pos, attr, 0) or 0)
if raw > 0:
self._position_margins[self._position_margin_key(sym, d)] = raw
break
except Exception as exc:
logger.debug("position margin cache: %s", exc)
_fire_position_refresh_callback_debounced()
self._ee.register(EVENT_POSITION, _on_position)
@@ -1177,6 +1191,7 @@ class CtpBridge:
"lots": vol,
"price": float(getattr(trade, "price", 0) or 0),
"datetime": dt,
"commission": round(float(getattr(trade, "commission", 0) or 0), 2),
}
except Exception as exc:
logger.debug("trade_row_from_vnpy: %s", exc)
@@ -1216,6 +1231,9 @@ class CtpBridge:
"lots": vol,
"price": price,
"datetime": dt,
"commission": round(
float(data.get("Commission") or data.get("commission") or 0), 2,
),
}
except Exception as exc:
logger.debug("trade_row_from_ctp_dict: %s", exc)
@@ -1476,6 +1494,24 @@ def ctp_get_account(mode: str) -> dict[str, Any]:
return b.get_account()
def ctp_account_margin_used(mode: str) -> Optional[float]:
"""账户实际占用保证金 ≈ 权益 − 可用(与顶栏柜台资金一致)。"""
b = get_bridge()
if b.connected_mode != mode or not b.ping():
return None
try:
acc = b.get_account()
balance = float(acc.get("balance") or 0)
available = float(acc.get("available") or 0)
if balance <= 0:
return None
used = balance - available
return round(used, 2) if used > 0 else None
except Exception as exc:
logger.debug("ctp_account_margin_used: %s", exc)
return None
def ctp_list_positions(
mode: str,
*,