{"record":{"id":"9d57b85d762ad2da","repo":"BerriAI/litellm","slug":"content-item-of-type-text-must-have-a-string-te","errorCode":null,"errorMessage":"Content item of type `text` must have a string `text` field","messagePattern":"Content item of type `text` must have a string `text` field","errorType":"validation","errorClass":"OCIError","httpStatus":400,"severity":"error","filePath":"litellm/llms/oci/chat/generic.py","lineNumber":89,"sourceCode":"        if not isinstance(content_item, dict):\n            raise OCIError(status_code=400, message=\"Each content item must be a dictionary\")\n\n        item_type = content_item.get(\"type\")\n        if not isinstance(item_type, str):\n            raise OCIError(\n                status_code=400,\n                message=\"Each content item must have a string `type` field\",\n            )\n        if item_type not in [\"text\", \"image_url\"]:\n            raise OCIError(\n                status_code=400,\n                message=f\"Content type `{item_type}` is not supported by OCI\",\n            )\n\n        if item_type == \"text\":\n            text = content_item.get(\"text\")\n            if not isinstance(text, str):\n                raise OCIError(\n                    status_code=400,\n                    message=\"Content item of type `text` must have a string `text` field\",\n                )\n            new_content.append(OCITextContentPart(text=text))\n\n        elif item_type == \"image_url\":\n            image_url = content_item.get(\"image_url\")\n            if isinstance(image_url, dict):\n                image_url = image_url.get(\"url\")\n            if not isinstance(image_url, str):\n                raise OCIError(\n                    status_code=400,\n                    message=\"Prop `image_url` must be a string or an object with a `url` property\",\n                )\n            new_content.append(OCIImageContentPart(imageUrl=OCIImageUrl(url=image_url)))\n\n    return OCIMessage(\n        role=open_ai_to_generic_oci_role_map[role],","sourceCodeStart":71,"sourceCodeEnd":107,"githubUrl":"https://github.com/BerriAI/litellm/blob/77b7c6c40c0c5aa5fbcb1d6a1825ac39ca8829b8/litellm/llms/oci/chat/generic.py#L71-L107","documentation":"A content part with type \"text\" must carry its payload in a string `text` field for OCI GENERIC. If `text` is missing, None, or a non-string (number, dict, list), translation aborts with OCIError 400. Fail-fast validation mirroring the OpenAI content-part contract OCI maps onto.","triggerScenarios":"messages=[{\"role\":\"user\",\"content\":[{\"type\":\"text\"}]}] (missing text), [{\"type\":\"text\",\"text\":123}] (int), or [{\"type\":\"text\",\"text\":None}] against an oci/generic.* model. Raised locally in content adaptation before any HTTP request.","commonSituations":"Template code inserting numbers/None into text fields without str(); JSON where text serialized as a non-string; omitting the field when constructing parts programmatically; refactors renaming the field.","solutions":["Ensure every {\"type\":\"text\"} part has a string: coerce with str(value) when building the message","Default empty strings explicitly: text=msg.get(\"text\") or \"\" if an empty text part is intentional","Validate message shape with a type guard/serializer before calling litellm","Check for None coming from optional chain construction (e.g. data.get(\"text\") when key absent)"],"exampleFix":"# before\ncontent = [{\"type\": \"text\", \"text\": 12345}]\n\n# after\ncontent = [{\"type\": \"text\", \"text\": \"12345\"}]","handlingStrategy":"type-guard","validationCode":"def coerce_text_parts(content: list) -> list:\n    return [\n        {**p, \"text\": str(p[\"text\"])} if p.get(\"type\") == \"text\" else p\n        for p in content\n    ]","typeGuard":"def is_valid_text_part(part) -> bool:\n    return part.get(\"type\") == \"text\" and isinstance(part.get(\"text\"), str)","tryCatchPattern":null,"preventionTips":["str()-coerce anything numeric inserted as text content at build time","Treat text as a required field in your message dataclasses/pydantic models"],"tags":["oci","request-validation","content-parts","type-mismatch"],"backgroundTag":"request-body-validation-failed","analyzedSha":"77b7c6c40c0c5aa5fbcb1d6a1825ac39ca8829b8","analyzedAt":"2026-08-18T11:44:31.656Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}