roboflow/supervision · error · ValueError

Expected string to end in location tags, but got {result}

Error message

Expected string to end in location tags, but got {result}

What it means

Raised while parsing Florence-2 '<REGION_TO_CATEGORY>'/'<REGION_TO_DESCRIPTION>' output when the returned string does not contain four consecutive '<loc_N>' tags. The regex r'<loc_(\d+)><loc_(\d+)><loc_(\d+)><loc_(\d+)>' searches the text for the region coordinates; if none are found, the location of the described object cannot be recovered and the error is raised.

Source

Thrown at src/supervision/detection/vlm.py:596

        return xyxy, None, masks, None

    if task == "<OPEN_VOCABULARY_DETECTION>":
        xyxy = np.array(result["bboxes"], dtype=np.float32)
        labels = np.array(result["bboxes_labels"])
        # Also has "polygons" and "polygons_labels", but they don't seem to be used
        return xyxy, labels, None, None

    if task in ["<REGION_TO_CATEGORY>", "<REGION_TO_DESCRIPTION>"]:
        if not isinstance(result, str):
            raise ValueError(f"Expected string as {task} result, got {type(result)}")

        if result == "No object detected.":
            return np.empty((0, 4), dtype=np.float32), np.array([]), None, None

        pattern = re.compile(r"<loc_(\d+)><loc_(\d+)><loc_(\d+)><loc_(\d+)>")
        match = pattern.search(result)
        if match is None:
            raise ValueError(
                f"Expected string to end in location tags, but got {result}"
            )

        w, h = _validate_resolution(resolution_wh)
        xyxy = np.array([match.groups()], dtype=np.float32)
        xyxy *= np.array([w, h, w, h]) / 1000
        result_string = result[: match.start()]
        labels = np.array([result_string])
        return xyxy, labels, None, None

    raise RuntimeError(f"Unimplemented task: {task}")


def _recover_gemini_json_objects(text: str) -> list[Any]:
    """
    Salvage individual JSON objects from a malformed Gemini JSON array.

    Scans for balanced `{...}` spans and parses each independently, keeping the

View on GitHub (pinned to 7f254d9784)

Solutions

  1. Decode with skip_special_tokens=False so <loc_*> tags survive: processor.decode(output_ids[0], skip_special_tokens=False).
  2. Verify the string passed in actually contains loc tags by printing it; strip only the task token, not the location tags.
  3. Ensure the task string used for parsing matches the prompt used at inference.
  4. Treat tag-less output as 'no detection' in your pipeline: check with re.search before calling, or catch ValueError and skip the frame.

Example fix

# before
 text = processor.decode(generated_ids[0], skip_special_tokens=True)
 detections = sv.Detections.from_florence_2(result=text, task="<REGION_TO_CATEGORY>")

# after
 text = processor.decode(generated_ids[0], skip_special_tokens=False)
 detections = sv.Detections.from_florence_2(result=text, task="<REGION_TO_CATEGORY>")
Defensive patterns

Strategy: validation

Validate before calling

import re

LOC_TAG = re.compile(r"<loc_(\d+)><loc_(\d+)><loc_(\d+)><loc_(\d+)>")

if not LOC_TAG.search(text):
    logger.warning("No loc tags in model output; skipping")

Type guard

def has_loc_tags(text: str) -> bool:
    return re.search(r"<loc_(\d+)><loc_(\d+)><loc_(\d+)><loc_(\d+)>", text) is not None

Try / catch

try:
    detections = sv.Detections.from_florence_2(result=text, task="<REGION_TO_CATEGORY>")
except ValueError:
    detections = sv.Detections.empty()  # caption without grounding

Prevention

When it happens

Trigger: The model returns a plain caption without location tags (common when the task prompt was '<MORE_DETAILED_CAPTION>' or a region task on a non-grounded checkpoint), or the loc tags were stripped by a post-processing/decoding step (e.g. skip_special_tokens=True in processor.decode).

Common situations: Decoding Florence-2 output with skip_special_tokens=True so <loc_*> tokens are removed; using a captioning task but parsing with a region task; prompt/task token typos so the model falls back to captioning; fine-tuned checkpoints that emit a different tag format.

Related errors


AI-assisted analysis of roboflow/supervision@7f254d9784 (2026-08-15). Data as JSON: /api/errors/cc477ae57c1d3ab2. Report an issue: GitHub.