"""
reentry.py

[2026-09-23] Entry selectivity after a losing trade in the same symbol.
Backtest finding (09-18..09-23, 144 baseline trades): re-entries into a
symbol right after a LOSING trade won 21% of the time for -$262, while
re-entries after a winner won 59% for +$173 and brand-new symbols were
net positive. The user's read: slot-refill losses are an entry-selection
problem, not an exit problem.

Modes (trading.reentry_after_loss.mode):
  "off"          no restriction (previous behavior)
  "block"        after a losing trade, no new entry in that symbol today
  "above_entry"  after a losing trade, re-entry only once price trades
                 above that losing trade's entry price + buffer (the stock
                 has recovered past where it beat us)
Only the symbol's MOST RECENT closed trade is checked, so a later
winning trade in the symbol lifts the restriction.
"""

DEFAULT = {"mode": "off", "buffer_cents": 1.0}


def check(symbol: str, price: float, last_trade: dict, cfg: dict):
    """last_trade: the symbol's most recent CLOSED trade today (dict with
    entry_price, pl_dollars), or None. Returns (allowed, reason)."""
    cfg = {**DEFAULT, **(cfg or {})}
    if cfg["mode"] == "off" or not last_trade or last_trade.get("pl_dollars", 0) > 0:
        return True, ""
    if cfg["mode"] == "block":
        return False, f"re-entry blocked: last {symbol} trade lost ${last_trade['pl_dollars']:.2f}"
    need = last_trade["entry_price"] + cfg["buffer_cents"] / 100.0
    if price > need:
        return True, ""
    return False, (f"re-entry after a ${last_trade['pl_dollars']:.2f} loss needs price > "
                   f"{need:.2f} (last entry {last_trade['entry_price']:.2f})")
