Skip to content

fix(aistudio): improve JSON Schema compatibility for null fields, boolean schemas, and not constraints - #44

Merged
Mag1cFall merged 1 commit into
Mag1cFall:mainfrom
IllusionOfControl:fix/json-schema-normalization
Oct 4, 2026
Merged

Mag1cFall merged 1 commit into
Mag1cFall:mainfrom
IllusionOfControl:fix/json-schema-normalization

Conversation

@IllusionOfControl

Copy link
Copy Markdown
Contributor

Description

Motivation (Client Schema Compatibility Context)

When using tool calling (Function Calling) and structured outputs (response_format: json_schema) via OpenAI-, Anthropic-, or Gemini-compatible endpoints, client libraries and modern schema generators (such as Pydantic v2, Instructor, LangChain, LlamaIndex, and the official OpenAI Python SDK) frequently emit valid Draft-07/2020-12 constructs or lenient extensions:

  1. Explicit null values: Pydantic v2 and various serializers produce optional/unset schema fields with explicit null values (e.g., "description": null, "format": null, "items": null, "properties": null, "nullable": null). Previously, AIStudio2API strictly validated these fields using rigid type decoders (schemaString, json.Unmarshal(..., &bool)), resulting in immediate rejection (schema.description must be a string / schema.nullable must be a boolean) before the request could even reach Google AI Studio.
  2. Top-level null or empty schemas: Tools defined with empty parameter sets or serializers outputting "parameters": null / "parameters": "" failed with schema must be a JSON object, breaking zero-argument tool calls.
  3. Boolean schemas (items & properties): Under the JSON Schema specification (Draft-07, 2020-12), schemas can be booleans ("items": true allowing any elements, "items": false disallowing them, or boolean properties). The encoder previously expected JSON objects exclusively and rejected boolean values.
  4. Unsupported and no-op "not" constraints: Many client libraries express non-null types or excluded options via "not" constraints (e.g., not: {"type": "null"}, not: ["gpt-3.5", "gpt-4"], not: null). These caused upstream protocol encoding failures or HTTP 400 errors because the wire format expects a specific schema structure at wire index 19.

While the official OpenAI API leniently sanitizes and tolerates these constructs, AIStudio2API was previously failing at the proxy encoding boundary. This PR aligns the proxy's schema normalization with real-world client behavior.

Key Changes

  1. Top-level null & empty schema fallback:

    • In encodeJSONSchema, inspects incoming raw message bytes: if empty, whitespace-only, or null, safely falls back to a default empty object schema {"type":"object","properties":{}}.
  2. Explicit null field stripping (cleanNullFields):

    • Added cleanNullFields to purge keys with explicit null values (format, description, nullable, enum, items, properties, required, etc.).
    • Applied to both root-level schemas and nested properties dictionaries.
    • Explicitly preserves const fields where null may be a valid constant value.
  3. Boolean schema support for items and properties:

    • For items: maps boolean true to open schema {} and prunes false.
    • For properties: normalizes boolean true properties to {} and removes false properties to prevent invalid downstream wire encoding.
  4. Normalization and pruning of "not" constraints (normalizeNot):

    • Filters out no-op and redundant clauses (not: null, not: false, not: true, not: "", not: {}, not: {"type": "null"}).
    • Wraps scalar and array exclusions (e.g., not: ["gpt-3.5"] or not: "gpt-3.5") into compliant enum sub-schemas ({"enum": [...]}).
  5. Comprehensive unit test suite (internal/aistudio/schema_test.go):

    • TestEncodeJSONSchema_NullFields: verifies sanitization across 22 common schema fields with explicit null values.
    • TestEncodeJSONSchema_NotVariants: validates all "not" variants, boolean items, and boolean properties.
    • TestEncodeJSONSchema_TopLevelNullOrEmpty: tests empty strings, spaces, and null root inputs.
    • TestEncodeJSONSchema_DirectConst: ensures valid const schemas remain intact.

Verification

  • go test -v ./internal/aistudio/...: all test suites passed.
  • go test ./...: all repository package tests passed.
  • go vet ./...: 0 issues detected.

…lean schemas, and not constraints

- Default empty or null top-level schema to empty object
- Strip explicit null fields from schema and properties to prevent validation failure
- Support boolean schemas for items and properties (true -> {}, false -> delete)
- Normalize or prune no-op and unsupported "not" constraints into enum schemas
- Add unit tests covering null fields, not variants, boolean schemas, and const
@Mag1cFall
Mag1cFall merged commit f4cd7ad into Mag1cFall:main Oct 4, 2026
2 checks passed
@Mag1cFall

Copy link
Copy Markdown
Owner

Thank you so much! Tested and merged, with some more fixes
3f3298d
https://github.com/Mag1cFall/AIStudio2API/releases/tag/v0.2.4

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