"""Tests for cascade delete behavior.

Deleting a run should automatically delete its turns and results.
Deleting a target/scenario should automatically delete its runs.
"""


from agenteval.models import (
    Case,
    CaseType,
    ChannelType,
    EvalResult,
    EvalRun,
    EvalTarget,
    PlatformType,
    RunStatus,
    Scenario,
    Turn,
)
from agenteval.storage.db import EvalResultDB, EvalRunDB, EvalTargetDB, ScenarioDB, TurnDB
from agenteval.storage.repository import (
    ResultRepository,
    RunRepository,
    ScenarioRepository,
    TargetRepository,
)


def _make_target() -> EvalTarget:
    return EvalTarget(
        id="t-1", name="t",
        platform=PlatformType.AI_DIGITAL_EMPLOYEE,
        channel_type=ChannelType.TUTU_API,
        channel_config={"base_url": "x", "token": "x", "tenant": "x",
                        "chat_channel_id": "x", "chat_contact_id": "x"},
    )


def _make_scenario() -> Scenario:
    return Scenario(
        id="s-1", name="s",
        cases=[Case(id="c1", type=CaseType.SINGLE, messages=["hi"])],
    )


def test_delete_run_cascades_to_turns_and_results(db_session):
    TargetRepository(db_session).create(_make_target())
    ScenarioRepository(db_session).create(_make_scenario())

    RunRepository(db_session).create(EvalRun(
        id="r-1", target_id="t-1", scenario_id="s-1", status=RunStatus.COMPLETED,
    ))
    ResultRepository(db_session).save_turn(Turn(
        id="tu-1", run_id="r-1", case_id="c1", round_index=1,
    ))
    ResultRepository(db_session).save_result(EvalResult(
        id="e-1", run_id="r-1", case_id="c1", turn_id="tu-1",
        rule_type="keyword_match", passed=True,
    ))

    # Sanity: everything is there.
    assert db_session.get(EvalRunDB, "r-1") is not None
    assert db_session.get(TurnDB, "tu-1") is not None
    assert db_session.get(EvalResultDB, "e-1") is not None

    # Delete the run.
    RunRepository(db_session).delete("r-1")

    # Turn and result must be gone too.
    assert db_session.get(EvalRunDB, "r-1") is None
    assert db_session.get(TurnDB, "tu-1") is None
    assert db_session.get(EvalResultDB, "e-1") is None


def test_delete_target_cascades_to_runs(db_session):
    TargetRepository(db_session).create(_make_target())
    ScenarioRepository(db_session).create(_make_scenario())
    RunRepository(db_session).create(EvalRun(
        id="r-1", target_id="t-1", scenario_id="s-1",
    ))

    TargetRepository(db_session).delete("t-1")

    assert db_session.get(EvalTargetDB, "t-1") is None
    assert db_session.get(EvalRunDB, "r-1") is None


def test_delete_scenario_cascades_to_runs(db_session):
    TargetRepository(db_session).create(_make_target())
    ScenarioRepository(db_session).create(_make_scenario())
    RunRepository(db_session).create(EvalRun(
        id="r-1", target_id="t-1", scenario_id="s-1",
    ))

    ScenarioRepository(db_session).delete("s-1")

    assert db_session.get(ScenarioDB, "s-1") is None
    assert db_session.get(EvalRunDB, "r-1") is None
