oobabooga/textgen · error · InvalidRequestError

functions is not supported.

Error message

functions is not supported.

What it means

chat_completions_common rejects requests containing the legacy OpenAI 'functions' parameter. The backend supports the modern 'tools'/'tool_choice' API instead, so the legacy function-calling schema is explicitly rejected with an InvalidRequestError (HTTP 400) rather than silently ignored.

Source

Thrown at modules/api/completions.py:479

                # Mid-conversation system messages: preserve position in history
                if current_message:
                    chat_dialogue.append([current_message, '', '', {}])
                    current_message = ""
                chat_dialogue.append([content, '', '', {"role": "system"}])

    if not user_input_last:
        user_input = ""

    return user_input, system_message, {
        'internal': chat_dialogue,
        'visible': copy.deepcopy(chat_dialogue),
        'messages': history  # Store original messages for multimodal models
    }


def chat_completions_common(body: dict, is_legacy: bool = False, stream=False, prompt_only=False, stop_event=None) -> dict:
    if body.get('functions', []):
        raise InvalidRequestError(message="functions is not supported.", param='functions')

    if body.get('function_call', ''):
        raise InvalidRequestError(message="function_call is not supported.", param='function_call')

    if 'messages' not in body:
        raise InvalidRequestError(message="messages is required", param='messages')

    tools = None
    if 'tools' in body and body['tools'] is not None and isinstance(body['tools'], list) and body['tools']:
        tools = validateTools(body['tools'])  # raises InvalidRequestError if validation fails

    tool_choice = body.get('tool_choice', None)
    if tool_choice == "none":
        tools = None  # Disable tool detection entirely

    messages = body['messages']
    for m in messages:
        if 'role' not in m:

View on GitHub (pinned to ed888c71f2)

Solutions

  1. Migrate the request to the tools API: replace 'functions' with 'tools': [{"type": "function", "function": {"name": ..., "description": ..., "parameters": ...}}].
  2. Replace 'function_call' with 'tool_choice' at the same time, since it is rejected too.
  3. Upgrade old OpenAI SDK clients to openai>=1.0 and use client.chat.completions.create(tools=[...]) so the legacy param is never sent.
  4. Remove leftover function configs from frameworks (e.g. LangChain agents) that emit the legacy field.

Example fix

# before
resp = client.chat.completions.create(
    model="x",
    messages=msgs,
    functions=[{"name": "get_weather", "parameters": {...}}],
)

# after
tools = [{"type": "function", "function": {"name": "get_weather", "description": "Get weather", "parameters": {"type": "object", "properties": {"city": {"type": "string"}}, "required": ["city"]}}}]
resp = client.chat.completions.create(
    model="x",
    messages=msgs,
    tools=tools,
    tool_choice="auto",
)
Defensive patterns

Strategy: validation

Validate before calling

def sanitize_chat_body(body: dict) -> dict:
    body = dict(body)
    body.pop('functions', None)   # or migrate to tools
    body.pop('function_call', None)
    return body

Try / catch

try:
    resp = client.chat.completions.create(**params)
except openai.BadRequestError as e:
    if 'functions is not supported' in str(e):
        params = migrate_functions_to_tools(params)
        resp = client.chat.completions.create(**params)
    else:
        raise

Prevention

When it happens

Trigger: POST /v1/chat/completions (or the legacy /v1/completions-style chat endpoint) with a non-empty 'functions' array in the JSON body, e.g. {"model": ..., "messages": [...], "functions": [{"name": "get_weather", "parameters": {...}}]}. Any truthy value for body['functions'] triggers it.

Common situations: Running old OpenAI SDK code (openai<1.0 style or tutorials predating 2023 tool-calling); porting a LangChain/LlamaIndex app that still emits 'functions'; SDK auto-injecting the param when a legacy function config is left in place.

Related errors


AI-assisted analysis of oobabooga/textgen@ed888c71f2 (2026-08-15). Data as JSON: /api/errors/a6ea2b38d7e68254. Report an issue: GitHub.