mellea.helpers.openai_compatible_helpers
A file for helper functions that deal with OpenAI API compatible helpers.
Functions
FUNC extract_model_tool_requests
extract_model_tool_requests(tools: dict[str, AbstractMelleaTool], response: dict[str, Any]) -> list[ModelToolCall] | None
Extract tool calls from the dict representation of an OpenAI-like chat response object.
Args:
tools: Mapping of tool name toAbstractMelleaToolfor lookup.response: Dict representation of an OpenAI-compatible chat completion message (must contain a"message"key).
Returns:
- List of
ModelToolCallfor each requested tool call (order preserved), - or
Noneif no tool calls were found.
FUNC chat_completion_delta_merge
chat_completion_delta_merge(chunks: list[dict], force_all_tool_calls_separate: bool = False) -> dict
Merge a list of deltas from ChatCompletionChunks into a single dict representing the ChatCompletion choice.
Args:
chunks: The list of dicts that represent the message deltas.force_all_tool_calls_separate: IfTrue, tool calls in separate message deltas will not be merged even if their index values are the same. Use when providers do not return the correct index value for tool calls; all tool calls must then be fully populated in a single delta.
Returns:
- A single merged dict representing the assembled
ChatCompletionchoice, - with
finish_reason,index, and amessagesub-dict containing content,role, andtool_calls.
FUNC should_replay_reasoning
should_replay_reasoning(messages: list[Message], provider: str | None) -> list[bool]
Decide, per message, whether its reasoning trace should be replayed to the provider.
Implements the cross-provider consensus rule from issue #1201: an assistant
message's reasoning is round-tripped only when that turn issued a tool call —
detected by the message's own tool_calls field — and stripped on plain
follow-up turns. Keying off tool_calls rather than a trailing tool-role
message means reasoning is still replayed for a turn that requested a tool
call even if the tool was never executed. Non-assistant messages and
assistant messages without reasoning always return False.
Args:
messages: The conversation in order, as it will be serialised.provider: The backend provider name (e.g."openai","ollama"). Currently unused — every provider follows the consensus rule above. It is a reserved hook for a provider-specific deviation (e.g. a model that must replay reasoning on plain turns, or must not after a tool call); add a keyed branch here once such a case is verified live.
Returns:
- A list of booleans, one per message in
messages, indicating whether that - message's reasoning should be included in the serialised payload.
FUNC message_to_openai_message
message_to_openai_message(msg: Message, formatter: Formatter | None = None) -> dict
Serialise a Mellea Message to the format required by OpenAI-compatible API providers.
Args:
msg: TheMessageobject to serialise.formatter: Optional formatter used to render the message content (including documents) through the template system. WhenNone, uses the rawmsg.contentstring without document rendering.replay_reasoning: WhenTrueandmsg.thinkingis a non-empty string, the reasoning trace is emitted under the"reasoning_content"key so the provider receives the model's prior reasoning. Defaults toFalse(reasoning is stripped), preserving the historical behaviour; callers decide per-turn via their replay policy (seeshould_replay_reasoning).
Returns:
- A dict with
"role"and"content"fields. When the message carries - images or audio,
"content"is a list of content-part dicts; otherwise - is a plain string. For tool-only assistant turns,
"content"isNone - and
"tool_calls"carries the structured call list. When content is - present alongside tool calls, both keys are included. For a tool-result
- turn whose message carries a provider-supplied
tool_call_id(a ToolMessage, which forwards it from itsModelToolCall, or a plainMessagethat declared it directly), the dict also carries"tool_call_id"(matching the assistant tool call), as spec-strict- OpenAI-compatible providers require on
role: "tool"messages. When replay_reasoningisTrueand reasoning is present, the dict also- carries a
"reasoning_content"field.
Raises:
ValueError: If the message contains anAudioUrlBlock. The OpenAI Chat Completions audio schema does not support audio by URL; fetch the audio and pass it as anAudioBlockwith base64 data instead.
FUNC messages_to_docs
messages_to_docs(msgs: list[Message]) -> list[dict[str, str]]
Extract all Document objects from a list of Message objects.
Args:
msgs: List ofMessageobjects whose_docsattributes are inspected.
Returns:
- A list of dicts, each with a
"text"key and optional"title"and "doc_id"keys, suitable for passing to an OpenAI-compatible RAG API.
FUNC build_completion_usage
build_completion_usage(output: ModelOutputThunk) -> CompletionUsage | None
Build a normalized usage object from a model output, if available.
Args:
output: Model output object whosegeneration.usagemapping contains token counts.
Returns:
- A
CompletionUsageobject when usage metadata is present on the - output, otherwise
None.
FUNC has_tool_calls
has_tool_calls(output: ModelOutputThunk) -> bool
Check if a model output has tool calls.
Args:
output: Model output thunk that may expose atool_callsmapping.
Returns:
Trueif the output has non-empty tool calls,Falseotherwise.
FUNC build_tool_calls
build_tool_calls(output: ModelOutputThunk) -> list[ToolCallDict] | None
Build OpenAI-compatible tool calls from a model output, if available.
Args:
output: Model output thunk that may expose atool_callsmapping.
Returns:
- List of
ToolCallDictobjects when tool calls are present, - otherwise
None.
Classes
CLASS ToolCallFunction
Function details in a tool call.
CLASS ToolCallDict
OpenAI-compatible tool call dictionary with ID and function.
CLASS CompletionUsage
Token usage statistics for a completion request.