07.4.4.1.7 — Live Market Runtime & Advanced Trend Diagnostics

This commit is contained in:
2026-05-11 15:20:41 +03:00
parent fe33e0c026
commit ec9904f91d
7 changed files with 591 additions and 18 deletions

View File

@@ -53,6 +53,8 @@ class ScalpStrategy:
"strategy": self.name,
"symbol": context.symbol,
"error": str(exc),
"entry_block_reason": "MARKET_PRICE_ERROR",
"entry_block_message": "нет данных рынка",
},
)
@@ -75,17 +77,25 @@ class ScalpStrategy:
if len(prices) > self._window_size:
prices.pop(0)
base_payload = {
"strategy": self.name,
"symbol": symbol,
"price": current_price,
"runtime_window_ttl_seconds": self._window_ttl_seconds,
"runtime_window_size": len(prices),
}
if len(prices) < self._window_size:
return SignalResult(
signal=SignalType.HOLD,
reason="Недостаточно данных для SCALP.",
confidence=0.0,
payload={
"strategy": self.name,
"symbol": symbol,
"price": current_price,
**base_payload,
"window_size": len(prices),
"required_window_size": self._window_size,
"entry_block_reason": "NOT_ENOUGH_LIVE_DATA",
"entry_block_message": "мало данных",
},
)
@@ -98,9 +108,10 @@ class ScalpStrategy:
reason="Некорректная стартовая цена в окне SCALP.",
confidence=0.0,
payload={
"strategy": self.name,
"symbol": symbol,
**base_payload,
"prices": prices,
"entry_block_reason": "INVALID_WINDOW_PRICE",
"entry_block_message": "ошибка цены",
},
)
@@ -108,8 +119,7 @@ class ScalpStrategy:
direction_ratio = self._direction_ratio(prices, change_percent)
payload = {
"strategy": self.name,
"symbol": symbol,
**base_payload,
"first_price": first_price,
"current_price": last_price,
"change_percent": round(change_percent, 5),
@@ -141,11 +151,23 @@ class ScalpStrategy:
payload=payload,
)
expected_direction = "BUY" if change_percent >= 0 else "SELL"
entry_block_reason = (
"WEAK_UP_IMPULSE"
if expected_direction == "BUY"
else "WEAK_DOWN_IMPULSE"
)
return SignalResult(
signal=SignalType.HOLD,
reason="SCALP-импульс недостаточно сильный.",
confidence=0.0,
payload=payload,
payload={
**payload,
"entry_block_reason": entry_block_reason,
"entry_block_message": "слабый импульс",
"expected_direction": expected_direction,
},
)
def _direction_ratio(self, prices: list[float], change_percent: float) -> float:

View File

@@ -64,6 +64,8 @@ class TrendStrategy:
"symbol": context.symbol,
"error": str(exc),
"market_analysis": market.payload,
"entry_block_reason": "MARKET_SNAPSHOT_ERROR",
"entry_block_message": "нет данных рынка",
},
)
@@ -80,6 +82,8 @@ class TrendStrategy:
"symbol": symbol,
"snapshot": snapshot,
"market_analysis": market.payload,
"entry_block_reason": "INVALID_MARKET_PRICE",
"entry_block_message": "нет цены",
},
)
@@ -138,6 +142,8 @@ class TrendStrategy:
**base_payload,
"window_size": len(prices),
"required_window_size": self._window_size,
"entry_block_reason": "NOT_ENOUGH_LIVE_DATA",
"entry_block_message": "мало данных",
},
)
@@ -152,6 +158,8 @@ class TrendStrategy:
payload={
**base_payload,
"prices": prices,
"entry_block_reason": "INVALID_WINDOW_PRICE",
"entry_block_message": "ошибка цены",
},
)
@@ -185,7 +193,12 @@ class TrendStrategy:
signal=SignalType.HOLD,
reason="TREND_UP есть, но live-импульс вверх недостаточно сильный.",
confidence=0.0,
payload=payload,
payload={
**payload,
"entry_block_reason": "WEAK_UP_IMPULSE",
"entry_block_message": "слабый импульс",
"expected_direction": "BUY",
},
)
if market.state == MarketState.TREND_DOWN:
@@ -204,14 +217,23 @@ class TrendStrategy:
signal=SignalType.HOLD,
reason="TREND_DOWN есть, но live-импульс вниз недостаточно сильный.",
confidence=0.0,
payload=payload,
payload={
**payload,
"entry_block_reason": "WEAK_DOWN_IMPULSE",
"entry_block_message": "слабый импульс",
"expected_direction": "SELL",
},
)
return SignalResult(
signal=SignalType.HOLD,
reason=f"Market state не подходит для TREND: {market.state.value}.",
confidence=0.0,
payload=payload,
payload={
**payload,
"entry_block_reason": "MARKET_STATE_NOT_TREND",
"entry_block_message": "рынок флэт",
},
)
def _analysis_price(self, snapshot: dict[str, object]) -> float: