"""Tests for ProcessManagerHandler."""

from angzarr_client.process_manager_handler import ProcessManagerHandler
from angzarr_client.proto.angzarr import process_manager_pb2 as pm
from angzarr_client.proto.angzarr import types_pb2 as types


def _trigger() -> types.EventBook:
    return types.EventBook(
        cover=types.Cover(domain="source", root=types.UUID(value=b"root-1")),
    )


class TestPrepare:
    def test_default_returns_empty(self):
        h = ProcessManagerHandler("test")
        req = pm.ProcessManagerPrepareRequest(trigger=_trigger())

        resp = h.Prepare(req, None)

        assert len(resp.destinations) == 0

    def test_custom_returns_destinations(self):
        def prepare_fn(trigger, process_state):
            return [types.Cover(domain="target", root=trigger.cover.root)]

        h = ProcessManagerHandler("test").with_prepare(prepare_fn)
        req = pm.ProcessManagerPrepareRequest(trigger=_trigger())

        resp = h.Prepare(req, None)

        assert len(resp.destinations) == 1
        assert resp.destinations[0].domain == "target"


class TestHandle:
    def test_default_returns_empty(self):
        h = ProcessManagerHandler("test")
        req = pm.ProcessManagerHandleRequest(trigger=_trigger())

        resp = h.Handle(req, None)

        assert len(resp.commands) == 0

    def test_custom_returns_commands_and_events(self):
        def handle_fn(trigger, process_state, destinations):
            # Now returns ProcessManagerHandleResponse (proto-generated type)
            return pm.ProcessManagerHandleResponse(
                process_events=types.EventBook(
                    pages=[types.EventPage(header=types.PageHeader(sequence=0))],
                ),
                commands=[
                    types.CommandBook(cover=types.Cover(domain="target")),
                ],
            )

        h = ProcessManagerHandler("test").with_handle(handle_fn)
        req = pm.ProcessManagerHandleRequest(trigger=_trigger())

        resp = h.Handle(req, None)

        assert len(resp.commands) == 1
        assert resp.commands[0].cover.domain == "target"
        assert len(resp.process_events.pages) == 1

    def test_handle_receives_destinations(self):
        received = {}

        def handle_fn(trigger, process_state, destinations):
            received["destinations"] = destinations
            return pm.ProcessManagerHandleResponse()

        h = ProcessManagerHandler("test").with_handle(handle_fn)
        dest = types.EventBook(pages=[types.EventPage(), types.EventPage()])
        req = pm.ProcessManagerHandleRequest(
            trigger=_trigger(),
            destinations=[dest],
        )

        h.Handle(req, None)

        assert len(received["destinations"]) == 1
        assert len(received["destinations"][0].pages) == 2
