Skip to content

fix(llm): handle TypedDict required and optional fields in response format - #6546

Open
hsusul wants to merge 1 commit into
livekit:mainfrom
hsusul:fix/typeddict-response-format
Open

fix(llm): handle TypedDict required and optional fields in response format#6546
hsusul wants to merge 1 commit into
livekit:mainfrom
hsusul:fix/typeddict-response-format

Conversation

@hsusul

@hsusul hsusul commented Jul 25, 2026

Copy link
Copy Markdown

Summary

Fixes a bug in to_response_format_param where passing a TypedDict containing Required[...] or NotRequired[...] qualifiers (or stringified type annotations under from __future__ import annotations) raises PydanticUserError or PydanticForbiddenQualifier when converted to a Pydantic BaseModel.

Additionally, fixes an issue where all TypedDict fields were previously set as required (...) regardless of NotRequired annotations or total=False.

Changes

  1. Unwrap Type Qualifiers: Implemented _get_typed_dict_hints and _clean_type_annotation to safely unwrap Required and NotRequired qualifiers and evaluate type annotations.
  2. Field Requirement Resolution: Added _is_typed_dict_field_required to check __required_keys__, __optional_keys__, __total__, and annotation markers (NotRequired/Required) so optional fields are properly initialized with default=None.
  3. Unit Tests: Added test_to_response_format_param_typed_dict to tests/test_llm_utils.py verifying response format parameter generation and OpenAI response format conversion for TypedDict.

Verification

  • uv run pytest tests/test_llm_utils.py passes (14/14 tests).
  • make lint (ruff check) passes with zero issues.
  • make type-check (mypy) passes across 625 source files with zero issues.

…ormat

When converting a TypedDict to a Pydantic BaseModel via to_response_format_param, raw type annotations were passed directly to create_model, causing PydanticUserError/PydanticForbiddenQualifier when Required[...] or NotRequired[...] qualifiers or string annotations were present. Additionally, all fields were marked as required (...) regardless of NotRequired annotations or total=False.

This fix:
1. Uses get_type_hints and unwraps Required/NotRequired qualifiers from field type annotations.
2. Inspects __required_keys__, __optional_keys__, __total__, and annotation markers to accurately determine field requirement status.
3. Adds unit test coverage for TypedDict response format parameters.
@hsusul
hsusul requested a review from a team as a code owner July 25, 2026 04:19
@CLAassistant

CLAassistant commented Jul 25, 2026

Copy link
Copy Markdown

CLA assistant check
All committers have signed the CLA.

@devin-ai-integration devin-ai-integration Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

✅ Devin Review: No Issues Found

Devin Review analyzed this PR and found no bugs or issues to report.

Open in Devin Review

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants