feat: options sheet sizing, ITM/OTM labels, and 14-day chain view
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -84,6 +84,7 @@ def _build_cfg(app_module: Any) -> dict[str, Any]:
|
||||
"budget_buffer": _env_float("OKX_OPTIONS_BUDGET_BUFFER", 0.95),
|
||||
"default_underly": (os.getenv("OKX_OPTIONS_DEFAULT_UNDERLY") or "ETH").strip().upper(),
|
||||
"max_dte_days": _env_float("OKX_OPTIONS_MAX_DTE_DAYS", 2.0),
|
||||
"chain_max_dte_days": _env_float("OKX_OPTIONS_CHAIN_MAX_DTE_DAYS", 14.0),
|
||||
"itm_max_dist": _env_float("OKX_OPTIONS_ITM_MAX_DIST_USD", 30.0),
|
||||
"td_mode": (os.getenv("OKX_OPTIONS_TD_MODE") or "cross").strip(),
|
||||
"allow_market_close": _env_bool("OKX_OPTIONS_ALLOW_MARKET_CLOSE", False),
|
||||
@@ -136,11 +137,11 @@ def register_options_routes(app: Flask, cfg: dict[str, Any]) -> None:
|
||||
chain = cfg["build_option_chain"](
|
||||
ex,
|
||||
u,
|
||||
max_dte_days=cfg["max_dte_days"],
|
||||
itm_only=True,
|
||||
max_dte_days=cfg["chain_max_dte_days"],
|
||||
itm_only=False,
|
||||
itm_max_dist_usd=cfg["itm_max_dist"],
|
||||
)
|
||||
return jsonify({"ok": True, **chain})
|
||||
return jsonify({"ok": True, **chain, "chain_max_dte_days": cfg["chain_max_dte_days"]})
|
||||
|
||||
@app.route("/api/options/quote")
|
||||
@lr
|
||||
@@ -160,20 +161,27 @@ def register_options_routes(app: Flask, cfg: dict[str, Any]) -> None:
|
||||
mode = (request.args.get("mode") or "budget_full").strip()
|
||||
budget = cfg["trade_budget"]
|
||||
eth_amount = None
|
||||
sheet_count = None
|
||||
try:
|
||||
if request.args.get("eth_amount"):
|
||||
eth_amount = float(request.args.get("eth_amount"))
|
||||
except (TypeError, ValueError):
|
||||
pass
|
||||
try:
|
||||
if request.args.get("sheets"):
|
||||
sheet_count = int(request.args.get("sheets"))
|
||||
except (TypeError, ValueError):
|
||||
pass
|
||||
if ask is None or ask <= 0:
|
||||
return jsonify({**q, "ok": False, "msg": "暂无卖一价"})
|
||||
sizing = calc_order_size(
|
||||
quote_per_unit=float(ask),
|
||||
ct_mult=float(ct_mult),
|
||||
min_sz=int(min_sz),
|
||||
budget_usdc=budget if mode != "eth_amount" else None,
|
||||
budget_usdc=budget if mode == "budget_full" else None,
|
||||
budget_buffer=cfg["budget_buffer"],
|
||||
eth_amount=eth_amount if mode == "eth_amount" else None,
|
||||
sheets=sheet_count if mode == "sheets" else None,
|
||||
budget_cap=cfg["trade_budget"],
|
||||
)
|
||||
return jsonify(
|
||||
@@ -206,18 +214,25 @@ def register_options_routes(app: Flask, cfg: dict[str, Any]) -> None:
|
||||
ct_mult = float(q.get("ct_mult") or 0.01)
|
||||
min_sz = int(q.get("min_sz") or 1)
|
||||
eth_amount = None
|
||||
sheet_count = None
|
||||
if mode == "eth_amount":
|
||||
try:
|
||||
eth_amount = float(data.get("eth_amount"))
|
||||
except (TypeError, ValueError):
|
||||
return jsonify({"ok": False, "msg": "ETH 数量无效"})
|
||||
elif mode == "sheets":
|
||||
try:
|
||||
sheet_count = int(data.get("sheets"))
|
||||
except (TypeError, ValueError):
|
||||
return jsonify({"ok": False, "msg": "张数无效"})
|
||||
sizing = calc_order_size(
|
||||
quote_per_unit=float(ask),
|
||||
ct_mult=ct_mult,
|
||||
min_sz=min_sz,
|
||||
budget_usdc=cfg["trade_budget"] if mode != "eth_amount" else None,
|
||||
budget_usdc=cfg["trade_budget"] if mode == "budget_full" else None,
|
||||
budget_buffer=cfg["budget_buffer"],
|
||||
eth_amount=eth_amount,
|
||||
sheets=sheet_count,
|
||||
budget_cap=cfg["trade_budget"],
|
||||
)
|
||||
if not sizing.get("ok"):
|
||||
|
||||
Reference in New Issue
Block a user