File size: 2,968 Bytes
3fb9411
 
 
 
 
 
 
0c163b8
 
 
 
 
 
 
3fb9411
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
from __future__ import annotations

import base64
from typing import Any, Iterable


def _data_uri_from(value: Any) -> str | None:
    """Convert raw slide/image representations into a data URI string.

    This accepts several shapes that can appear in MCP tool responses:
    - plain bytes
    - dicts or objects with ``data``/``mimeType`` fields
    - already-encoded ``data:...`` URIs
    """

    if not value:
        return None

    if isinstance(value, str):
        if value.startswith("data:"):
            return value
        return None

    if isinstance(value, bytes):
        b64 = base64.b64encode(value).decode("ascii")
        return f"data:image/png;base64,{b64}"

    # Handle ImageContent-like objects or dicts
    data = getattr(value, "data", None)
    mime = getattr(value, "mimeType", None) or getattr(value, "mime_type", None)

    if isinstance(value, dict):
        data = value.get("data", data)
        mime = value.get("mimeType") or value.get("mime_type") or mime

    if data is None:
        return None

    if isinstance(data, bytes):
        b64 = base64.b64encode(data).decode("ascii")
    else:
        if isinstance(data, str) and data.startswith("data:"):
            return data
        if not isinstance(data, str):
            return None
        b64 = data

    if not mime:
        mime = "image/png"
    return f"data:{mime};base64,{b64}"


def normalize_slide_entries(slides_result: Any) -> list[dict]:
    """Return a list of slide dicts with `image_data_uri` populated."""
    if not isinstance(slides_result, dict):
        return []

    candidates: Iterable[Any] | None = slides_result.get("slides")
    if isinstance(candidates, dict):
        candidates = candidates.get("slides")
    elif candidates is None:
        maybe_nested = slides_result.get("result")
        if isinstance(maybe_nested, dict):
            candidates = maybe_nested.get("slides")
            if isinstance(candidates, dict):
                candidates = candidates.get("slides")

    if not isinstance(candidates, list):
        return []

    normalized: list[dict] = []
    for idx, raw in enumerate(candidates):
        entry: dict | None = None
        if isinstance(raw, dict):
            entry = dict(raw)
            data_uri = entry.get("image_data_uri")
            if not data_uri:
                for key in ("image", "image_content", "content"):
                    if key in entry:
                        data_uri = _data_uri_from(entry[key])
                        if data_uri:
                            entry["image_data_uri"] = data_uri
                            break
            entry.setdefault("index", idx)
        else:
            data_uri = _data_uri_from(raw)
            if data_uri:
                entry = {"index": idx, "image_data_uri": data_uri}

        if entry and entry.get("image_data_uri"):
            normalized.append(entry)

    return normalized


__all__ = ["normalize_slide_entries"]