BerriAI/litellm · error · ValueError
`pages` must be integers, not booleans
Error message
`pages` must be integers, not booleans
What it means
Raised when the `pages` parameter passed to Azure Document Intelligence OCR is a list containing a boolean. Python bools are subclasses of int, so [True, 2] would otherwise silently become '2,3' (True→1-based 2); LiteLLM explicitly rejects booleans to prevent that silent corruption. It fires before any network call, during request transformation.
Source
Thrown at litellm/llms/azure_ai/ocr/document_intelligence/transformation.py:155
- list[str]: tokens like "1" or "3-5". Validated, joined as-is
(treated as Azure-native, i.e. 1-based).
- str: already in Azure format. Validated and whitespace-stripped.
"""
pages_pattern: Final = re.compile(r"^\s*\d+(-\d+)?(\s*,\s*\d+(-\d+)?)*\s*$")
if isinstance(pages, str):
if not pages_pattern.match(pages):
raise ValueError(
f"Invalid `pages` string for Azure Document Intelligence: "
f"{pages!r}. Expected format like '1-3,5,7-9'."
)
return pages.replace(" ", "")
if isinstance(pages, list):
if len(pages) == 0:
return ""
if any(isinstance(p, bool) for p in pages):
raise ValueError("`pages` must be integers, not booleans")
if all(isinstance(p, int) for p in pages):
if any(p < 0 for p in pages):
raise ValueError("`pages` integers must be >= 0 (Mistral 0-based indices)")
# Mistral 0-based -> Azure 1-based.
return ",".join(str(p + 1) for p in sorted(set(pages)))
if all(isinstance(p, str) for p in pages):
joined: Final = ",".join(p.strip() for p in pages)
if not pages_pattern.match(joined):
raise ValueError(
f"Invalid `pages` list for Azure Document Intelligence: "
f"{pages!r}. Expected tokens like '1' or '3-5'."
)
return joined
raise ValueError("`pages` must be a list[int] (0-based, Mistral-style) or a string like '1-3,5,7-9'.")
@staticmethod
def _normalize_features_param(features: object) -> str:View on GitHub (pinned to 6c2dcb801b)
Solutions
- Pass only real integers in the list: [0, 1, 2] (0-based Mistral-style, converted to 1-based automatically).
- Filter/convert booleans before the call if they come from untyped input.
- Alternatively pass a validated string like '1-3,5'.
Example fix
# before pages = [0, 1, True] # bool leaked in from a config flag litellm.aocr_document(model="azure_ai/doc-intelligence/prebuilt-layout", document=doc, pages=pages) # after pages = [p for p in pages if isinstance(p, int) and not isinstance(p, bool)] litellm.aocr_document(model="azure_ai/doc-intelligence/prebuilt-layout", document=doc, pages=pages)
Defensive patterns
Strategy: type-guard
Validate before calling
def clean_pages(pages: list) -> list[int]:
return [p for p in pages if isinstance(p, int) and not isinstance(p, bool)] Type guard
def is_int_pages_list(v: object) -> bool:
return isinstance(v, list) and all(isinstance(p, int) and not isinstance(p, bool) for p in v) Prevention
- Type page lists as list[int] in pydantic/TypedDict models so bools can't enter.
- Sanitize untyped JSON input (filter bools) before passing `pages`.
When it happens
Trigger: Calling the azure_ai doc-intelligence OCR endpoint with optional_params={"pages": [True, False]} or [1, True] — any list where isinstance(p, bool) is True for at least one element.
Common situations: Building the pages list from flags/checkboxes or JSON where true/false leaked into an integer list; data deserialization (e.g. pydantic with loose typing, JSON 'true') inserting booleans.
Related errors
- `pages` must be a list[int] (0-based, Mistral-style) or a st
- Invalid `pages` string for Azure Document Intelligence: {pag
- `pages` integers must be >= 0 (Mistral 0-based indices)
- Invalid `pages` list for Azure Document Intelligence: {pages
- Missing Azure Document Intelligence API Key - Set AZURE_DOCU
AI-assisted analysis of BerriAI/litellm@6c2dcb801b (2026-08-15).
Data as JSON: /api/errors/8c22f880aabe1cf0.
Report an issue: GitHub.