From 860843953daa59300d58ebf9766485eb97ad0331 Mon Sep 17 00:00:00 2001 From: mateo-berri <277851410+mateo-berri@users.noreply.github.com> Date: Thu, 30 Apr 2026 19:14:02 +0000 Subject: [PATCH] fix(vertex_ai): default missing items on array schemas Vertex rejects array schemas without an items field (GenerateContentRequest.tools[*].function_declarations[*].parameters...items: missing field). This happened for tool params containing anyOf branches like {"type": "array"} with no items, including the case where convert_anyof_null_to_nullable strips an empty items entry. Default missing items to {"type": "object"} in process_items so the same default applies to bare arrays and arrays nested inside anyOf. --- litellm/llms/vertex_ai/common_utils.py | 2 ++ .../vertex_ai/test_vertex_ai_common_utils.py | 23 ++++++++++++++++++- 2 files changed, 24 insertions(+), 1 deletion(-) diff --git a/litellm/llms/vertex_ai/common_utils.py b/litellm/llms/vertex_ai/common_utils.py index ccd4d4f2934..8a6b5ddd70b 100644 --- a/litellm/llms/vertex_ai/common_utils.py +++ b/litellm/llms/vertex_ai/common_utils.py @@ -599,6 +599,8 @@ def process_items(schema, depth=0): if isinstance(schema, dict): if "items" in schema and schema["items"] == {}: schema["items"] = {"type": "object"} + elif schema.get("type") == "array" and "items" not in schema: + schema["items"] = {"type": "object"} for key, value in schema.items(): if isinstance(value, dict): process_items(value, depth + 1) diff --git a/tests/test_litellm/llms/vertex_ai/test_vertex_ai_common_utils.py b/tests/test_litellm/llms/vertex_ai/test_vertex_ai_common_utils.py index ef93375c3cd..5d8dec75456 100644 --- a/tests/test_litellm/llms/vertex_ai/test_vertex_ai_common_utils.py +++ b/tests/test_litellm/llms/vertex_ai/test_vertex_ai_common_utils.py @@ -225,7 +225,11 @@ def test_build_vertex_schema(): "metadata": {"type": "object"}, "callbacks": { "anyOf": [ - {"type": "array", "nullable": True}, + { + "type": "array", + "items": {"type": "object"}, + "nullable": True, + }, {"type": "object", "nullable": True}, ] }, @@ -288,6 +292,23 @@ def test_process_items_basic(): process_items(schema) assert schema["properties"]["nested"]["items"] == {"type": "object"} + # Test array with no items field at all - Vertex requires items to be present + schema = {"type": "array"} + process_items(schema) + assert schema["items"] == {"type": "object"} + + # Test array missing items inside anyOf branch + schema = { + "type": "object", + "properties": { + "callbacks": { + "anyOf": [{"type": "array"}, {"type": "object"}], + } + }, + } + process_items(schema) + assert schema["properties"]["callbacks"]["anyOf"][0]["items"] == {"type": "object"} + def test_vertex_ai_complex_response_schema(): import json