sgl-project/sglang · error · ValueError

image payload requires b64_json

Error message

image payload requires b64_json

What it means

The action endpoint's image decoder expects an embedded image as base64 in the b64_json (or base64) key of an image payload dict. If both keys are missing/empty/falsy, _decode_b64_image raises before attempting decode. Data-URI prefixed strings (data:image/...;base64,...) are handled automatically.

Source

Thrown at python/sglang/multimodal_gen/runtime/entrypoints/action/protocol.py:80

    return obj


def pack_msgpack(payload: Any) -> bytes:
    import msgpack

    return msgpack.packb(payload, default=pack_numpy_payload, use_bin_type=True)


def unpack_msgpack(payload: bytes) -> Any:
    import msgpack

    return msgpack.unpackb(payload, object_hook=unpack_numpy_payload, raw=False)


def _decode_b64_image(payload: dict[str, Any]) -> Image.Image:
    data = payload.get("b64_json") or payload.get("base64")
    if not data:
        raise ValueError("image payload requires b64_json")
    if isinstance(data, str) and "," in data and data.startswith("data:"):
        data = data.split(",", 1)[1]
    return Image.open(io.BytesIO(base64.b64decode(data))).convert("RGB")


def _decode_tensor_payload(payload: dict[str, Any]) -> Any:
    values = payload.get("values")
    if values is None:
        values = payload.get("data")
    if values is None:
        return payload
    dtype = payload.get("dtype")
    array = np.asarray(values, dtype=np.dtype(dtype) if dtype else None)
    shape = payload.get("shape")
    if shape is not None:
        array = array.reshape(tuple(shape))
    return array

View on GitHub (pinned to 0132848349)

Solutions

  1. Populate b64_json with the full base64 of the image bytes (data-URI prefix is fine)
  2. If you have a file/URL, pass the path/URL in the image field instead of an embedded payload object
  3. Verify base64.b64encode(open(p,'rb').read()).decode() is non-empty before sending

Example fix

# before
{"image": {"format": "png"}}
# after
{"image": {"b64_json": base64.b64encode(open('obs.png','rb').read()).decode()}}
Defensive patterns

Strategy: validation

Validate before calling

import base64
def embedded_image_ok(img):
    if isinstance(img, dict):
        d = img.get('b64_json') or img.get('base64')
        return bool(d) and len(base64.b64decode(d.split(',')[-1])) > 0
    return True  # path/URL form

Type guard

def has_b64_payload(img) -> bool:
    return not isinstance(img, dict) or bool(img.get('b64_json') or img.get('base64'))

Prevention

When it happens

Trigger: Sending an image object like {"url": "..."} or {"format": "png"} without b64_json/base64 content; sending b64_json: "" or null.

Common situations: Client sends a URL-style image object where embedded bytes were expected; upstream base64 encoding failed producing an empty string; key name mismatch between client and server versions.

Related errors


AI-assisted analysis of sgl-project/sglang@0132848349 (2026-08-28). Data as JSON: /api/errors/cfefa306da9c787e. Report an issue: GitHub.