diff --git a/app/src/trading/execution/flip.py b/app/src/trading/execution/flip.py index 48ba95b..bb3a55d 100644 --- a/app/src/trading/execution/flip.py +++ b/app/src/trading/execution/flip.py @@ -14,7 +14,16 @@ from src.trading.auto.state_reset import ( reset_execution_block_state, ) from src.trading.execution.models import ExecutionDecision -from src.trading.execution.payloads import build_market_context_payload +from src.trading.execution.payloads import ( + build_adaptive_size_payload, + build_autonomous_payload, + build_execution_quality_payload, + build_market_context_payload, + build_position_health_payload, + build_position_intelligence_payload, + build_runtime_protection_payload, + build_signal_payload, +) from src.trading.execution.pricing import ExecutionPrice from src.trading.journal.service import JournalService from src.trading.position.state import PositionState @@ -116,11 +125,8 @@ class ExecutionFlipMixin(_ExecutionFlipProtocol): "execution_type": EXECUTION_TYPE_FLIP_REJECTED, "symbol": state.symbol, "position_side": position.side, - "signal": state.last_signal, - "confidence": state.last_signal_confidence, - "execution_confidence_score": state.execution_confidence_score, - "repeat_count": state.last_signal_repeat_count, - "reason": state.last_signal_reason, + **build_signal_payload(state), + **build_execution_quality_payload(state), "reject_reason": reason, "unrealized_pnl_usd": state.unrealized_pnl_usd, "entry_timing_state": state.entry_timing_state, @@ -143,11 +149,14 @@ class ExecutionFlipMixin(_ExecutionFlipProtocol): "execution_type": EXECUTION_TYPE_FLIP_BLOCKED, "symbol": state.symbol, "position_side": position.side, - "signal": state.last_signal, - "confidence": confidence, - "execution_confidence_score": state.execution_confidence_score, - "repeat_count": state.last_signal_repeat_count, - "reason": reason, + + **build_signal_payload( + state, + confidence=confidence, + reason=reason, + ), + **build_execution_quality_payload(state), + "unrealized_pnl_usd": state.unrealized_pnl_usd, **build_market_context_payload(state), "opened_at": position.opened_at, @@ -219,20 +228,9 @@ class ExecutionFlipMixin(_ExecutionFlipProtocol): "hold_seconds": metrics.hold_seconds, "overnight_count": metrics.overnight_count, - "signal": state.last_signal, - "confidence": state.last_signal_confidence, - "execution_confidence_score": state.execution_confidence_score, - "execution_confidence_level": state.execution_confidence_level, - "execution_confidence_reason": state.execution_confidence_reason, - "adaptive_size_multiplier": state.adaptive_size_multiplier, - "adaptive_size_reason": state.adaptive_size_reason, - "adaptive_size_factors": state.adaptive_size_factors, - "effective_risk_percent": state.effective_risk_percent, - "effective_target_risk_usd": state.effective_target_risk_usd, - "adaptive_size_base": state.adaptive_size_base, - "adaptive_size_final": state.adaptive_size_final, - "repeat_count": state.last_signal_repeat_count, - "reason": state.last_signal_reason, + **build_signal_payload(state), + **build_execution_quality_payload(state), + **build_adaptive_size_payload(state), "opened_at": old_opened_at, "new_opened_monotonic_at": opened_monotonic_at, "closed_at": now, @@ -240,46 +238,16 @@ class ExecutionFlipMixin(_ExecutionFlipProtocol): **build_market_context_payload(state), # ---------- Position health ---------- - "position_hold_seconds": state.position_hold_seconds, - "position_health_status": state.position_health_status, - "position_health_score": state.position_health_score, - "position_health_reason": state.position_health_reason, - "position_risk_level": state.position_risk_level, - "position_risk_reason": state.position_risk_reason, - "position_trend_alignment": state.position_trend_alignment, - "position_adverse_momentum": state.position_adverse_momentum, + **build_position_health_payload(state), # ---------- Position intelligence ---------- - "position_exit_signal": state.position_exit_signal, - "position_exit_confidence": state.position_exit_confidence, - "position_exit_urgency": state.position_exit_urgency, - "position_reversal_risk": state.position_reversal_risk, - "position_fatigue_state": state.position_fatigue_state, - "position_giveback_percent": state.position_giveback_percent, - "position_mfe_percent": state.position_mfe_percent, - "position_mae_percent": state.position_mae_percent, - "position_peak_pnl_usd": state.position_peak_pnl_usd, - "position_peak_pnl_percent": state.position_peak_pnl_percent, + **build_position_intelligence_payload(state), # ---------- Autonomous ---------- - "autonomous_action": state.autonomous_action, - "autonomous_action_reason": state.autonomous_action_reason, - "autonomous_action_confidence": state.autonomous_action_confidence, - "autonomous_protection_required": state.autonomous_protection_required, - "autonomous_reduce_required": state.autonomous_reduce_required, - "autonomous_exit_required": state.autonomous_exit_required, + **build_autonomous_payload(state), # ---------- Runtime protection ---------- - "position_protection_status": state.position_protection_status, - "position_protection_reason": state.position_protection_reason, - "runtime_protection_action": state.runtime_protection_action, - "runtime_protection_reason": state.runtime_protection_reason, - "break_even_armed": state.break_even_armed, - "break_even_price": state.break_even_price, - "profit_lock_active": state.profit_lock_active, - "profit_lock_price": state.profit_lock_price, - "trailing_stop_active": state.trailing_stop_active, - "trailing_stop_price": state.trailing_stop_price, + **build_runtime_protection_payload(state), "pricing": PRICING_FLIP_MODE, "exit_pricing_role": exit_execution.pricing_role, diff --git a/app/src/trading/execution/payloads.py b/app/src/trading/execution/payloads.py index eb81059..993662f 100644 --- a/app/src/trading/execution/payloads.py +++ b/app/src/trading/execution/payloads.py @@ -78,7 +78,6 @@ def build_market_context_payload(state: AutoTradeState) -> JsonDict: **build_market_runtime_payload(state), } - def build_runtime_payload(state: AutoTradeState) -> JsonDict: return { "status": state.status, @@ -87,12 +86,25 @@ def build_runtime_payload(state: AutoTradeState) -> JsonDict: } -def build_signal_payload(state: AutoTradeState) -> JsonDict: +def build_signal_payload( + state: AutoTradeState, + *, + confidence: float | None = None, + reason: str | None = None, +) -> JsonDict: return { "signal": state.last_signal, - "confidence": state.last_signal_confidence, + "confidence": ( + state.last_signal_confidence + if confidence is None + else confidence + ), "repeat_count": state.last_signal_repeat_count, - "reason": state.last_signal_reason, + "reason": ( + state.last_signal_reason + if reason is None + else reason + ), }