from __future__ import annotations

import json
from pathlib import Path

from worai.update import (
    CACHE_TTL_SECONDS,
    check_for_update,
    command_to_string,
    is_newer_version,
)


def test_is_newer_version_handles_semver_like_values() -> None:
    assert is_newer_version("3.1.0", "3.0.1")
    assert not is_newer_version("3.0.1", "3.0.1rc1")
    assert not is_newer_version("3.0.1", "3.0.1")
    assert not is_newer_version("3.0.0", "3.0.1")


def test_check_for_update_uses_fresh_cache(tmp_path: Path) -> None:
    cache_path = tmp_path / "update-check.json"
    cache_path.write_text(
        json.dumps({"checked_at": 1000.0, "latest_version": "3.1.0"}),
        encoding="utf-8",
    )

    def _failing_fetcher(_timeout: float) -> str | None:
        raise AssertionError("network fetcher should not be called when cache is fresh")

    result = check_for_update(
        current_version="3.0.1",
        cache_path=cache_path,
        now_ts=1000.0 + (CACHE_TTL_SECONDS / 2),
        fetcher=_failing_fetcher,
    )

    assert result.used_cache is True
    assert result.latest_version == "3.1.0"
    assert result.update_available is True


def test_check_for_update_refreshes_stale_cache(tmp_path: Path) -> None:
    cache_path = tmp_path / "update-check.json"
    cache_path.write_text(
        json.dumps({"checked_at": 1000.0, "latest_version": "3.0.2"}),
        encoding="utf-8",
    )

    result = check_for_update(
        current_version="3.0.1",
        cache_path=cache_path,
        now_ts=1000.0 + CACHE_TTL_SECONDS + 1,
        fetcher=lambda _timeout: "3.2.0",
    )

    assert result.used_cache is False
    assert result.latest_version == "3.2.0"
    assert result.update_available is True

    refreshed_payload = json.loads(cache_path.read_text(encoding="utf-8"))
    assert refreshed_payload["latest_version"] == "3.2.0"


def test_command_to_string_shell_quotes_arguments() -> None:
    rendered = command_to_string(["python", "-m", "pip", "install", "--upgrade", "worai"])
    assert "pip install --upgrade worai" in rendered
