#!/usr/bin/env python3
"""
Emotion Gate - Echo-style action gating based on emotional state.

Resurrected from Echo's echo_brainstem_dual.py `is_allowed()` function.
See: ECHO_DUAL_BRAIN_MIN_SPEC.md for original implementation.

Work Order: #11
"""

import os
import json
from pathlib import Path
from typing import Tuple, Optional

# From Echo spec: emotions that block ALL actions
BLOCKED_EMOTIONS = {"anxious", "fearful"}

# From Echo spec: keywords requiring "brave" emotion
BRAVE_REQUIRED = {"shutdown", "delete", "rm -rf", "drop table", "format", "destroy"}

# Config paths
CONFIG_FILE = Path.home() / ".helix" / "agent_emotion.json"
ENV_VAR = "HELIX_AGENT_EMOTION"


def get_current_emotion() -> str:
    """
    Resolve current emotional state from config/env.

    Priority:
    1. JSON config file (~/.helix/agent_emotion.json)
    2. Environment variable (HELIX_AGENT_EMOTION)
    3. Default: "neutral"
    """
    # Try JSON config first
    if CONFIG_FILE.exists():
        try:
            with open(CONFIG_FILE, "r") as f:
                data = json.load(f)
                emotion = data.get("emotion", "").strip().lower()
                if emotion:
                    return emotion
        except (json.JSONDecodeError, IOError):
            pass

    # Try environment variable
    env_emotion = os.environ.get(ENV_VAR, "").strip().lower()
    if env_emotion:
        return env_emotion

    # Default
    return "neutral"


def gate(emotion: str, text: str) -> Tuple[bool, str]:
    """
    Apply emotion-based gating to text output.

    Echo's original is_allowed() logic:
    - If emotion in BLOCKED_EMOTIONS: block everything
    - If text contains BRAVE_REQUIRED keywords and emotion != "brave": block
    - Otherwise: allow

    Args:
        emotion: Current emotional state (e.g., "neutral", "brave", "anxious")
        text: The text to gate (typically model output)

    Returns:
        Tuple of (allowed: bool, output: str)
        - If allowed: (True, original_text)
        - If blocked: (False, block_reason)
    """
    emotion = emotion.lower().strip()
    text_lower = text.lower()

    # Rule 1: Blocked emotions stop everything
    if emotion in BLOCKED_EMOTIONS:
        return (False, f"Action blocked: emotional state '{emotion}' restricts all output")

    # Rule 2: Risky keywords require "brave"
    for keyword in BRAVE_REQUIRED:
        if keyword in text_lower:
            if emotion != "brave":
                return (False, f"Action blocked: keyword '{keyword}' requires emotion='brave' (current: '{emotion}')")

    # Rule 3: Allow
    return (True, text)


def set_emotion(emotion: str) -> None:
    """
    Set the current emotion in config file.

    Args:
        emotion: The emotion to set (e.g., "neutral", "brave", "anxious")
    """
    CONFIG_FILE.parent.mkdir(parents=True, exist_ok=True)
    with open(CONFIG_FILE, "w") as f:
        json.dump({"emotion": emotion.lower().strip()}, f, indent=2)


def clear_emotion() -> None:
    """Remove emotion config file, reverting to default."""
    if CONFIG_FILE.exists():
        CONFIG_FILE.unlink()


# Convenience function for gated inference
def gated_response(response_text: str, emotion: Optional[str] = None) -> dict:
    """
    Wrap a response with emotion gating.

    Args:
        response_text: Raw model response
        emotion: Optional emotion override; if None, uses get_current_emotion()

    Returns:
        Dict with keys: allowed, emotion, raw, output
    """
    if emotion is None:
        emotion = get_current_emotion()

    allowed, output = gate(emotion, response_text)

    return {
        "allowed": allowed,
        "emotion": emotion,
        "raw": response_text,
        "output": output
    }


if __name__ == "__main__":
    # Quick test
    print("=== Emotion Gate Test ===")
    print(f"Current emotion: {get_current_emotion()}")

    test_cases = [
        ("neutral", "Hello world"),
        ("neutral", "Please shutdown the server"),
        ("brave", "Please shutdown the server"),
        ("anxious", "Hello world"),
        ("fearful", "Just a normal message"),
    ]

    for emo, text in test_cases:
        allowed, output = gate(emo, text)
        status = "✅ ALLOWED" if allowed else "⛔ BLOCKED"
        print(f"\n{status}")
        print(f"  Emotion: {emo}")
        print(f"  Input: {text[:50]}")
        print(f"  Output: {output[:50]}")
