"""Tests for economy-state-guard.py — PreToolUse hook on Edit/Write/Bash/Agent."""
import json
import os
import subprocess
import sys
import tempfile

try:
    sys.stdout.reconfigure(encoding="utf-8")
except Exception:
    pass

SCRIPT = os.path.expanduser("~/.claude/hooks/economy-state-guard.py")


def run_guard(payload, state=None):
    sid = payload.get("session_id", "test-sid")
    state_path = os.path.join(tempfile.gettempdir(), f"claude-economy-{sid}.json")
    if state is None and os.path.exists(state_path):
        os.remove(state_path)
    if state is not None:
        with open(state_path, "w", encoding="utf-8") as f:
            json.dump(state, f)
    r = subprocess.run(
        ["python", SCRIPT],
        input=json.dumps(payload, ensure_ascii=False).encode("utf-8"),
        capture_output=True,
        timeout=5,
    )
    out = r.stdout.decode("utf-8", errors="replace")
    if state is not None and os.path.exists(state_path):
        os.remove(state_path)
    return out


def test_no_state_silent():
    out = run_guard({"session_id": "t1", "tool_name": "Edit",
                     "tool_input": {"file_path": "x.py"}})
    assert out.strip() == "", f"Expected silent, got: {out!r}"
    print("  PASS: no_state_silent")


def test_level_100_silent():
    out = run_guard({"session_id": "t2", "tool_name": "Edit",
                     "tool_input": {"file_path": "x.py"}},
                    state={"session_id": "t2", "level": 100, "label": "100%"})
    assert out.strip() == "", f"Expected silent at level 100, got: {out!r}"
    print("  PASS: level_100_silent")


def test_level_0_edit_emits_reminder():
    out = run_guard({"session_id": "t3", "tool_name": "Edit",
                     "tool_input": {"file_path": "x.php"}},
                    state={"session_id": "t3", "level": 0,
                           "label": "0%", "tail": "max quality"})
    assert "REMINDER" in out, f"Expected REMINDER, got: {out!r}"
    assert "0%" in out, f"Expected level mention, got: {out!r}"
    print("  PASS: level_0_edit_emits_reminder")


def test_level_75_bash_sed_emits_warning():
    out = run_guard({"session_id": "t4", "tool_name": "Bash",
                     "tool_input": {"command": "sed -i 's/old/new/' file.php"}},
                    state={"session_id": "t4", "level": 75, "label": "75%", "tail": ""})
    assert "WARNING" in out or "Bash" in out, f"Expected Bash warning, got: {out!r}"
    print("  PASS: level_75_bash_sed_emits_warning")


def test_level_50_bash_safe_no_warning():
    out = run_guard({"session_id": "t5", "tool_name": "Bash",
                     "tool_input": {"command": "git status"}},
                    state={"session_id": "t5", "level": 50, "label": "50%", "tail": ""})
    assert "WARNING" not in out, f"Expected no Bash warning on git status, got: {out!r}"
    print("  PASS: level_50_bash_safe_no_warning")


def test_agent_inherits_parent_state():
    out = run_guard({"session_id": "t6", "tool_name": "Agent",
                     "tool_input": {"description": "test", "prompt": "Do X"}},
                    state={"session_id": "t6", "level": 0, "label": "0%", "tail": "max"})
    assert "0%" in out or "PARENT" in out or "Inherited" in out, \
        f"Expected agent inherit, got: {out!r}"
    print("  PASS: agent_inherits_parent_state")


def test_level_5_edit_emits_reminder():
    out = run_guard({"session_id": "t7", "tool_name": "Edit",
                     "tool_input": {"file_path": "x.php"}},
                    state={"session_id": "t7", "level": 5,
                           "label": "5%", "tail": "качество 0% без избыточности"})
    assert "REMINDER" in out, f"Expected REMINDER, got: {out!r}"
    assert "5%" in out, f"Expected level mention, got: {out!r}"
    print("  PASS: level_5_edit_emits_reminder")


if __name__ == "__main__":
    test_no_state_silent()
    test_level_100_silent()
    test_level_0_edit_emits_reminder()
    test_level_75_bash_sed_emits_warning()
    test_level_50_bash_safe_no_warning()
    test_agent_inherits_parent_state()
    test_level_5_edit_emits_reminder()
    print("\n=== 7/7 PASSED ===")
