Skip to content

fix: add strict mode support for OpenAI tool definitions in prompt-2025 endpoint#5538

Merged
H2Shami merged 6 commits intomainfrom
ENG-3845
Feb 4, 2026
Merged

fix: add strict mode support for OpenAI tool definitions in prompt-2025 endpoint#5538
H2Shami merged 6 commits intomainfrom
ENG-3845

Conversation

@replicas-connector
Copy link
Contributor

Ticket

ENG-3845 - Check parameters for Facilitator tool call in promptBody

Component/Service

What part of Helicone does this affect?

  • Web (Frontend)
  • Jawn (Backend)
  • Worker (Proxy)
  • Bifrost (Marketing)
  • AI Gateway
  • Packages
  • Infrastructure/Docker
  • Documentation

Type of Change

  • Bug fix
  • New feature
  • Breaking change
  • Documentation update
  • Performance improvement
  • Refactoring

Deployment Notes

  • No special deployment steps required
  • Database migrations need to run
  • Environment variable changes required
  • Coordination with other teams needed

Screenshots / Demos

N/A - API-only change

Extra Notes

Users were receiving a 422 Unprocessable Entity error when creating prompts with tool definitions that include OpenAI's strict mode (strict: true) and additionalProperties: false in the function parameters.

Root Cause:
The OpenAIChatRequest interface in packages/llm-mapper/mappers/openai/chat-v2.ts was missing the strict field in the tool function definition. Since TSOA is configured with noImplicitAdditionalProperties: "throw-on-extras", any request with extra properties like strict: true was being rejected with a 422 validation error.

Changes Made:

  1. Added strict?: boolean field to the tool function interface in OpenAIChatRequest
  2. Made description and parameters optional to match OpenAI's API (they're not strictly required)
  3. Updated the internal Tool type to include the strict property
  4. Updated toExternalTools and convertTools functions to preserve the strict field
  5. Updated TSOA-generated validation schemas in both public and private routes.ts files

Example Request That Now Works:

{
  "tools": [
    {
      "type": "function",
      "function": {
        "name": "facilitator",
        "description": "...",
        "parameters": {
          "type": "object",
          "required": ["optimized_user_request", "conversation_context"],
          "properties": { ... },
          "additionalProperties": false
        },
        "strict": true
      }
    }
  ]
}

Context

A user was unable to create prompts via the /v1/prompt-2025 endpoint when their prompt body included tool definitions with OpenAI's strict mode enabled. This is a common pattern for users who want to ensure their tool calls have validated parameters.

🤖 Generated with Claude Code

…25 endpoint

Users were receiving a 422 Unprocessable Entity error when creating prompts
with tool definitions that include OpenAI's strict mode (strict: true) and
additionalProperties: false in the function parameters.

Changes:
- Add `strict` field to OpenAIChatRequest tools function interface
- Make `description` and `parameters` optional in tool function definition
  to match OpenAI's API behavior
- Update internal Tool type to include `strict` property
- Update toExternalTools and convertTools functions to preserve the strict field
- Update TSOA validation schemas in routes.ts to accept strict mode

This allows prompts with tool calls using OpenAI's strict mode for function
calling to be created and validated correctly.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Co-Authored-By: Hammad Shami <hammad@helicone.ai>
@vercel
Copy link

vercel bot commented Jan 21, 2026

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
helicone Ready Ready Preview, Comment Feb 2, 2026 9:24pm
helicone-bifrost Ready Ready Preview, Comment Feb 2, 2026 9:24pm
helicone-eu Ready Ready Preview, Comment Feb 2, 2026 9:24pm

Request Review

Copy link
Contributor

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

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

Your free trial has ended. If you'd like to continue receiving code reviews, you can add a payment method here.

@supabase
Copy link

supabase bot commented Jan 21, 2026

This pull request has been ignored for the connected project bolqqmqbrciybnypvklh because there are no changes detected in supbase/supabase directory. You can change this behaviour in Project Integrations Settings ↗︎.


Preview Branches by Supabase.
Learn more about Supabase Branching ↗︎.

@supabase
Copy link

supabase bot commented Jan 21, 2026

This pull request has been ignored for the connected project lmahfbbnchpworytrrqk because there are no changes detected in .supabase/supabase directory. You can change this behaviour in Project Integrations Settings ↗︎.


Preview Branches by Supabase.
Learn more about Supabase Branching ↗︎.

@claude
Copy link
Contributor

claude bot commented Jan 21, 2026

Claude finished @replicas-connector[bot]'s task —— View job


Code Review Complete

Score: 8/10 - Good implementation with minor improvement suggestions

Suggestions Summary:

  • Implementation is solid: Correctly adds strict?: boolean support to OpenAI tool definitions
  • API compatibility: Makes description and parameters optional to match OpenAI API spec
  • ⚠️ Minor consistency issue: Nullish coalescing usage could be more consistent
  • Breaking changes: No breaking changes, purely additive
  • Security: No security concerns identified

Detailed Analysis:

✅ Positive Aspects:

  1. Correct API Compliance - The implementation properly adds strict?: boolean to match OpenAI's API specification for function calling validation

  2. Proper Type Safety - Updated the core Tool interface in packages/llm-mapper/types.ts:230 to include the strict field, maintaining type consistency across the codebase

  3. Comprehensive Coverage - Changes propagated correctly through:

    • Core types (packages/llm-mapper/types.ts)
    • OpenAI mappers (packages/llm-mapper/mappers/openai/chat-v2.ts)
    • TSOA generated files (routes and swagger)
    • Client type definitions (web, bifrost, helicone-mcp)
  4. Backward Compatibility - All changes are additive; existing code without strict field continues to work

  5. CI Fixes Applied - Author already resolved TypeScript compilation errors with nullish coalescing operators

