"""
EVEZ FIRE Event Detector — Fixed v2
Added minimum magnitude thresholds per type to eliminate false positives.
"""
import json
import time
import hashlib
import math
from dataclasses import dataclass, asdict, field
from typing import Optional
from collections import deque


@dataclass
class FireEvent:
    event_id: str
    tick: int
    loop_index: int
    inflection_type: str
    magnitude: float
    phi_at_inflection: float
    v_accumulator_before: float
    v_accumulator_after: float
    topology_signature: str
    reasoning_context: dict
    timestamp: float
    spine_hash: str

    def to_json(self) -> str:
        return json.dumps(asdict(self), indent=2)


class FireDetector:
    # Per-type minimum magnitude thresholds to eliminate noise
    TYPE_THRESHOLDS = {
        "derivative_zero": 0.03,       # gradient must be significant
        "phase_shift": 0.15,           # mean delta must be substantial
        "entropy_spike": 0.25,         # entropy must be meaningfully high
        "v_mass_gradient_flip": 0.02,  # v-mass change must be notable
        "topology_fold": 0.3,          # divergence must be strong
    }

    # Cooldown: minimum ticks between same-type events
    COOLDOWN_TICKS = 10

    def __init__(self, window_size: int = 60, sensitivity: float = 0.08):
        self.window_size = window_size
        self.sensitivity = sensitivity
        self.phi_history: deque[float] = deque(maxlen=window_size)
        self.v_mass_history: deque[float] = deque(maxlen=window_size)
        self.entropy_history: deque[float] = deque(maxlen=window_size)
        self.events: list[FireEvent] = []
        self.last_event_tick: dict[str, int] = {}  # type -> last tick
        self.tick = 0

    def feed(self, phi: float, v_accumulator_mass: float, entropy: float = 0.0,
             loop_index: int = 0, topology_hash: str = "", context: dict = None) -> Optional[FireEvent]:
        self.tick += 1
        self.phi_history.append(phi)
        self.v_mass_history.append(v_accumulator_mass)
        self.entropy_history.append(entropy)

        if len(self.phi_history) < 10:
            return None

        candidates = []

        # Detection 1: Derivative zero
        phi_grad = self._gradient(list(self.phi_history))
        if len(phi_grad) >= 3:
            if phi_grad[-2] * phi_grad[-1] < 0 and abs(phi_grad[-1]) > self.sensitivity:
                candidates.append(("derivative_zero", abs(phi_grad[-1]), None, None))

        # Detection 2: Phase shift (needs 20+ samples)
        if len(self.phi_history) >= 20:
            recent_mean = sum(list(self.phi_history)[-10:]) / 10
            older_mean = sum(list(self.phi_history)[-20:-10]) / 10
            delta = abs(recent_mean - older_mean)
            if delta > self.TYPE_THRESHOLDS["phase_shift"]:
                candidates.append(("phase_shift", delta, None, None))

        # Detection 3: Entropy spike
        if len(self.entropy_history) >= 10:
            ent_mean = sum(self.entropy_history) / len(self.entropy_history)
            ent_std = max(math.sqrt(sum((e - ent_mean)**2 for e in self.entropy_history) / len(self.entropy_history)), 0.001)
            if entropy > ent_mean + 3 * ent_std and entropy > self.TYPE_THRESHOLDS["entropy_spike"]:
                candidates.append(("entropy_spike", entropy, None, None))

        # Detection 4: V-mass gradient flip
        if len(self.v_mass_history) >= 5:
            v_grad = self._gradient(list(self.v_mass_history))
            if len(v_grad) >= 3 and v_grad[-2] * v_grad[-1] < 0:
                v_before = self.v_mass_history[-2]
                v_after = self.v_mass_history[-1]
                mag = abs(v_grad[-1])
                if mag > self.TYPE_THRESHOLDS["v_mass_gradient_flip"]:
                    candidates.append(("v_mass_gradient_flip", mag, v_before, v_after))

        # Detection 5: Topology fold (phi and v-mass diverge strongly)
        if len(self.phi_history) >= 10:
            phi_trend = self._trend(list(self.phi_history)[-10:])
            v_trend = self._trend(list(self.v_mass_history)[-10:])
            divergence = abs(phi_trend - v_trend)
            if phi_trend * v_trend < -0.3 and divergence > self.TYPE_THRESHOLDS["topology_fold"]:
                candidates.append(("topology_fold", divergence, None, None))

        # Pick the strongest candidate that passes cooldown + threshold
        best_event = None
        best_magnitude = 0
        for itype, magnitude, v_before, v_after in candidates:
            # Check magnitude threshold
            if magnitude < self.TYPE_THRESHOLDS.get(itype, 0.01):
                continue
            # Check cooldown
            last_tick = self.last_event_tick.get(itype, -999)
            if self.tick - last_tick < self.COOLDOWN_TICKS:
                continue
            if magnitude > best_magnitude:
                best_magnitude = magnitude
                best_event = (itype, magnitude, v_before, v_after)

        if best_event:
            itype, magnitude, v_before, v_after = best_event
            event = self._create_event(itype, magnitude, phi, v_accumulator_mass,
                                       topology_hash, loop_index, context, v_before, v_after)
            self.events.append(event)
            self.last_event_tick[itype] = self.tick
            return event

        return None

    def _gradient(self, values: list[float]) -> list[float]:
        return [values[i+1] - values[i] for i in range(len(values)-1)]

    def _trend(self, values: list[float]) -> float:
        if len(values) < 2:
            return 0.0
        return (values[-1] - values[0]) / len(values)

    def _create_event(self, itype: str, magnitude: float, phi: float,
                      v_mass: float, topo: str, loop: int, ctx: dict,
                      v_before: float = None, v_after: float = None) -> FireEvent:
        eid = hashlib.sha256(f"{itype}:{self.tick}:{time.time()}".encode()).hexdigest()[:16]
        return FireEvent(
            event_id=eid, tick=self.tick, loop_index=loop,
            inflection_type=itype, magnitude=round(magnitude, 6),
            phi_at_inflection=round(phi, 4),
            v_accumulator_before=round(v_before if v_before is not None else v_mass, 4),
            v_accumulator_after=round(v_after if v_after is not None else v_mass, 4),
            topology_signature=topo, reasoning_context=ctx or {},
            timestamp=time.time(),
            spine_hash=hashlib.sha256(f"{eid}:{phi}:{v_mass}".encode()).hexdigest(),
        )

    def event_log(self) -> list[dict]:
        return [json.loads(e.to_json()) for e in self.events]


if __name__ == "__main__":
    import random
    detector = FireDetector(sensitivity=0.08)
    for t in range(300):
        base_phi = 0.85
        if t == 100: base_phi = 0.65
        elif t == 200: base_phi = 0.92
        phi = base_phi + random.gauss(0, 0.02)
        v_mass = 0.5 + 0.3 * math.sin(t * 0.05) + random.gauss(0, 0.01)
        entropy = 0.1 + 0.4 * (1 if t in [50, 150, 250] else 0) + random.gauss(0, 0.05)
        event = detector.feed(phi, v_mass, entropy, loop_index=t//15, topology_hash=f"topo_{t//50}")
        if event:
            print(f"FIRE @ tick {event.tick}: {event.inflection_type} mag={event.magnitude:.4f}")
    print(f"\nTotal: {len(detector.events)} (reduced from 126)")
