Files
claude-code/packages/@ant/model-provider/src/shared/__tests__/openaiConvertTools.test.ts
unraid 23bb09d240 feat: 添加 model/provider 层改进
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-22 22:38:10 +08:00

175 lines
4.9 KiB
TypeScript

import { describe, expect, test } from 'bun:test'
import { anthropicToolsToOpenAI, anthropicToolChoiceToOpenAI } from '../openaiConvertTools.js'
describe('anthropicToolsToOpenAI', () => {
test('converts basic tool', () => {
const tools = [
{
type: 'custom',
name: 'bash',
description: 'Run a bash command',
input_schema: {
type: 'object',
properties: { command: { type: 'string' } },
required: ['command'],
},
},
]
const result = anthropicToolsToOpenAI(tools as any)
expect(result).toEqual([
{
type: 'function',
function: {
name: 'bash',
description: 'Run a bash command',
parameters: {
type: 'object',
properties: { command: { type: 'string' } },
required: ['command'],
},
},
},
])
})
test('uses empty schema when input_schema missing', () => {
const tools = [{ type: 'custom', name: 'noop', description: 'no-op' }]
const result = anthropicToolsToOpenAI(tools as any)
expect(
(result[0] as { function: { parameters: unknown } }).function.parameters,
).toEqual({ type: 'object', properties: {} })
})
test('strips Anthropic-specific fields', () => {
const tools = [
{
type: 'custom',
name: 'bash',
description: 'Run bash',
input_schema: { type: 'object', properties: {} },
cache_control: { type: 'ephemeral' },
defer_loading: true,
},
]
const result = anthropicToolsToOpenAI(tools as any)
expect((result[0] as any).cache_control).toBeUndefined()
expect((result[0] as any).defer_loading).toBeUndefined()
})
test('handles empty tools array', () => {
expect(anthropicToolsToOpenAI([])).toEqual([])
})
test('sanitizes const to enum in tool schema', () => {
const tools = [
{
type: 'custom',
name: 'test',
description: 'test tool',
input_schema: {
type: 'object',
properties: {
mode: { const: 'read' },
name: { type: 'string' },
},
},
},
]
const result = anthropicToolsToOpenAI(tools as any)
const props = (result[0] as { function: { parameters: any } }).function
.parameters as any
expect(props.properties.mode).toEqual({ enum: ['read'] })
expect(props.properties.mode.const).toBeUndefined()
expect(props.properties.name).toEqual({ type: 'string' })
})
test('sanitizes const in deeply nested schemas', () => {
const tools = [
{
type: 'custom',
name: 'deep',
description: 'nested const',
input_schema: {
type: 'object',
properties: {
outer: {
type: 'object',
properties: {
inner: { const: 'fixed' },
},
},
},
definitions: {
MyType: {
type: 'object',
properties: {
field: { const: 42 },
},
},
},
},
},
]
const result = anthropicToolsToOpenAI(tools as any)
const params = (result[0] as { function: { parameters: any } }).function
.parameters as any
expect(params.properties.outer.properties.inner).toEqual({
enum: ['fixed'],
})
expect(params.definitions.MyType.properties.field).toEqual({ enum: [42] })
})
test('sanitizes const in anyOf/oneOf/allOf', () => {
const tools = [
{
type: 'custom',
name: 'union',
description: 'union test',
input_schema: {
type: 'object',
properties: {
val: {
anyOf: [{ const: 'a' }, { const: 'b' }, { type: 'string' }],
},
},
},
},
]
const result = anthropicToolsToOpenAI(tools as any)
const anyOf = (
(result[0] as { function: { parameters: any } }).function
.parameters as any
).properties.val.anyOf
expect(anyOf[0]).toEqual({ enum: ['a'] })
expect(anyOf[1]).toEqual({ enum: ['b'] })
expect(anyOf[2]).toEqual({ type: 'string' })
})
})
describe('anthropicToolChoiceToOpenAI', () => {
test('maps auto', () => {
expect(anthropicToolChoiceToOpenAI({ type: 'auto' })).toBe('auto')
})
test('maps any to required', () => {
expect(anthropicToolChoiceToOpenAI({ type: 'any' })).toBe('required')
})
test('maps tool to function', () => {
const result = anthropicToolChoiceToOpenAI({ type: 'tool', name: 'bash' })
expect(result).toEqual({ type: 'function', function: { name: 'bash' } })
})
test('returns undefined for undefined input', () => {
expect(anthropicToolChoiceToOpenAI(undefined)).toBeUndefined()
})
test('returns undefined for unknown type', () => {
expect(anthropicToolChoiceToOpenAI({ type: 'unknown' })).toBeUndefined()
})
})