fix(moonshot): add schema cleaning for Moonshot/Kimi tool definitions#39618
fix(moonshot): add schema cleaning for Moonshot/Kimi tool definitions#39618MPavleski wants to merge 4 commits intoopenclaw:mainfrom
Conversation
Greptile SummaryThis PR restores Moonshot/Kimi API compatibility by adding provider-specific schema cleaning ( Key observations:
Confidence Score: 3/5
Last reviewed commit: 5f2f2da |
| export const MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS = new Set([ | ||
| // Validation constraints that frequently cause issues | ||
| "minLength", | ||
| "maxLength", | ||
| "minimum", | ||
| "maximum", | ||
| "multipleOf", | ||
| "pattern", | ||
| "format", | ||
| "minItems", | ||
| "maxItems", | ||
| "uniqueItems", | ||
| "minProperties", | ||
| "maxProperties", | ||
| "minContains", | ||
| "maxContains", | ||
|
|
||
| // Meta keywords that may not be supported | ||
| "patternProperties", | ||
| "$schema", | ||
| "$id", | ||
| "$ref", | ||
| "$defs", | ||
| "definitions", |
There was a problem hiding this comment.
additionalProperties may need to be stripped
MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS is described as mirroring Gemini's constraints, but it omits additionalProperties, which is present in GEMINI_UNSUPPORTED_SCHEMA_KEYWORDS. If Moonshot's API rejects additionalProperties in tool schemas (a common restriction in OpenAI-compatible providers), passing it through will produce 400 errors.
The PR description states the root cause was that Moonshot used to get the Gemini cleaning applied universally — meaning additionalProperties was always stripped for it before the regression. If that worked correctly, the new implementation should replicate that behavior:
| export const MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS = new Set([ | |
| // Validation constraints that frequently cause issues | |
| "minLength", | |
| "maxLength", | |
| "minimum", | |
| "maximum", | |
| "multipleOf", | |
| "pattern", | |
| "format", | |
| "minItems", | |
| "maxItems", | |
| "uniqueItems", | |
| "minProperties", | |
| "maxProperties", | |
| "minContains", | |
| "maxContains", | |
| // Meta keywords that may not be supported | |
| "patternProperties", | |
| "$schema", | |
| "$id", | |
| "$ref", | |
| "$defs", | |
| "definitions", | |
| export const MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS = new Set([ | |
| // Validation constraints that frequently cause issues | |
| "minLength", | |
| "maxLength", | |
| "minimum", | |
| "maximum", | |
| "multipleOf", | |
| "pattern", | |
| "format", | |
| "minItems", | |
| "maxItems", | |
| "uniqueItems", | |
| "minProperties", | |
| "maxProperties", | |
| "minContains", | |
| "maxContains", | |
| // Meta keywords that may not be supported | |
| "patternProperties", | |
| "additionalProperties", | |
| "$schema", | |
| "$id", | |
| "$ref", | |
| "$defs", | |
| "definitions", | |
| "examples", | |
| ]); |
Prompt To Fix With AI
This is a comment left during a code review.
Path: src/agents/schema/clean-for-moonshot.ts
Line: 6-29
Comment:
**`additionalProperties` may need to be stripped**
`MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS` is described as mirroring Gemini's constraints, but it omits `additionalProperties`, which **is** present in `GEMINI_UNSUPPORTED_SCHEMA_KEYWORDS`. If Moonshot's API rejects `additionalProperties` in tool schemas (a common restriction in OpenAI-compatible providers), passing it through will produce 400 errors.
The PR description states the root cause was that Moonshot used to get the Gemini cleaning applied universally — meaning `additionalProperties` was always stripped for it before the regression. If that worked correctly, the new implementation should replicate that behavior:
```suggestion
export const MOONSHOT_UNSUPPORTED_SCHEMA_KEYWORDS = new Set([
// Validation constraints that frequently cause issues
"minLength",
"maxLength",
"minimum",
"maximum",
"multipleOf",
"pattern",
"format",
"minItems",
"maxItems",
"uniqueItems",
"minProperties",
"maxProperties",
"minContains",
"maxContains",
// Meta keywords that may not be supported
"patternProperties",
"additionalProperties",
"$schema",
"$id",
"$ref",
"$defs",
"definitions",
"examples",
]);
```
How can I resolve this? If you propose a fix, please make it concise.| return cleaned; | ||
| } | ||
|
|
||
| export function isMoonshotProvider(modelProvider?: string, modelId?: string): boolean { | ||
| const provider = modelProvider?.toLowerCase() ?? ""; | ||
| if (provider.includes("moonshot")) { | ||
| return true; | ||
| } | ||
| // OpenRouter and other proxies may use moonshotai/ prefix | ||
| const lowerModelId = modelId?.toLowerCase() ?? ""; | ||
| if (provider === "openrouter" && lowerModelId.includes("moonshot")) { | ||
| return true; | ||
| } | ||
| // DeepInfra proxies Moonshot models | ||
| if (provider === "deepinfra" && lowerModelId.includes("moonshot")) { | ||
| return true; |
There was a problem hiding this comment.
Kimi model IDs without moonshot prefix won't be detected
The proxy-provider checks rely on lowerModelId.includes("moonshot"), which works for moonshotai/kimi-k2.5 and moonshot/kimi-k2. However, if a proxy ever routes using only the model family name (e.g. "kimi/kimi-k2.5" or "kimi-k2.5") it will not be caught.
This is a minor false-negative risk rather than a regression — it's strictly better than before — but it's worth considering whether "kimi" should also be part of the detection heuristic for proxy routes, since Kimi is Moonshot's primary model line.
Prompt To Fix With AI
This is a comment left during a code review.
Path: src/agents/schema/clean-for-moonshot.ts
Line: 63-78
Comment:
**Kimi model IDs without `moonshot` prefix won't be detected**
The proxy-provider checks rely on `lowerModelId.includes("moonshot")`, which works for `moonshotai/kimi-k2.5` and `moonshot/kimi-k2`. However, if a proxy ever routes using only the model family name (e.g. `"kimi/kimi-k2.5"` or `"kimi-k2.5"`) it will not be caught.
This is a minor false-negative risk rather than a regression — it's strictly better than before — but it's worth considering whether `"kimi"` should also be part of the detection heuristic for proxy routes, since Kimi is Moonshot's primary model line.
How can I resolve this? If you propose a fix, please make it concise.Moonshot Kimi API rejects certain JSON Schema keywords (minLength, maxLength, minimum, maximum, format, etc.) in tool parameter schemas, causing tool calls to fail with 400 errors. This commit introduces Moonshot-specific schema cleaning similar to the existing Gemini and xAI cleaners: - Created src/agents/schema/clean-for-moonshot.ts with stripMoonshotUnsupportedKeywords - Added isMoonshotProvider to detect Moonshot directly or via proxies (OpenRouter, DeepInfra) - Integrated Moonshot schema cleaning into normalizeToolParameters in pi-tools.schema.ts This fixes the regression introduced in commit fe94e83 (Feb 16, 2026) where schema cleaning became provider-aware but Moonshot was not included, causing previously working Moonshot agents to fail tool calls. Fixes: openclaw#39586 (assumed issue number for Moonshot tool call failures)
5f2f2da to
497bff2
Compare
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 20006db02f
ℹ️ About Codex in GitHub
Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: 20006db02f
ℹ️ About Codex in GitHub
Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: e91948866b
ℹ️ About Codex in GitHub
Codex has been enabled to automatically review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
When you sign up for Codex through ChatGPT, Codex can also answer questions or update the PR, like "@codex address that feedback".
| const name = decodeJsonPointerSegment(match[1] ?? ""); | ||
| if (!name) { | ||
| return undefined; | ||
| } | ||
| return defs.get(name); |
There was a problem hiding this comment.
Resolve full JSON Pointer refs instead of top-level def keys
tryResolveLocalRef only does defs.get(name) on the whole suffix after #/$defs/, so valid pointers like #/$defs/Foo/properties/bar are treated as unresolved and then stripped to {} when $ref is removed. This silently weakens those parameter schemas for Moonshot (the property loses its type/enum shape), which can lead to malformed tool arguments passing model-side validation and failing downstream. The new cleaner now handles simple refs, but nested local JSON Pointer refs still regress in this path.
Useful? React with 👍 / 👎.
|
Closing this PR in favor of a follow-up fix for Moonshot tool-calling behavior regression. |
Summary
Fixes #39603
This PR fixes tool call failures with Moonshot/Kimi K2.5 agents by adding provider-specific schema cleaning for Moonshot's API validation constraints.
Root Cause
The regression was introduced in commit fe94e83 (February 16, 2026) when tool schema normalization became provider-aware. Before this commit,
cleanSchemaForGemini()was applied universally to all providers, including Moonshot. After the commit, only Gemini and xAI received schema cleaning, while Moonshot was left without any cleaning, causing it to fail when tool schemas contained validation keywords it doesn't support.Changes
src/agents/schema/clean-for-moonshot.tswithstripMoonshotUnsupportedKeywords()andisMoonshotProvider()normalizeToolParameters()inpi-tools.schema.tssrc/agents/schema/clean-for-moonshot.test.tsTechnical Details
Moonshot Kimi API (like Gemini and xAI) rejects certain JSON Schema keywords in tool parameter schemas:
minLength,maxLength,minimum,maximum,pattern,format, etc.$schema,$ref,$defs,definitions, etc.The implementation mirrors the existing pattern used for Gemini and xAI schema cleaning.
Testing
Impact
This restores Moonshot functionality that was working before February 16, 2026, and affects: