Skip to content

Implement guided generation for OpenAI models#111

Merged
mattt merged 3 commits intomainfrom
mattt/openai-guided-generation
Feb 6, 2026
Merged

Implement guided generation for OpenAI models#111
mattt merged 3 commits intomainfrom
mattt/openai-guided-generation

Conversation

@mattt
Copy link
Owner

@mattt mattt commented Feb 5, 2026

Related to #27
Supersedes #29

Copy link

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR implements guided generation (structured output) support for OpenAI models, addressing issue #27 which requested support for the @Generable protocol and @Guide macro with OpenAI and Anthropic language models. The implementation adds structured output capabilities to both the Chat Completions and Responses API variants.

Changes:

  • Removed the String-only constraint in OpenAI model's respond and streamResponse methods to support structured types
  • Added JSON schema conversion to OpenAI strict mode format and integrated it into API request bodies
  • Implemented comprehensive test coverage for structured output functionality across both API variants

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 5 comments.

File Description
Tests/AnyLanguageModelTests/OpenAILanguageModelTests.swift Added test suites for structured output with Person and Book types, covering basic generation, optional fields, nested types, and streaming for both Chat Completions and Responses APIs
Sources/AnyLanguageModel/Models/OpenAILanguageModel.swift Implemented structured generation by removing String-only guards, adding schema conversion to OpenAI strict mode, updating request body creation, handling JSON parsing in responses, adding refusal detection, and implementing streaming support for structured types

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 498 to 506
if type == String.self {
return LanguageModelSession.Response(
content: "" as! Content,
rawContent: GeneratedContent(""),
transcriptEntries: ArraySlice(entries)
)
}
throw OpenAILanguageModelError.noResponseGenerated
}
Copy link

Copilot AI Feb 5, 2026

Choose a reason for hiding this comment

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

The error handling logic treats empty responses differently for String vs. structured types. When there's no choice from the API and type == String.self, it returns an empty string (lines 498-503), but for structured types it throws an error (line 505). This inconsistency could be confusing. Consider documenting why this difference exists or making the behavior consistent.

Copilot uses AI. Check for mistakes.
@mattt mattt merged commit 08089db into main Feb 6, 2026
3 checks passed
@mattt mattt deleted the mattt/openai-guided-generation branch February 6, 2026 10:10
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.

1 participant