from __future__ import annotations

from pathlib import Path

import pytest


class _FakeVectorIndex:
    def __init__(self) -> None:
        self.insert_calls: list[list[object]] = []
        self.delete_calls: list[tuple[str, bool]] = []

    def insert_nodes(self, nodes: list[object]) -> None:
        self.insert_calls.append(nodes)

    def delete_ref_doc(self, ref_doc_id: str, delete_from_docstore: bool = False) -> None:
        self.delete_calls.append((ref_doc_id, delete_from_docstore))


class _FakeNode:
    def __init__(self, text: str) -> None:
        self.text = text
        self.id_ = ""
        self.relationships: dict[object, object] = {}


def test_ingest_same_pdf_twice_is_idempotent(monkeypatch: pytest.MonkeyPatch, tmp_path: Path) -> None:
    pytest.importorskip("llama_index.core")

    # Import after skip guard so this file is safe in minimal dependency environments.
    import ketju.rag.llama_index.ingestion.simple_pdf as simple_pdf_mod
    from ketju.rag.llama_index.ingestion.simple_pdf import SimplePdfIngestionHandler

    pdf = tmp_path / "doc.pdf"
    pdf.write_bytes(b"%PDF-1.4\n1 0 obj\n<<>>\nendobj\n%%EOF\n")

    class _FakeReader:
        def __init__(self, **_: object) -> None:
            pass

        def load_data(self) -> list[object]:
            return [object()]

    class _FakePipeline:
        def __init__(self, **_: object) -> None:
            pass

        def run(self, documents: list[object]) -> list[_FakeNode]:
            assert documents
            return [_FakeNode("chunk-a"), _FakeNode("chunk-b")]

    monkeypatch.setattr(simple_pdf_mod, "SimpleDirectoryReader", _FakeReader)
    monkeypatch.setattr(simple_pdf_mod, "IngestionPipeline", _FakePipeline)

    class _FakeRag:
        pass

    rag = _FakeRag()
    rag.name = "test_simple"
    rag.docs_dir = tmp_path
    rag.cache_dir = tmp_path / "cache"
    rag.cache_dir.mkdir(parents=True, exist_ok=True)
    rag.vector_store_index = _FakeVectorIndex()
    rag.save = lambda: None  # noqa: E731
    rag.resolve_pdf_files = lambda files, max_files=None: [Path(f) for f in files] if files else []
    rag.vector_index = rag.vector_store_index

    handler = SimplePdfIngestionHandler()
    first = handler.ingest(rag, files=[pdf])
    second = handler.ingest(rag, files=[pdf])

    assert first == 2
    assert second == 0
    assert len(rag.vector_index.insert_calls) == 1
