Inference APIs
Reference/Errors/Together AI

"Grammar error: properties must be an object": tool_choice fails on a tool with no parameters

Forcing a tool call makes the host compile the tool's JSON schema into a grammar that constrains the output. A schema with "properties": [] is invalid, because JSON Schema requires an object there, and the grammar compiler refuses. The catch is that nobody writes [] on purpose: the tool was defined with "properties": {}, and something between the client and the model turned the empty object into an empty array. The "Engine aborted" variant is the same failure reported by a different serving stack, and its text about context length is a red herring.

Last verified September 18, 2026 against JSON Schema: properties must be an object · 3 min read

ProviderTogether AI (api.together.xyz), and any gateway that re-encodes JSON in a language whose empty object becomes an empty array (PHP, some Go and Perl code)
HTTP status400 Bad Request
MessageFailed to start generation: Grammar error: properties must be an object; on some models instead Engine aborted the request — typically because the input exceeds the model's maximum context length
When it happenstool_choice is "required" or names a function, and that function's parameters.properties arrives as [] instead of {}
Models seenGLM 5.3 Flash (grammar error), GPT-OSS 120B and MiniMax M3 (engine aborted); DeepSeek and Kimi tolerate it
Can you wait it out?No. The request is rejected before generation starts
Short answer
  • Quick check: give the tool one dummy property, or drop parameters entirely. If the call then works, this is your problem.
  • If you run a gateway: restore empty objects at schema keys before forwarding; code below.
  • If you do not: the host or gateway in front of the model needs the fix; the table on the capabilities page shows which models are affected.

What the error looks like

HTTP 400 · Together AI (and any host that compiles tool schemas to a grammar)
{
  "error": {
    "message": "Failed to start generation: Grammar error: properties must be an object",
    "type": "invalid_request_error"
  }
}
The same cause, worse message (seen on GPT-OSS 120B and MiniMax M3)
{
  "error": {
    "message": "Engine aborted the request — typically because the input exceeds the model's maximum context length, or the requested completion budget would not fit.",
    "type": "invalid_request_error"
  }
}

Both come back only when tool_choice forces a call. With "auto" the schema is not compiled to a grammar and the same tool definition works, which is why the bug hides until a client such as an agent framework sets required.

The tool that triggers it

The tool that triggers it: no parameters
{
  "type": "function",
  "function": {
    "name": "get_current_time",
    "description": "Returns the current time.",
    "parameters": {"type": "object", "properties": {}}
  }
}

Tools with no arguments are common in agents: "get the current time", "list open files", "read the secret". Any of them, with a forced tool_choice, through a path that loses the empty object.

The round-trip, and the fix

PHP · the round-trip that breaks it, and the fix
$body = json_decode($raw, true);        // {"properties": {}} becomes ['properties' => []]
echo json_encode($body);               // ... and comes back out as "properties": []   <- grammar error

// Restore empty objects where the schema needs them before forwarding:
function schema_fix_empty($node) {
    if (!is_array($node)) return $node;
    foreach ($node as $k => $v) {
        if (is_array($v)) $node[$k] = ($v === [] && in_array($k, ['properties', 'parameters', 'schema', 'items', 'additionalProperties', '$defs'], true))
            ? new stdClass() : schema_fix_empty($v);
    }
    return $node;
}

The list of keys is the set that must be objects in JSON Schema and in OpenAI's tool format. required is deliberately not in it: an empty required is a valid array. Apply the fix to tools[*].function.parameters and to response_format.json_schema.schema, which has the same problem with structured outputs.

Frequently asked questions

Why does DeepSeek accept the broken schema?

Different serving stack. Some validate the schema strictly before compiling, some coerce, some ignore properties entirely when there are none. The models that reject it are being correct about JSON Schema.

I use Python, not PHP. Can this still happen?

Python's json module keeps {} as a dict, so not from serialisation. It can happen if the schema is built by code that initialises properties as a list.

Where Inference APIs fits

We had this bug ourselves until September 18, 2026: our gateway is written in PHP, whose JSON decoder turns {} into an empty array, and forced tool_choice on a parameterless tool failed on GLM 5.3 Flash, GPT-OSS 120B and MiniMax M3. It is fixed, tested on every chat model on both /v1/chat/completions and /v1/responses, and the fix is above for anyone running a gateway of their own.

Something changed or wrong? Tell us and we will re-verify the entry.