diff --git a/backend/app/api/lots.py b/backend/app/api/lots.py index 739b30e..b098f1e 100644 --- a/backend/app/api/lots.py +++ b/backend/app/api/lots.py @@ -4,6 +4,7 @@ """ from __future__ import annotations +import logging import secrets import threading import time @@ -31,6 +32,10 @@ def _resolve_asset_type(request: Request, symbol: str) -> str: try: return repo.resolve_asset_type(symbol) if repo is not None else "stock" except Exception: + # 回退为 stock 会让 etf 批次的止盈止损规则落入错误的监控轮, 必须留痕排查 + logging.getLogger(__name__).warning( + "resolve_asset_type failed for %s, falling back to stock", symbol, exc_info=True + ) return "stock" diff --git a/backend/app/backtest/matrix.py b/backend/app/backtest/matrix.py index bcf0198..7d7b17a 100644 --- a/backend/app/backtest/matrix.py +++ b/backend/app/backtest/matrix.py @@ -1435,7 +1435,7 @@ def _populate_matrix_derived_arrays( # 异常, 由 _resolve_matrix_storage_fields 的 vector 装载路径显式失败。 if "float_shares" in vector_fields: raise ValueError("matrix turnover_rate requires float_shares") - logger.info( + logger.debug( "turnover_rate unavailable (asset has no float_shares); keeping NaN column" ) else: diff --git a/backend/app/strategy/monitor_rules.py b/backend/app/strategy/monitor_rules.py index 972e276..787d313 100644 --- a/backend/app/strategy/monitor_rules.py +++ b/backend/app/strategy/monitor_rules.py @@ -261,7 +261,7 @@ def validate(rule: dict) -> None: try: date.fromisoformat(remind.strip()) except ValueError: - raise ValueError(f"remind_date 必须是 YYYY-MM-DD 日期: {remind!r}") + raise ValueError(f"remind_date 必须是 YYYY-MM-DD 日期: {remind!r}") from None lead = rule.get("lead_days", 0) if isinstance(lead, bool) or not isinstance(lead, int) or lead < 0: raise ValueError("lead_days 必须是非负整数 (提前提醒天数)")