"""
Comprehensive Trade Logger.

Logs all trades with complete mathematical reasoning and decision logic.
Designed to capture every calculation involved in trade decisions for
analysis and model validation.

Output format is human-readable with full mathematical formulas shown.
"""
import json
import os
from dataclasses import dataclass, asdict
from datetime import datetime
from decimal import Decimal
from pathlib import Path
from typing import Any

from utils import get_logger


logger = get_logger("trade_logger")


@dataclass
class SpreadTradeLog:
    """Complete log entry for a spread arbitrage trade."""
    # Metadata
    timestamp: str
    trade_id: int
    trade_type: str = "SPREAD_ARBITRAGE"

    # Trade details
    symbol: str = ""
    buy_exchange: str = ""
    sell_exchange: str = ""
    direction: str = "BUY_LOW_SELL_HIGH"

    # Prices
    buy_price_ask: float = 0.0
    sell_price_bid: float = 0.0

    # Fee calculations
    buy_fee_pct: float = 0.0
    sell_fee_pct: float = 0.0
    effective_buy_price: float = 0.0
    effective_sell_price: float = 0.0

    # Spread calculations
    gross_spread_bps: float = 0.0
    net_spread_bps: float = 0.0
    spread_threshold_bps: float = 0.0

    # Position sizing
    trade_size_usd: float = 0.0
    quantity: float = 0.0

    # P&L
    gross_profit_usd: float = 0.0
    net_profit_usd: float = 0.0

    # Portfolio state
    portfolio_value_before: float = 0.0
    portfolio_value_after: float = 0.0
    total_pnl_usd: float = 0.0

    # Decision reasoning
    decision_reason: str = ""
    math_summary: str = ""


@dataclass
class LeadLagTradeLog:
    """Complete log entry for a lead-lag model trade."""
    # Metadata
    timestamp: str
    trade_id: int
    trade_type: str = "LEAD_LAG_SIGNAL"
    event_type: str = "OPEN"  # OPEN or CLOSE

    # Trade details
    symbol: str = ""
    exchange: str = ""
    direction: str = ""  # LONG or SHORT
    entry_price: float = 0.0
    close_price: float = 0.0

    # Leader (BTC) statistics
    btc_return_pct: float = 0.0
    btc_z_score: float = 0.0
    btc_z_threshold: float = 0.0

    # Lagger (altcoin) statistics
    altcoin_return_pct: float = 0.0
    altcoin_z_score: float = 0.0
    altcoin_z_threshold: float = 0.0

    # Expected vs actual
    expected_return_pct: float = 0.0
    return_gap_pct: float = 0.0
    gap_z_score: float = 0.0
    gap_threshold: float = 0.0

    # Model parameters
    rolling_beta: float = 0.0
    rolling_correlation: float = 0.0
    correlation_threshold: float = 0.0
    idiosyncratic_std: float = 0.0
    total_std: float = 0.0

    # Confidence calculation breakdown
    confidence_score: float = 0.0
    confidence_threshold: float = 0.0
    z_confidence: float = 0.0
    correlation_confidence: float = 0.0
    gap_confidence: float = 0.0
    time_confidence: float = 0.0

    # Timing
    time_since_btc_signal_ms: int = 0
    max_lag_ms: int = 0
    half_life_ms: int = 0
    max_hold_ms: int = 0
    position_duration_ms: int = 0

    # Position sizing
    trade_size_usd: float = 0.0

    # P&L (filled on close)
    actual_return_pct: float = 0.0
    pnl_usd: float = 0.0
    win_loss: str = ""

    # Portfolio state
    portfolio_value_before: float = 0.0
    portfolio_value_after: float = 0.0
    pending_positions: int = 0
    total_pnl_usd: float = 0.0

    # Decision reasoning
    decision_checks: dict = None
    decision_reason: str = ""
    math_summary: str = ""

    def __post_init__(self):
        if self.decision_checks is None:
            self.decision_checks = {}


