"""Tests for dynamic importance scoring."""

from __future__ import annotations

from datetime import UTC, datetime, timedelta

from arandu.read.importance import compute_dynamic_importance


def test_base_importance_no_history():
    """New fact with no retrieval history returns base importance."""
    score = compute_dynamic_importance(
        base_importance=0.5,
        times_retrieved=0,
        last_retrieved_at=None,
        user_correction_count=0,
        is_in_active_pattern=False,
    )
    assert 0.45 <= score <= 0.55


def test_retrieval_boost_increases_score():
    """Facts retrieved multiple times should score higher."""
    low = compute_dynamic_importance(
        0.5, times_retrieved=0, last_retrieved_at=None, user_correction_count=0, is_in_active_pattern=False
    )
    high = compute_dynamic_importance(
        0.5, times_retrieved=10, last_retrieved_at=None, user_correction_count=0, is_in_active_pattern=False
    )
    assert high > low


def test_recency_boost_recent():
    """Recently retrieved fact gets recency boost."""
    now = datetime.now(UTC)
    recent = compute_dynamic_importance(
        0.5,
        times_retrieved=1,
        last_retrieved_at=now - timedelta(hours=1),
        user_correction_count=0,
        is_in_active_pattern=False,
        now=now,
    )
    old = compute_dynamic_importance(
        0.5,
        times_retrieved=1,
        last_retrieved_at=now - timedelta(days=30),
        user_correction_count=0,
        is_in_active_pattern=False,
        now=now,
    )
    assert recent > old


def test_correction_penalty():
    """Corrected facts should have lower score."""
    no_corrections = compute_dynamic_importance(0.5, 0, None, user_correction_count=0, is_in_active_pattern=False)
    with_corrections = compute_dynamic_importance(0.5, 0, None, user_correction_count=3, is_in_active_pattern=False)
    assert with_corrections < no_corrections


def test_pattern_boost():
    """Facts in active patterns should score higher."""
    without = compute_dynamic_importance(0.5, 0, None, 0, is_in_active_pattern=False)
    with_pattern = compute_dynamic_importance(0.5, 0, None, 0, is_in_active_pattern=True)
    assert with_pattern > without
    assert abs(with_pattern / without - 1.3) < 0.01


def test_clamped_to_range():
    """Score should be clamped between 0.05 and 3.0."""
    # Very low importance
    low = compute_dynamic_importance(0.01, 0, None, 5, False)
    assert low >= 0.05

    # Very high importance
    now = datetime.now(UTC)
    high = compute_dynamic_importance(2.0, 10, now, 0, True, now=now)
    assert high <= 3.0


def test_naive_datetime_handled():
    """Naive datetime for last_retrieved_at should be handled gracefully."""
    now = datetime.now(UTC)
    naive_dt = datetime(2024, 1, 1, 12, 0, 0)  # no timezone
    score = compute_dynamic_importance(0.5, 5, naive_dt, 0, False, now=now)
    assert score > 0