⚠️ Areas for Improvement:

  1. Inconsistent Nullish Coalescing (packages/llm-mapper/mappers/openai/responses.ts:565)

    // Current implementation
    description: tool?.description ?? "",
    
    // Should match the pattern used elsewhere
    description: tool.description,

    The OpenAI Responses API mapper uses nullish coalescing for description but not for other optional fields, creating inconsistency.

  2. Missing Anthropic Support - The strict field is only implemented for OpenAI mappers. While this matches the current requirement, consider documenting that Anthropic doesn't support strict mode to avoid confusion.

🔍 Code Quality Assessment:

File: packages/llm-mapper/mappers/openai/chat-v2.ts

  • ✅ Correctly adds strict?: boolean to tool function interface (line 42)
  • ✅ Makes description and parameters optional (lines 40-41)
  • ✅ Preserves strict field in conversion functions (lines 299, 316)

File: packages/llm-mapper/types.ts

  • ✅ Clean addition of strict?: boolean to Tool interface (line 230)
  • ✅ Maintains existing type structure

File: packages/llm-mapper/mappers/openai/responses.ts

  • ⚠️ Uses inconsistent nullish coalescing pattern (line 565)
  • ✅ Otherwise follows same patterns as chat mapper

Technical Verification:

  1. TSOA Integration: Generated routes correctly include strict field validation
  2. Type Propagation: Client type files properly reflect the new optional field
  3. Mapper Functions: Both convertTools and toExternalTools preserve the strict field
  4. Error Resolution: TypeScript compilation errors were properly fixed with nullish coalescing

Recommendation:

MERGE WITH CONSIDERATION - This is a well-implemented feature that solves the reported 422 validation error. The minor consistency issue with nullish coalescing is not critical but should be addressed in a follow-up if consistency is important.

Suggested Follow-up:

Consider standardizing the nullish coalescing usage across all mapper functions for better code consistency.


@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Jan 21, 2026

CI/CD Failure - Resolved

Workflow Worker AI Gateway Tests failed on commit 9215c7c.

Fix: Fixed TypeScript compilation errors caused by making description optional in the Tool interface. The toExternalTools functions in both anthropic/chat-v2.ts and openai/responses.ts mappers now use nullish coalescing (??) to provide a default empty string when tool.description is undefined.

Commit: 00ce337

Fix TypeScript compilation errors by providing default empty string
when tool.description is undefined in toExternalTools functions for
Anthropic and OpenAI responses mappers.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@vercel vercel bot temporarily deployed to Preview – helicone-bifrost January 21, 2026 20:32 Inactive
@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Jan 21, 2026

CI/CD Failure - Resolved

Workflow Jawn TypeScript Check failed on commit 9215c7c.

Fix: This failure was caused by the same TypeScript compilation error as the Worker AI Gateway Tests failure. The fix was already committed in 00ce337, which adds nullish coalescing (??) to provide a default empty string when tool.description is undefined in the toExternalTools function in openai/responses.ts.

New workflow runs are now in progress for commit 00ce337.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Jan 21, 2026

CI/CD Failure - Resolved

Workflow Worker Build Precheck failed on commit 9215c7c.

Fix: This failure was caused by the same TypeScript compilation error that has been fixed in commit 00ce337. The fix adds nullish coalescing (??) to provide a default empty string when tool.description is undefined in the toExternalTools functions in both anthropic/chat-v2.ts and openai/responses.ts.

New workflow runs are now in progress for commit 00ce337.

This reverts commit 00ce337. The nullish coalescing changes were not
necessary - the actual fix was regenerating the TSOA routes files to
pick up the updated type definitions.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker AI Gateway Tests failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker Build Precheck failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn Build Precheck failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Packages Test failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Claude Code Review failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn TypeScript Check failed on commit acc486f.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

Since the Tool interface's description field is now optional (string | undefined),
the toExternalTools functions need to provide a default empty string when
converting to external API types that expect a required string field.

This fixes TypeScript compilation errors in anthropic/chat-v2.ts and
openai/responses.ts mappers.

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Copy link
Contributor

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.

Copilot encountered an error and was unable to review this pull request. You can try again by re-requesting a review.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Packages Test failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn Build Precheck failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Claude Code Review failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Packages Test failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn TypeScript Check failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker Build Precheck failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn TypeScript Check failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker AI Gateway Tests failed on commit 925240c.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Claude Code Review failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Jawn Build Precheck failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker Build Precheck failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@replicas-connector
Copy link
Contributor Author

replicas-connector bot commented Feb 2, 2026

CI/CD Failure - Unresolved (Infrastructure Issue)

Workflow Worker AI Gateway Tests failed on commit 8c19769.

Findings: This failure is not related to code changes. The error message is:

The job was not acquired by Runner of type hosted even after multiple attempts

This is a GitHub Actions infrastructure issue where the hosted runner was not available to execute the job. This is a transient problem that should resolve on retry. The workflow can be re-run manually or will likely succeed on the next push.

@H2Shami H2Shami merged commit dfa37ff into main Feb 4, 2026
12 of 18 checks passed
@H2Shami H2Shami deleted the ENG-3845 branch February 4, 2026 20:22
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.

3 participants