"""Regression coverage for the keyframe sidecar refs aggregation.

The aggregator is the single source of truth for what populate_sidecar
records as ``refs_used`` on keyframe writes. The pre-2026-05-26 inline
version omitted ``reference_images`` (the flat list used by fal-routed
multi-ref image models like gpt-image-2 i2i), so successful multi-ref
edit calls landed sidecars with ``refs_used=[]``. These tests lock the
contract so the bug class can't silently re-emerge.
"""

from __future__ import annotations

from pathlib import Path

from recoil.execution.step_runner import _aggregate_keyframe_refs


def test_reference_images_included_when_only_source():
    """The original bug: gpt-image-2 i2i passes only reference_images."""
    refs = _aggregate_keyframe_refs(
        scene_ref_path=None,
        pose_ref_path=None,
        identity_refs=None,
        expression_refs=None,
        reference_images=[Path("/refs/jade_hero.png"), Path("/refs/jade_front.png")],
    )
    assert refs == ["/refs/jade_hero.png", "/refs/jade_front.png"]


def test_all_five_sources_aggregated_in_discovery_order():
    refs = _aggregate_keyframe_refs(
        scene_ref_path=Path("/refs/scene.png"),
        pose_ref_path=Path("/refs/pose.png"),
        identity_refs=[Path("/refs/id1.png")],
        expression_refs=[Path("/refs/exp1.png")],
        reference_images=[Path("/refs/flat1.png")],
    )
    assert refs == [
        "/refs/scene.png",
        "/refs/pose.png",
        "/refs/id1.png",
        "/refs/exp1.png",
        "/refs/flat1.png",
    ]


def test_duplicates_deduped_across_sources():
    """A path passed as identity_ref AND reference_image lands once."""
    refs = _aggregate_keyframe_refs(
        scene_ref_path=None,
        pose_ref_path=None,
        identity_refs=[Path("/refs/hero.png")],
        expression_refs=None,
        reference_images=[Path("/refs/hero.png"), Path("/refs/other.png")],
    )
    assert refs == ["/refs/hero.png", "/refs/other.png"]


def test_none_and_empty_lists_yield_empty():
    assert _aggregate_keyframe_refs(None, None, None, None, None) == []
    assert _aggregate_keyframe_refs(None, None, [], [], []) == []


def test_accepts_str_paths_alongside_path_objects():
    refs = _aggregate_keyframe_refs(
        scene_ref_path="/refs/a.png",
        pose_ref_path=None,
        identity_refs=None,
        expression_refs=None,
        reference_images=[Path("/refs/b.png"), "/refs/c.png"],
    )
    assert refs == ["/refs/a.png", "/refs/b.png", "/refs/c.png"]
