@@ -1076,6 +1076,25 @@
|
|||||||
return "约 " + Number(v).toFixed(1) + "×";
|
return "约 " + Number(v).toFixed(1) + "×";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function calcPosLeverage(p) {
|
||||||
|
const direct = Number(p && (p.contract_leverage != null ? p.contract_leverage : p.leverage));
|
||||||
|
if (Number.isFinite(direct) && direct > 0) return direct;
|
||||||
|
const idx = Number(p && p.idx_px);
|
||||||
|
const amt = Number(p && p.eth_amount);
|
||||||
|
const prem = Number(p && p.premium_paid);
|
||||||
|
if (!Number.isFinite(idx) || !Number.isFinite(amt) || !Number.isFinite(prem) || amt <= 0 || prem <= 0) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (isCoinPos(p)) {
|
||||||
|
return Math.round((amt / prem) * 10) / 10;
|
||||||
|
}
|
||||||
|
return Math.round((idx * amt) / prem * 10) / 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
function fmtPosLeverage(p) {
|
||||||
|
return fmtLeverage(calcPosLeverage(p));
|
||||||
|
}
|
||||||
|
|
||||||
/** 链上展示:USDC=指数÷卖一(美元);币本位卖一为币报价 → 1÷卖一. */
|
/** 链上展示:USDC=指数÷卖一(美元);币本位卖一为币报价 → 1÷卖一. */
|
||||||
function calcAskLeverage(indexPx, askPx) {
|
function calcAskLeverage(indexPx, askPx) {
|
||||||
if (indexPx == null || askPx == null) return null;
|
if (indexPx == null || askPx == null) return null;
|
||||||
@@ -1691,6 +1710,7 @@
|
|||||||
'<span class="pos-meta-item">持仓来源: ' + sourceText(p) + "</span>" +
|
'<span class="pos-meta-item">持仓来源: ' + sourceText(p) + "</span>" +
|
||||||
'<span class="pos-meta-item">行权价: ' + fmt(p.strike, 0) + "</span>" +
|
'<span class="pos-meta-item">行权价: ' + fmt(p.strike, 0) + "</span>" +
|
||||||
'<span class="pos-meta-item">张数: ' + fmt(p.pos, 0) + " · 币量 " + fmt(p.eth_amount, 4) + "</span>" +
|
'<span class="pos-meta-item">张数: ' + fmt(p.pos, 0) + " · 币量 " + fmt(p.eth_amount, 4) + "</span>" +
|
||||||
|
'<span class="pos-meta-item" title="名义价值÷权利金,测算用">杠杆倍数: ' + fmtPosLeverage(p) + "</span>" +
|
||||||
(expAttr
|
(expAttr
|
||||||
? '<span class="pos-meta-item">到期倒计时: <span class="opt-expiry-cd" data-opt-exp-ms="' + expAttr + '">—</span></span>'
|
? '<span class="pos-meta-item">到期倒计时: <span class="opt-expiry-cd" data-opt-exp-ms="' + expAttr + '">—</span></span>'
|
||||||
: "") +
|
: "") +
|
||||||
|
|||||||
@@ -88,6 +88,38 @@
|
|||||||
return "";
|
return "";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function isCoinPos(p) {
|
||||||
|
const mode = String((p && p.margin_mode) || "").toLowerCase();
|
||||||
|
if (mode === "coin") return true;
|
||||||
|
if (mode === "usdc") return false;
|
||||||
|
const ccy = String((p && p.premium_ccy) || "").toUpperCase();
|
||||||
|
if (ccy === "USDC") return false;
|
||||||
|
if (ccy === "BTC" || ccy === "ETH") return true;
|
||||||
|
const inst = String((p && p.inst_id) || "");
|
||||||
|
return inst.indexOf("-USD-") >= 0 && inst.indexOf("_UM") < 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
function calcPosLeverage(p) {
|
||||||
|
const direct = Number(p && (p.contract_leverage != null ? p.contract_leverage : p.leverage));
|
||||||
|
if (Number.isFinite(direct) && direct > 0) return direct;
|
||||||
|
const idx = Number(p && p.idx_px);
|
||||||
|
const amt = Number(p && p.eth_amount);
|
||||||
|
const prem = Number(p && p.premium_paid);
|
||||||
|
if (!Number.isFinite(idx) || !Number.isFinite(amt) || !Number.isFinite(prem) || amt <= 0 || prem <= 0) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
if (isCoinPos(p)) {
|
||||||
|
return Math.round((amt / prem) * 10) / 10;
|
||||||
|
}
|
||||||
|
return Math.round((idx * amt) / prem * 10) / 10;
|
||||||
|
}
|
||||||
|
|
||||||
|
function fmtPosLeverage(p) {
|
||||||
|
const lev = calcPosLeverage(p);
|
||||||
|
if (lev == null || Number.isNaN(Number(lev))) return "—";
|
||||||
|
return "约 " + Number(lev).toFixed(1) + "×";
|
||||||
|
}
|
||||||
|
|
||||||
function fmtPxSz(px, sz, tickSz) {
|
function fmtPxSz(px, sz, tickSz) {
|
||||||
if (px === null || px === undefined || Number.isNaN(Number(px))) return "—";
|
if (px === null || px === undefined || Number.isNaN(Number(px))) return "—";
|
||||||
let price = fmtOptionPx(px, tickSz);
|
let price = fmtOptionPx(px, tickSz);
|
||||||
@@ -224,6 +256,7 @@
|
|||||||
'<span class="pos-meta-item">持仓来源: ' + sourceText(p) + "</span>" +
|
'<span class="pos-meta-item">持仓来源: ' + sourceText(p) + "</span>" +
|
||||||
'<span class="pos-meta-item">行权价: ' + fmt(p.strike, 0) + "</span>" +
|
'<span class="pos-meta-item">行权价: ' + fmt(p.strike, 0) + "</span>" +
|
||||||
'<span class="pos-meta-item">张数: ' + fmt(p.pos, 0) + " · 币量 " + fmt(p.eth_amount, 4) + "</span>" +
|
'<span class="pos-meta-item">张数: ' + fmt(p.pos, 0) + " · 币量 " + fmt(p.eth_amount, 4) + "</span>" +
|
||||||
|
'<span class="pos-meta-item" title="名义价值÷权利金,测算用">杠杆倍数: ' + fmtPosLeverage(p) + "</span>" +
|
||||||
(expAttr
|
(expAttr
|
||||||
? '<span class="pos-meta-item">到期倒计时: ' + expiryCdHtml(expAttr) + "</span>"
|
? '<span class="pos-meta-item">到期倒计时: ' + expiryCdHtml(expAttr) + "</span>"
|
||||||
: "") +
|
: "") +
|
||||||
|
|||||||
@@ -1806,6 +1806,7 @@ def format_position_row(
|
|||||||
) -> dict[str, Any]:
|
) -> dict[str, Any]:
|
||||||
from lib.options.options_pricing_lib import (
|
from lib.options.options_pricing_lib import (
|
||||||
close_breakeven_idx,
|
close_breakeven_idx,
|
||||||
|
equivalent_contract_leverage,
|
||||||
expiry_breakeven_px,
|
expiry_breakeven_px,
|
||||||
idx_distance_to_be,
|
idx_distance_to_be,
|
||||||
strike_distance_to_be,
|
strike_distance_to_be,
|
||||||
@@ -1891,6 +1892,12 @@ def format_position_row(
|
|||||||
"close_be_px": close_be,
|
"close_be_px": close_be,
|
||||||
"dist_expiry_be": strike_distance_to_be(strike, expiry_be),
|
"dist_expiry_be": strike_distance_to_be(strike, expiry_be),
|
||||||
"dist_close_be": idx_distance_to_be(idx_px, close_be),
|
"dist_close_be": idx_distance_to_be(idx_px, close_be),
|
||||||
|
"contract_leverage": equivalent_contract_leverage(
|
||||||
|
index_px=idx_px,
|
||||||
|
eth_amount=eth_amount,
|
||||||
|
total_premium=premium_paid,
|
||||||
|
margin_mode=row_mode,
|
||||||
|
),
|
||||||
"raw": pos,
|
"raw": pos,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -99,6 +99,19 @@ def _enrich_hub_protocol(snap: dict[str, Any], *, app_module: Any) -> dict[str,
|
|||||||
if premium_usdt is not None:
|
if premium_usdt is not None:
|
||||||
has_premium = True
|
has_premium = True
|
||||||
premium_total_usdt += float(premium_usdt)
|
premium_total_usdt += float(premium_usdt)
|
||||||
|
contract_leverage = p.get("contract_leverage")
|
||||||
|
if contract_leverage is None:
|
||||||
|
try:
|
||||||
|
from lib.options.options_pricing_lib import equivalent_contract_leverage
|
||||||
|
|
||||||
|
contract_leverage = equivalent_contract_leverage(
|
||||||
|
index_px=p.get("idx_px") or p.get("index_px"),
|
||||||
|
eth_amount=p.get("eth_amount"),
|
||||||
|
total_premium=premium_paid,
|
||||||
|
margin_mode=p.get("margin_mode"),
|
||||||
|
)
|
||||||
|
except Exception:
|
||||||
|
contract_leverage = None
|
||||||
slim_pos.append(
|
slim_pos.append(
|
||||||
{
|
{
|
||||||
"inst_id": p.get("inst_id"),
|
"inst_id": p.get("inst_id"),
|
||||||
@@ -108,6 +121,7 @@ def _enrich_hub_protocol(snap: dict[str, Any], *, app_module: Any) -> dict[str,
|
|||||||
"premium_paid": premium_paid,
|
"premium_paid": premium_paid,
|
||||||
"premium_paid_usdt": round(float(premium_usdt), 4) if premium_usdt is not None else None,
|
"premium_paid_usdt": round(float(premium_usdt), 4) if premium_usdt is not None else None,
|
||||||
"premium_ccy": p.get("premium_ccy"),
|
"premium_ccy": p.get("premium_ccy"),
|
||||||
|
"contract_leverage": contract_leverage,
|
||||||
"mark": p.get("mark") or p.get("mark_px"),
|
"mark": p.get("mark") or p.get("mark_px"),
|
||||||
"underlying": p.get("underlying"),
|
"underlying": p.get("underlying"),
|
||||||
"source_label": p.get("source_label"),
|
"source_label": p.get("source_label"),
|
||||||
|
|||||||
@@ -29,6 +29,25 @@ def enrich_position_row_display(
|
|||||||
if premium_override is not None:
|
if premium_override is not None:
|
||||||
row["premium_paid"] = premium_override
|
row["premium_paid"] = premium_override
|
||||||
row["premium_paid_fmt"] = format_premium_amount(row.get("premium_paid"), ccy=premium_ccy)
|
row["premium_paid_fmt"] = format_premium_amount(row.get("premium_paid"), ccy=premium_ccy)
|
||||||
|
try:
|
||||||
|
from lib.options.options_pricing_lib import equivalent_contract_leverage
|
||||||
|
|
||||||
|
def _sf(v: Any) -> float | None:
|
||||||
|
if v is None or v == "":
|
||||||
|
return None
|
||||||
|
try:
|
||||||
|
return float(v)
|
||||||
|
except (TypeError, ValueError):
|
||||||
|
return None
|
||||||
|
|
||||||
|
row["contract_leverage"] = equivalent_contract_leverage(
|
||||||
|
index_px=_sf(row.get("idx_px")),
|
||||||
|
eth_amount=_sf(row.get("eth_amount")),
|
||||||
|
total_premium=_sf(row.get("premium_paid")),
|
||||||
|
margin_mode=row_mode,
|
||||||
|
)
|
||||||
|
except Exception:
|
||||||
|
row.setdefault("contract_leverage", None)
|
||||||
return row
|
return row
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -364,4 +364,4 @@
|
|||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<script src="/static/options_expiry_countdown.js?v=1"></script>
|
<script src="/static/options_expiry_countdown.js?v=1"></script>
|
||||||
<script src="/static/options_panel.js?v=70"></script>
|
<script src="/static/options_panel.js?v=71"></script>
|
||||||
|
|||||||
Reference in New Issue
Block a user