#!/usr/bin/env python3
"""orphan-watchdog.py 테스트 (TDD)"""

import importlib.util
import json
from datetime import datetime, timedelta
from pathlib import Path

# 파일명에 하이픈이 포함되어 있어 importlib로 직접 로드한다.
_SCRIPT_PATH = Path(__file__).parent.parent / "scripts" / "orphan-watchdog.py"
_spec = importlib.util.spec_from_file_location("orphan_watchdog", _SCRIPT_PATH)
_mod = importlib.util.module_from_spec(_spec)  # type: ignore[arg-type]
_spec.loader.exec_module(_mod)  # type: ignore[union-attr]
detect_zombies = _mod.detect_zombies


def _make_timer_file(tmp_path: Path, tasks: dict) -> Path:
    """임시 task-timers.json 파일을 생성한다."""
    timer_file = tmp_path / "task-timers.json"
    timer_file.write_text(json.dumps({"tasks": tasks}), encoding="utf-8")
    return timer_file


def _iso(dt: datetime) -> str:
    return dt.isoformat()


def test_no_zombies(tmp_path: Path) -> None:
    """모든 태스크가 completed 상태이면 zombies 리스트는 비어있다."""
    now = datetime.now()
    tasks = {
        "task-1.1": {
            "task_id": "task-1.1",
            "team_id": "dev1-team",
            "start_time": _iso(now - timedelta(minutes=90)),
            "status": "completed",
        },
        "task-1.2": {
            "task_id": "task-1.2",
            "team_id": "dev2-team",
            "start_time": _iso(now - timedelta(minutes=120)),
            "status": "completed",
        },
    }
    timer_file = _make_timer_file(tmp_path, tasks)
    result = detect_zombies(timer_file=timer_file)

    assert result["zombies"] == []
    assert result["total"] == 0
    assert "checked_at" in result


def test_detect_zombie(tmp_path: Path) -> None:
    """'started' 상태이고 90분 경과한 태스크는 zombies에 포함된다."""
    now = datetime.now()
    start = now - timedelta(minutes=90)
    tasks = {
        "task-414.1": {
            "task_id": "task-414.1",
            "team_id": "dev1-team",
            "description": "좀비 태스크",
            "start_time": _iso(start),
            "status": "started",
        }
    }
    timer_file = _make_timer_file(tmp_path, tasks)
    result = detect_zombies(timer_file=timer_file)

    assert result["total"] == 1
    zombie = result["zombies"][0]
    assert zombie["task_id"] == "task-414.1"
    assert zombie["team_id"] == "dev1-team"
    assert zombie["elapsed_minutes"] >= 90
    assert zombie["start_time"] == _iso(start)


def test_running_status_also_detected(tmp_path: Path) -> None:
    """'running' 상태도 started와 동일하게 좀비로 감지된다."""
    now = datetime.now()
    tasks = {
        "task-500.1": {
            "task_id": "task-500.1",
            "team_id": "dev3-team",
            "start_time": _iso(now - timedelta(minutes=75)),
            "status": "running",
        }
    }
    timer_file = _make_timer_file(tmp_path, tasks)
    result = detect_zombies(timer_file=timer_file)

    assert result["total"] == 1
    assert result["zombies"][0]["task_id"] == "task-500.1"
    assert result["zombies"][0]["elapsed_minutes"] >= 75


def test_within_threshold_not_zombie(tmp_path: Path) -> None:
    """started 상태이지만 30분밖에 경과하지 않은 태스크는 zombies에 포함되지 않는다."""
    now = datetime.now()
    tasks = {
        "task-600.1": {
            "task_id": "task-600.1",
            "team_id": "dev2-team",
            "start_time": _iso(now - timedelta(minutes=30)),
            "status": "started",
        }
    }
    timer_file = _make_timer_file(tmp_path, tasks)
    result = detect_zombies(timer_file=timer_file)

    assert result["zombies"] == []
    assert result["total"] == 0


def test_file_not_exists(tmp_path: Path) -> None:
    """task-timers.json 파일이 없으면 빈 결과를 반환한다."""
    non_existent = tmp_path / "no-such-file.json"
    result = detect_zombies(timer_file=non_existent)

    assert result["zombies"] == []
    assert result["total"] == 0
    assert "checked_at" in result


def test_custom_threshold(tmp_path: Path) -> None:
    """threshold_minutes 파라미터로 임계값을 조정할 수 있다."""
    now = datetime.now()
    tasks = {
        "task-700.1": {
            "task_id": "task-700.1",
            "team_id": "dev1-team",
            "start_time": _iso(now - timedelta(minutes=45)),
            "status": "started",
        }
    }
    timer_file = _make_timer_file(tmp_path, tasks)

    # 기본 임계값(60분)에서는 좀비 아님
    result_default = detect_zombies(timer_file=timer_file, threshold_minutes=60)
    assert result_default["total"] == 0

    # 30분 임계값에서는 좀비 감지
    result_custom = detect_zombies(timer_file=timer_file, threshold_minutes=30)
    assert result_custom["total"] == 1
    assert result_custom["zombies"][0]["task_id"] == "task-700.1"