class TradeLogger:
    """
    Comprehensive trade logger with full mathematical reasoning.

    Logs all trades to a structured log file with:
    - Complete price and spread calculations
    - All statistical parameters used in decisions
    - Mathematical formulas and their results
    - Portfolio state before/after each trade
    - Decision logic and threshold checks
    """

    def __init__(
        self,
        log_dir: str = "trade_logs",
        log_prefix: str = "trades",
        include_json: bool = True,
    ):
        """
        Initialize the trade logger.

        Args:
            log_dir: Directory for log files
            log_prefix: Prefix for log filenames
            include_json: Also write JSON format for programmatic analysis
        """
        self.log_dir = Path(log_dir)
        self.log_dir.mkdir(parents=True, exist_ok=True)

        self.include_json = include_json

        # Create log files with timestamp
        timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
        self.log_file = self.log_dir / f"{log_prefix}_{timestamp}.log"
        self.json_file = self.log_dir / f"{log_prefix}_{timestamp}.json"

        # Track trade counts
        self.spread_trade_count = 0
        self.lead_lag_trade_count = 0

        # JSON log buffer
        self._json_logs: list[dict] = []

        # Write header
        self._write_header()

        logger.info(f"Trade logger initialized: {self.log_file}")

    def _write_header(self) -> None:
        """Write log file header."""
        header = f"""
{'='*80}
TRADE LOG - Started {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}
{'='*80}

This log contains complete mathematical reasoning for all trades.
All calculations, thresholds, and decision logic are recorded for analysis.

Strategies:
  1. SPREAD_ARBITRAGE - Buy low on one exchange, sell high on another
  2. LEAD_LAG_SIGNAL - Predict altcoin moves from BTC signals

{'='*80}

"""
        with open(self.log_file, 'w') as f:
            f.write(header)

    def _write_to_file(self, content: str) -> None:
        """Append content to log file."""
        with open(self.log_file, 'a') as f:
            f.write(content)

    def _write_json(self, log_entry: dict) -> None:
        """Append to JSON log."""
        if not self.include_json:
            return

        self._json_logs.append(log_entry)

        # Write incrementally to avoid data loss
        with open(self.json_file, 'w') as f:
            json.dump(self._json_logs, f, indent=2, default=str)

    def log_spread_trade(
        self,
        spread_result,  # SpreadResult
        trade_size_usd: Decimal,
        quantity: Decimal,
        gross_profit_usd: Decimal,
        net_profit_usd: Decimal,
        portfolio_state: dict,
        fees: dict,
        threshold_bps: Decimal,
    ) -> None:
        """
        Log a spread arbitrage trade with complete mathematical details.

        Args:
            spread_result: The SpreadResult that triggered the trade
            trade_size_usd: Position size in USD
            quantity: Quantity of crypto traded
            gross_profit_usd: Profit before fees
            net_profit_usd: Profit after fees
            portfolio_state: Current portfolio metrics
            fees: Fee dictionary by exchange
            threshold_bps: Spread threshold that was met
        """
        self.spread_trade_count += 1
        timestamp = datetime.now()

        # Calculate effective prices
        buy_fee = float(fees.get(spread_result.buy_exchange, Decimal("0.001")))
        sell_fee = float(fees.get(spread_result.sell_exchange, Decimal("0.001")))
        effective_buy = float(spread_result.buy_price) * (1 + buy_fee)
        effective_sell = float(spread_result.sell_price) * (1 - sell_fee)

        portfolio_before = portfolio_state.get("total_pnl_usd", 0) + float(trade_size_usd) - float(net_profit_usd)
        portfolio_after = portfolio_state.get("total_pnl_usd", 0) + float(trade_size_usd)

        log_entry = SpreadTradeLog(
            timestamp=timestamp.isoformat(),
            trade_id=self.spread_trade_count,
            symbol=spread_result.symbol,
            buy_exchange=spread_result.buy_exchange,
            sell_exchange=spread_result.sell_exchange,
            buy_price_ask=float(spread_result.buy_price),
            sell_price_bid=float(spread_result.sell_price),
            buy_fee_pct=buy_fee * 100,
            sell_fee_pct=sell_fee * 100,
            effective_buy_price=effective_buy,
            effective_sell_price=effective_sell,
            gross_spread_bps=float(spread_result.gross_spread_bps),
            net_spread_bps=float(spread_result.spread_bps),
            spread_threshold_bps=float(threshold_bps),
            trade_size_usd=float(trade_size_usd),
            quantity=float(quantity),
            gross_profit_usd=float(gross_profit_usd),
            net_profit_usd=float(net_profit_usd),
            portfolio_value_before=portfolio_before,
            portfolio_value_after=portfolio_after,
            total_pnl_usd=portfolio_state.get("total_pnl_usd", 0),
        )

        # Build math summary
        log_entry.math_summary = self._build_spread_math_summary(log_entry)
        log_entry.decision_reason = self._build_spread_decision_reason(log_entry)

        # Write human-readable log
        self._write_spread_log(log_entry)

        # Write JSON
        self._write_json(asdict(log_entry))

    def _build_spread_math_summary(self, log: SpreadTradeLog) -> str:
        """Build mathematical summary for spread trade."""
        return f"""
SPREAD CALCULATION:
  Gross Spread = (Sell Bid - Buy Ask) / Buy Ask x 10,000
              = ({log.sell_price_bid:.4f} - {log.buy_price_ask:.4f}) / {log.buy_price_ask:.4f} x 10,000
              = {log.gross_spread_bps:.2f} bps

FEE-ADJUSTED PRICES:
  Effective Buy  = Ask x (1 + fee) = {log.buy_price_ask:.4f} x (1 + {log.buy_fee_pct/100:.4f}) = {log.effective_buy_price:.4f}
  Effective Sell = Bid x (1 - fee) = {log.sell_price_bid:.4f} x (1 - {log.sell_fee_pct/100:.4f}) = {log.effective_sell_price:.4f}

NET SPREAD:
  Net Spread = (Effective Sell - Effective Buy) / Effective Buy x 10,000
            = ({log.effective_sell_price:.4f} - {log.effective_buy_price:.4f}) / {log.effective_buy_price:.4f} x 10,000
            = {log.net_spread_bps:.2f} bps

POSITION SIZING:
  Trade Size = ${log.trade_size_usd:.2f}
  Quantity   = Trade Size / Buy Price = ${log.trade_size_usd:.2f} / {log.buy_price_ask:.4f} = {log.quantity:.8f}

PROFIT CALCULATION:
  Gross Profit = (Sell - Buy) x Quantity = ({log.sell_price_bid:.4f} - {log.buy_price_ask:.4f}) x {log.quantity:.8f} = ${log.gross_profit_usd:.4f}
  Net Profit   = Trade Size x (Net Spread / 10,000) = ${log.trade_size_usd:.2f} x ({log.net_spread_bps:.2f} / 10,000) = ${log.net_profit_usd:.4f}
"""

    def _build_spread_decision_reason(self, log: SpreadTradeLog) -> str:
        """Build decision reasoning for spread trade."""
        return f"""
DECISION: EXECUTE SPREAD ARBITRAGE

THRESHOLD CHECK:
  Net Spread ({log.net_spread_bps:.2f} bps) >= Threshold ({log.spread_threshold_bps:.2f} bps): PASSED

TRADE RATIONALE:
  - {log.symbol} is cheaper on {log.buy_exchange} (ask: {log.buy_price_ask:.4f})
  - {log.symbol} is more expensive on {log.sell_exchange} (bid: {log.sell_price_bid:.4f})
  - After accounting for {log.buy_fee_pct:.2f}% buy fee and {log.sell_fee_pct:.2f}% sell fee
  - Net profit opportunity: {log.net_spread_bps:.2f} basis points = ${log.net_profit_usd:.4f}
"""

    def _write_spread_log(self, log: SpreadTradeLog) -> None:
        """Write spread trade to log file."""
        content = f"""
{'='*80}
TRADE #{log.trade_id} - {log.trade_type}
{'='*80}
Timestamp: {log.timestamp}
Symbol:    {log.symbol}
Route:     BUY {log.buy_exchange} @ {log.buy_price_ask:.4f} -> SELL {log.sell_exchange} @ {log.sell_price_bid:.4f}

{log.math_summary}
{log.decision_reason}

PORTFOLIO UPDATE:
  Before: ${log.portfolio_value_before:.2f}
  After:  ${log.portfolio_value_after:.2f}
  Change: ${log.net_profit_usd:+.4f}
  Total P&L: ${log.total_pnl_usd:.2f}

{'='*80}

"""
        self._write_to_file(content)

    def log_lead_lag_open(
        self,
        signal,  # LeadLagSignal
        trade_size_usd: Decimal,
        portfolio_state: dict,
        stats: dict,  # EMAStats data
        config: dict,  # LeadLagConfig thresholds
    ) -> None:
        """
        Log a lead-lag position opening with complete mathematical details.

        Args:
            signal: The LeadLagSignal that triggered the trade
            trade_size_usd: Position size in USD
            portfolio_state: Current portfolio metrics
            stats: Statistics from EMAStats (beta, correlation, std, etc.)
            config: Configuration thresholds
        """
        self.lead_lag_trade_count += 1
        timestamp = datetime.now()

        log_entry = LeadLagTradeLog(
            timestamp=timestamp.isoformat(),
            trade_id=self.lead_lag_trade_count,
            event_type="OPEN",
            symbol=signal.lagger_symbol,
            exchange=signal.exchange,
            direction=signal.direction.value.upper(),
            entry_price=signal.entry_price,
            btc_return_pct=signal.leader_return_pct,
            btc_z_score=signal.leader_z_score,
            btc_z_threshold=config.get("leader_z_threshold", 2.0),
            altcoin_return_pct=signal.lagger_return_pct,
            expected_return_pct=signal.expected_return_pct,
            return_gap_pct=signal.return_gap_pct,
            rolling_beta=signal.rolling_beta,
            rolling_correlation=signal.rolling_correlation,
            correlation_threshold=config.get("min_correlation", 0.5),
            confidence_score=signal.confidence,
            confidence_threshold=config.get("min_confidence", 0.6),
            gap_threshold=config.get("gap_threshold", 1.5),
            max_lag_ms=config.get("max_lag_ms", 60000),
            half_life_ms=signal.max_hold_ms // 2,  # Approximate
            max_hold_ms=signal.max_hold_ms,
            trade_size_usd=float(trade_size_usd),
            portfolio_value_before=float(trade_size_usd) + portfolio_state.get("total_pnl_usd", 0),
            pending_positions=portfolio_state.get("pending_positions", 0) + 1,
            total_pnl_usd=portfolio_state.get("total_pnl_usd", 0),
            idiosyncratic_std=stats.get("idiosyncratic_std", 0),
            total_std=stats.get("total_std", 0),
        )

        # Calculate confidence breakdown
        log_entry.z_confidence = min(abs(signal.leader_z_score) / 3.0, 1.0)
        log_entry.correlation_confidence = min(abs(signal.rolling_correlation) / 0.8, 1.0)
        log_entry.gap_confidence = min(abs(signal.return_gap_pct) / 0.03, 1.0)  # Approximate normalization

        # Decision checks
        log_entry.decision_checks = {
            "btc_moved_significantly": abs(signal.leader_z_score) >= config.get("leader_z_threshold", 2.0),
            "correlation_strong": abs(signal.rolling_correlation) >= config.get("min_correlation", 0.5),
            "confidence_high": signal.confidence >= config.get("min_confidence", 0.6),
        }

        # Build summaries
        log_entry.math_summary = self._build_lead_lag_math_summary(log_entry, signal)
        log_entry.decision_reason = self._build_lead_lag_decision_reason(log_entry, signal)

        # Write logs
        self._write_lead_lag_log(log_entry)
        self._write_json(asdict(log_entry))

    def _build_lead_lag_math_summary(self, log: LeadLagTradeLog, signal) -> str:
        """Build mathematical summary for lead-lag trade."""
        idio_ratio = log.idiosyncratic_std / log.total_std if log.total_std > 0 else 0

        return f"""
LEADER (BTC) ANALYSIS:
  BTC Return = {log.btc_return_pct:.4f}%
  BTC Z-Score = (Return - Mean) / Std = {log.btc_z_score:.4f}
  Z-Score Threshold = {log.btc_z_threshold:.2f}
  Assessment: BTC made a {'SIGNIFICANT' if abs(log.btc_z_score) >= log.btc_z_threshold else 'minor'} move

BETA & CORRELATION:
  Rolling Beta (beta) = Cov(R_alt, R_btc) / Var(R_btc) = {log.rolling_beta:.4f}
  Rolling Correlation (rho) = Cov / (Std_alt x Std_btc) = {log.rolling_correlation:.4f}
  Correlation Threshold = {log.correlation_threshold:.2f}

EXPECTED RETURN CALCULATION:
  Expected Altcoin Return = beta x BTC Return
                        = {log.rolling_beta:.4f} x {log.btc_return_pct:.4f}%
                        = {log.expected_return_pct:.4f}%

RETURN GAP ANALYSIS:
  Actual Altcoin Return = {log.altcoin_return_pct:.4f}%
  Return Gap = Expected - Actual = {log.expected_return_pct:.4f}% - {log.altcoin_return_pct:.4f}% = {log.return_gap_pct:.4f}%

IDIOSYNCRATIC VOLATILITY:
  Total Std (sigma_total) = {log.total_std:.6f}
  Idiosyncratic Std (sigma_eps) = sigma_total x sqrt(1 - rho^2)
                               = {log.total_std:.6f} x sqrt(1 - {log.rolling_correlation:.4f}^2)
                               = {log.idiosyncratic_std:.6f}
  Note: sigma_eps is {idio_ratio*100:.1f}% of sigma_total (using total would miss {(1-idio_ratio)*100:.0f}% of trades)

CONFIDENCE CALCULATION:
  Z-Confidence = min(|BTC_Z| / 3.0, 1.0) = min({abs(log.btc_z_score):.4f} / 3.0, 1.0) = {log.z_confidence:.4f}
  Corr-Confidence = min(|rho| / 0.8, 1.0) = min({abs(log.rolling_correlation):.4f} / 0.8, 1.0) = {log.correlation_confidence:.4f}
  Gap-Confidence = min(|gap_z| / 3.0, 1.0) = {log.gap_confidence:.4f}

  Combined Confidence = (Z x Corr x Gap x Time)^0.25 = {log.confidence_score:.4f}
  Confidence Threshold = {log.confidence_threshold:.2f}

TIMING:
  Max Lag Window = {log.max_lag_ms}ms ({log.max_lag_ms/1000:.0f}s)
  Half-Life = {log.half_life_ms}ms ({log.half_life_ms/1000:.1f}s)
  Max Hold Time = 2 x Half-Life = {log.max_hold_ms}ms ({log.max_hold_ms/1000:.1f}s)
"""

    def _build_lead_lag_decision_reason(self, log: LeadLagTradeLog, signal) -> str:
        """Build decision reasoning for lead-lag trade."""
        checks = log.decision_checks
        all_passed = all(checks.values())

        check_results = []
        for check, passed in checks.items():
            status = "PASSED" if passed else "FAILED"
            check_results.append(f"  - {check.replace('_', ' ').title()}: {status}")

        direction_reason = (
            f"Altcoin is UNDERVALUED - expected to RISE toward fair value"
            if log.direction == "LONG"
            else f"Altcoin is OVERVALUED - expected to FALL toward fair value"
        )

        return f"""
DECISION: OPEN {log.direction} POSITION

THRESHOLD CHECKS:
{chr(10).join(check_results)}

TRADE RATIONALE:
  1. BTC moved significantly (Z={log.btc_z_score:.2f}, threshold={log.btc_z_threshold:.2f})
  2. {log.symbol} has strong correlation with BTC (rho={log.rolling_correlation:.4f})
  3. {log.symbol} hasn't fully responded yet (actual={log.altcoin_return_pct:.4f}%, expected={log.expected_return_pct:.4f}%)
  4. {direction_reason}
  5. Confidence score ({log.confidence_score:.2f}) exceeds threshold ({log.confidence_threshold:.2f})

POSITION:
  Direction: {log.direction} {log.symbol} @ {log.exchange}
  Entry Price: ${log.entry_price:.4f}
  Trade Size: ${log.trade_size_usd:.2f}
  Max Hold Time: {log.max_hold_ms/1000:.1f}s (based on mean-reversion half-life)
"""

    def _write_lead_lag_log(self, log: LeadLagTradeLog) -> None:
        """Write lead-lag trade to log file."""
        content = f"""
{'='*80}
TRADE #{log.trade_id} - {log.trade_type} - {log.event_type}
{'='*80}
Timestamp: {log.timestamp}
Symbol:    {log.symbol} @ {log.exchange}
Direction: {log.direction}
Price:     ${log.entry_price:.4f}

{log.math_summary}
{log.decision_reason}

PORTFOLIO STATE:
  Trade Size: ${log.trade_size_usd:.2f}
  Portfolio Value: ${log.portfolio_value_before:.2f}
  Pending Positions: {log.pending_positions}
  Total P&L: ${log.total_pnl_usd:.2f}

{'='*80}

"""
        self._write_to_file(content)

    def log_lead_lag_close(
        self,
        trade_id: int,
        symbol: str,
        exchange: str,
        direction: str,
        entry_price: float,
        close_price: float,
        trade_size_usd: float,
        expected_return_pct: float,
        actual_return_pct: float,
        pnl_usd: float,
        position_duration_ms: int,
        portfolio_state: dict,
    ) -> None:
        """
        Log a lead-lag position closing with P&L analysis.
        """
        timestamp = datetime.now()
        win_loss = "WIN" if pnl_usd > 0 else "LOSS" if pnl_usd < 0 else "BREAKEVEN"

        log_entry = LeadLagTradeLog(
            timestamp=timestamp.isoformat(),
            trade_id=trade_id,
            event_type="CLOSE",
            symbol=symbol,
            exchange=exchange,
            direction=direction,
            entry_price=entry_price,
            close_price=close_price,
            trade_size_usd=trade_size_usd,
            expected_return_pct=expected_return_pct,
            actual_return_pct=actual_return_pct,
            pnl_usd=pnl_usd,
            win_loss=win_loss,
            position_duration_ms=position_duration_ms,
            portfolio_value_after=trade_size_usd + portfolio_state.get("total_pnl_usd", 0),
            pending_positions=portfolio_state.get("pending_positions", 0),
            total_pnl_usd=portfolio_state.get("total_pnl_usd", 0),
        )

        # Build close summary
        log_entry.math_summary = self._build_close_math_summary(log_entry)
        log_entry.decision_reason = self._build_close_analysis(log_entry)

        # Write logs
        self._write_close_log(log_entry)
        self._write_json(asdict(log_entry))

    def _build_close_math_summary(self, log: LeadLagTradeLog) -> str:
        """Build mathematical summary for position close."""
        if log.direction == "LONG":
            formula = f"P&L = Size x (Exit - Entry) / Entry = ${log.trade_size_usd:.2f} x ({log.close_price:.4f} - {log.entry_price:.4f}) / {log.entry_price:.4f}"
        else:
            formula = f"P&L = Size x (Entry - Exit) / Entry = ${log.trade_size_usd:.2f} x ({log.entry_price:.4f} - {log.close_price:.4f}) / {log.entry_price:.4f}"

        return f"""
POSITION OUTCOME:
  Entry Price: ${log.entry_price:.4f}
  Exit Price:  ${log.close_price:.4f}
  Price Change: {((log.close_price - log.entry_price) / log.entry_price * 100):+.4f}%

P&L CALCULATION ({log.direction}):
  {formula}
  P&L = ${log.pnl_usd:+.4f}

EXPECTED VS ACTUAL:
  Expected Return: {log.expected_return_pct:+.4f}%
  Actual Return:   {log.actual_return_pct:+.4f}%
  Difference:      {(log.actual_return_pct - log.expected_return_pct):+.4f}%

TIMING:
  Position Duration: {log.position_duration_ms}ms ({log.position_duration_ms/1000:.1f}s)
"""

    def _build_close_analysis(self, log: LeadLagTradeLog) -> str:
        """Build analysis for position close."""
        prediction_accuracy = "accurate" if abs(log.actual_return_pct - log.expected_return_pct) < 0.05 else "inaccurate"

        return f"""
TRADE RESULT: {log.win_loss}

ANALYSIS:
  - Model prediction was {prediction_accuracy}
  - Expected {log.expected_return_pct:+.4f}%, got {log.actual_return_pct:+.4f}%
  - Net P&L: ${log.pnl_usd:+.4f} on ${log.trade_size_usd:.2f} position ({log.pnl_usd/log.trade_size_usd*100:+.2f}%)
"""

    def _write_close_log(self, log: LeadLagTradeLog) -> None:
        """Write position close to log file."""
        content = f"""
{'-'*80}
POSITION CLOSE - Trade #{log.trade_id} - {log.win_loss}
{'-'*80}
Timestamp: {log.timestamp}
Symbol:    {log.symbol} @ {log.exchange}
Direction: {log.direction}

{log.math_summary}
{log.decision_reason}

PORTFOLIO UPDATE:
  Portfolio Value: ${log.portfolio_value_after:.2f}
  Pending Positions: {log.pending_positions}
  Total P&L: ${log.total_pnl_usd:.2f}

{'-'*80}

"""
        self._write_to_file(content)

    def log_summary(self, portfolio_state: dict) -> None:
        """Write a summary of all trading activity."""
        timestamp = datetime.now()

        spread_pnl = portfolio_state.get("spread_pnl_usd", 0)
        lead_lag_pnl = portfolio_state.get("lead_lag_pnl_usd", 0)
        total_pnl = portfolio_state.get("total_pnl_usd", 0)
        win_rate = portfolio_state.get("win_rate", 0)

        content = f"""

{'#'*80}
TRADING SESSION SUMMARY - {timestamp.strftime('%Y-%m-%d %H:%M:%S')}
{'#'*80}

TRADE COUNTS:
  Spread Arbitrage Trades: {self.spread_trade_count}
  Lead-Lag Signal Trades:  {self.lead_lag_trade_count}
  Total Trades:            {self.spread_trade_count + self.lead_lag_trade_count}

P&L SUMMARY:
  Spread Arbitrage P&L: ${spread_pnl:.4f}
  Lead-Lag Model P&L:   ${lead_lag_pnl:.4f}
  Total P&L:            ${total_pnl:.4f}

LEAD-LAG PERFORMANCE:
  Win Rate: {win_rate:.1f}%
  Trades Closed: {portfolio_state.get('lead_lag_trades_closed', 0)}
  Trades Won: {portfolio_state.get('lead_lag_wins', 0)}

PORTFOLIO:
  Trade Size: ${portfolio_state.get('trade_size_usd', 0):.2f}
  Final Value: ${portfolio_state.get('trade_size_usd', 0) + total_pnl:.2f}

{'#'*80}

"""
        self._write_to_file(content)
        logger.info(f"Trade log summary written to {self.log_file}")
