Skip to content

Provider Hooks

GodeX's bridge runtime speaks one internal protocol, but every upstream provider has quirks -- DeepSeek uses a native reasoning_effort parameter and thinking object, Zhipu supports web_search and file_search tool types, MiniMax remaps max_tokens to max_completion_tokens, and Xiaomi uses a boolean thinking switch. ProviderHooks is the extension point where each provider injects its own normalisation logic. By keeping hooks optional and co-located with the provider spec, GodeX avoids a monolithic adapter layer and lets each provider own its transformations.

The hooks interface defines three optional methods (contract.ts:43-52): patchRequest, normalizeResponse, and normalizeChunk. These are invoked inside createProviderEdge at the boundary between the bridge runtime and the upstream HTTP call.

At a Glance

HookSignatureWhen CalledPurpose
patchRequest(bridgeReq) => providerReqBefore every HTTP callTransform bridge-shaped request into provider-shaped request
normalizeResponse(response) => responseAfter non-streaming responseFix provider response before bridge reads it
normalizeChunk(chunk) => chunkOn each SSE chunk in streaming modeFix provider chunk before bridge reads it

Hook Invocation Flow

DeepSeek Hooks

The DeepSeek provider hooks in hooks.ts:113-136 handle reasoning effort mapping and thinking mode activation:

ScenarioPatch Behaviour
reasoning_effort is "high" or "xhigh"Sets thinking: { type: "enabled" } and maps effort to native values ("high" -> "high", "xhigh" -> "max")
Messages contain historical reasoning_contentSets thinking: { type: "enabled" } to maintain continuity
Default (no reasoning)Sets thinking: { type: "disabled" } explicitly

The deepSeekStreamDeltas function (hooks.ts:149-164) maps each SSE chunk into an array of ProviderStreamDelta by extracting usage data, content text, tool calls, reasoning content, and finish reasons.

Zhipu Hooks

Zhipu's zhipuPatchRequest (hooks.ts:113-134) follows a similar pattern but with Zhipu-specific differences:

ScenarioPatch Behaviour
Request has thinking setPreserves it but forces clear_thinking: false
Messages contain historical reasoning_contentInjects thinking: { type: "enabled", clear_thinking: false }
DefaultStrips reasoning_effort and passes through unchanged

Zhipu also supports a wider set of tool types (hooks.ts:16-30) including web_search, file_search, mcp, and shell, with a degradation map that converts provider-specific tool types into standard Chat Completions equivalents:

Upstream TypeDegraded To
web_search_2025_08_26web_search
web_search_previewweb_search
file_searchretrieval
local_shell / shellfunction
custom / tool_search / namespacefunction

MiniMax Hooks

MiniMax's minimaxPatchRequest (hooks.ts:112-121) is simpler:

  1. Strips reasoning_effort (MiniMax does not support reasoning parameters).
  2. Remaps max_tokens to max_completion_tokens when present.

Xiaomi Hooks

Xiaomi's xiaomiPatchRequest (hooks.ts:115-143) follows the MiMo thinking model:

ScenarioPatch Behaviour
reasoning_effort is presentSets thinking: { type: "enabled" }
Messages contain historical reasoning_contentSets thinking: { type: "enabled" } to preserve reasoning continuity
DefaultSets thinking: { type: "disabled" }
max_tokens is presentRemaps it to max_completion_tokens

Shared Stream Delta Mapper

All four built-in providers delegate tool-call and reasoning-content extraction to mapCommonChatStreamDelta in stream-delta-mapper.ts:18-42. This shared utility handles:

Delta FieldMapping
reasoning_content{ reasoning: content } delta
tool_calls[i].idCopied to toolCall.id
tool_calls[i].function.nameCopied to toolCall.name
tool_calls[i].function.argumentsCopied to toolCall.arguments
tool_calls[i].indexCopied to toolCall.index
tool_calls[i].typeCopied to toolCall.type

Each provider's stream delta function calls mapCommonChatStreamDelta after extracting provider-specific content deltas. For example, DeepSeek's mapDeepSeekChoiceDelta (hooks.ts:166-175) pushes a { text } delta for delta.content, then spreads the common deltas on top.

Custom Tool Degradation

custom-tool-degradation.ts provides helpers to convert Responses API custom tools into Chat Completions function tools when a provider does not support them natively:

Input Compatibility

warnUnsupportedCurrentInputContent in input-compatibility.ts:9-34 emits diagnostics when a Responses request contains content types that Chat Completions cannot represent (anything other than input_text / output_text). This is called during bridging to give users visibility into silently ignored fields.

Request Guard

assertProviderChatRequest (chat-request-guard.ts:5-27) validates that the patched request has a model string and a messages array before it is sent to the upstream provider. Every patchRequest hook calls this guard as its first step.

Capability Comparison

CapabilityDeepSeekZhipuMiniMaxXiaomi
Reasoning effortnative (high/max)boolean (enabled/disabled)noneboolean (enabled/disabled)
Max tools128128128128
Tool choice modesauto, none, required, functionauto, noneauto, none, required, functionauto
Response formatstext, json_objecttext, json_objecttext, json_objecttext, json_object
Streaming usageYesYesYesYes
Web search toolsNoYesNoNo

Cross-references

References