from __future__ import annotations

from types import SimpleNamespace

from src.services.ollama_endpoint_circuit_breaker import (
    filter_ollama_urls_with_cooldown,
    get_ollama_endpoint_cooldown_remaining_seconds,
    is_ollama_endpoint_blocked,
    record_ollama_endpoint_failure,
    record_ollama_endpoint_success,
    reset_ollama_endpoint_cooldown_for_tests,
    resolve_ollama_order_with_cooldown,
)
from src.services.ollama_endpoint_resolver import resolve_ollama_order


def setup_function() -> None:
    reset_ollama_endpoint_cooldown_for_tests()


def teardown_function() -> None:
    reset_ollama_endpoint_cooldown_for_tests()


def test_cooldown_filters_failed_urls_without_reordering() -> None:
    urls = ("http://gcp-a:11434", "http://gcp-b:11434", "http://local-111:11434")

    record_ollama_endpoint_failure("http://gcp-a:11434", now=100.0)
    record_ollama_endpoint_failure("http://gcp-b:11434", now=100.0)

    assert filter_ollama_urls_with_cooldown(urls, now=101.0) == ("http://local-111:11434",)


def test_cooldown_expires_and_success_clears_block() -> None:
    record_ollama_endpoint_failure("http://gcp-a:11434", cooldown_seconds=10.0, now=100.0)

    assert is_ollama_endpoint_blocked("http://gcp-a:11434", now=109.9)
    assert not is_ollama_endpoint_blocked("http://gcp-a:11434", now=110.1)

    record_ollama_endpoint_failure("http://gcp-a:11434", now=200.0)
    record_ollama_endpoint_success("http://gcp-a:11434")
    assert not is_ollama_endpoint_blocked("http://gcp-a:11434", now=201.0)


def test_cooldown_remaining_seconds_expires_cleanly() -> None:
    record_ollama_endpoint_failure("http://gcp-a:11434", cooldown_seconds=10.0, now=100.0)

    assert (
        get_ollama_endpoint_cooldown_remaining_seconds(
            "http://gcp-a:11434",
            now=103.0,
        )
        == 7.0
    )
    assert (
        get_ollama_endpoint_cooldown_remaining_seconds(
            "http://gcp-a:11434",
            now=111.0,
        )
        == 0.0
    )
    assert not is_ollama_endpoint_blocked("http://gcp-a:11434", now=112.0)


def test_all_blocked_returns_full_order_for_recovery_probe() -> None:
    urls = ("http://gcp-a:11434", "http://gcp-b:11434")

    record_ollama_endpoint_failure("http://gcp-a:11434", now=100.0)
    record_ollama_endpoint_failure("http://gcp-b:11434", now=100.0)

    assert filter_ollama_urls_with_cooldown(urls, now=101.0) == urls


def test_resolver_order_itself_remains_global_policy(monkeypatch) -> None:
    cfg = SimpleNamespace(
        OLLAMA_URL="http://gcp-a:11434",
        OLLAMA_SECONDARY_URL="http://gcp-b:11434",
        OLLAMA_FALLBACK_URL="http://local-111:11434",
    )
    import src.services.ollama_endpoint_resolver as resolver

    monkeypatch.setattr(resolver, "settings", cfg)

    record_ollama_endpoint_failure("http://gcp-a:11434", now=100.0)
    cooled = resolve_ollama_order_with_cooldown("embedding", now=101.0)
    policy = resolve_ollama_order("embedding", config=cfg)

    assert [endpoint.provider_name for endpoint in cooled] == ["ollama_gcp_b", "ollama_local"]
    assert [endpoint.provider_name for endpoint in policy] == [
        "ollama_gcp_a",
        "ollama_gcp_b",
        "ollama_local",
    ]
