"""app.widgets.whiteboard -- unit-level, no HTTP: constructs Widget/
WhiteboardWidgetConfig rows directly and monkeypatches the underlying
fetch/render call (get_or_refresh_whiteboard_for_widget, already covered
against a real WebDAV server + mocked sidecar in
test_whiteboard_refresh_and_browse.py) rather than re-testing that
throttle/fetch logic here."""

from __future__ import annotations

import io
import time

from PIL import Image

from app import widgets
from app.models import Frame, Widget, WhiteboardWidgetConfig


def _make_widget(db_session) -> tuple[Frame, Widget]:
    frame = db_session.get(Frame, 1)
    widget = Widget(frame_id=frame.id, widget_type="whiteboard", x=0, y=0, w=8, h=5,
                    sort_order=0, created_at=time.time())
    db_session.add(widget)
    db_session.flush()
    db_session.add(WhiteboardWidgetConfig(widget_id=widget.id, url="https://example.com/board.whiteboard"))
    db_session.commit()
    return frame, widget


def _tiny_png() -> bytes:
    buf = io.BytesIO()
    Image.new("RGB", (40, 20), (10, 20, 30)).save(buf, format="PNG")
    return buf.getvalue()


def test_render_unconfigured_widget_returns_correctly_sized_placeholder(db_session):
    frame = db_session.get(Frame, 1)
    widget = Widget(frame_id=frame.id, widget_type="whiteboard", x=0, y=0, w=8, h=5,
                    sort_order=0, created_at=time.time())
    db_session.add(widget)
    db_session.flush()
    db_session.add(WhiteboardWidgetConfig(widget_id=widget.id))  # no url/user_id set
    db_session.commit()

    img = widgets.whiteboard.render(db_session, frame, widget, 300, 200)
    assert img.size == (300, 200)


def test_render_configured_widget_composes_the_fetched_png(db_session, monkeypatch):
    frame, widget = _make_widget(db_session)
    png = _tiny_png()
    monkeypatch.setattr(widgets.whiteboard, "get_or_refresh_whiteboard_for_widget",
                        lambda db, frame, widget, force=False: png)

    img = widgets.whiteboard.render(db_session, frame, widget, 300, 200)
    assert img.size == (300, 200)
    assert img.mode == "RGB"


def test_render_falls_back_to_placeholder_when_nothing_cached_yet(db_session, monkeypatch):
    frame, widget = _make_widget(db_session)
    monkeypatch.setattr(widgets.whiteboard, "get_or_refresh_whiteboard_for_widget",
                        lambda db, frame, widget, force=False: None)

    img = widgets.whiteboard.render(db_session, frame, widget, 300, 200)
    assert img.size == (300, 200)


def test_check_now_action_forces_a_refetch(db_session, monkeypatch):
    frame, widget = _make_widget(db_session)
    calls = []

    def fake_refresh(db, frame, widget, force=False):
        calls.append(force)
        return _tiny_png()

    monkeypatch.setattr(widgets.whiteboard, "get_or_refresh_whiteboard_for_widget", fake_refresh)
    widgets.whiteboard.ACTIONS["check_now"](db_session, frame, widget)
    assert calls == [True]


def test_both_buttons_map_to_check_now():
    """No real "next"/"back" concept for a static board -- both physical
    buttons mean the same thing for a whiteboard widget."""
    assert set(widgets.whiteboard.ACTIONS) == {"check_now"}
