{"record":{"id":"aef96296c54571e1","repo":"CoplayDev/unity-mcp","slug":"batch-execute-supports-up-to-max-commands-comman","errorCode":null,"errorMessage":"batch_execute supports up to {max_commands} commands (configured in Unity); received {len(commands)}","messagePattern":"batch_execute supports up to (.+?) commands \\(configured in Unity\\); received (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"Server/src/services/tools/batch_execute.py","lineNumber":96,"sourceCode":"    ctx: Context,\n    commands: Annotated[list[dict[str, Any]], \"List of commands with 'tool' and 'params' keys.\"],\n    parallel: Annotated[bool | None,\n                        \"Attempt to run read-only commands in parallel\"] = None,\n    fail_fast: Annotated[bool | None,\n                         \"Stop processing after the first failure\"] = None,\n    max_parallelism: Annotated[int | None,\n                               \"Hint for the maximum number of parallel workers\"] = None,\n) -> dict[str, Any]:\n    \"\"\"Proxy the batch_execute tool to the Unity Editor transporter.\"\"\"\n    unity_instance = await get_unity_instance_from_context(ctx)\n\n    if not isinstance(commands, list) or not commands:\n        raise ValueError(\n            \"'commands' must be a non-empty list of command specifications\")\n\n    max_commands = await _get_max_commands_from_editor_state(ctx)\n    if len(commands) > max_commands:\n        raise ValueError(\n            f\"batch_execute supports up to {max_commands} commands (configured in Unity); received {len(commands)}\"\n        )\n\n    normalized_commands: list[dict[str, Any]] = []\n    for index, command in enumerate(commands):\n        if not isinstance(command, dict):\n            raise ValueError(\n                f\"Command at index {index} must be an object with 'tool' and 'params' keys\")\n\n        tool_name = command.get(\"tool\")\n        params = command.get(\"params\", {})\n\n        if not tool_name or not isinstance(tool_name, str):\n            raise ValueError(\n                f\"Command at index {index} is missing a valid 'tool' name\")\n\n        if params is None:\n            params = {}","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/CoplayDev/unity-mcp/blob/c21bf496bca87d54e75bad048563c3adb1782081/Server/src/services/tools/batch_execute.py#L78-L114","documentation":"batch_execute enforces a configurable upper bound on the number of sub-commands per batch. The limit is read from Unity's editor state (settings.batch_execute_max_commands) and cached module-level; if unavailable it falls back to DEFAULT_MAX_COMMANDS_PER_BATCH (25). The hard ceiling is ABSOLUTE_MAX_COMMANDS_PER_BATCH (100). This error fires when len(commands) exceeds the resolved limit, preventing an AI from submitting an unbounded batch that could overwhelm Unity's main thread.","triggerScenarios":"A caller submits 30+ commands when the configured limit is 25 (default); an AI generates a very large batch (e.g., 50 object creations) in one call; the Unity-side setting was lowered from the default; the cached limit is stale after a config change (the cache is only invalidated by invalidate_cached_max_commands()).","commonSituations":"An LLM over-generates commands in a single batch; a script programmatically builds a large batch; the Unity project lowered batch_execute_max_commands in settings; the module cache holds an old value after the setting changed (cache is not auto-cleared).","solutions":["Split the batch into chunks of at most max_commands (default 25) and call batch_execute multiple times.","Raise the limit in Unity's MCP for Unity settings (batch_execute_max_commands), up to the hard ceiling of 100.","Call invalidate_cached_max_commands() if you changed the Unity setting at runtime and the old value is cached.","Read the current limit from the editor_state resource before building the batch to size it correctly."],"exampleFix":"# before\nawait batch_execute(ctx, commands=[...50 items...])\n# after — chunk into batches of <= 25\nfor i in range(0, len(commands), 25):\n    await batch_execute(ctx, commands=commands[i:i+25])","handlingStrategy":"validation","validationCode":"# Read the current limit and chunk accordingly\nfrom services.tools.batch_execute import _get_max_commands_from_editor_state, DEFAULT_MAX_COMMANDS_PER_BATCH\n\nmax_cmds = DEFAULT_MAX_COMMANDS_PER_BATCH  # safe fallback\n# In async context: max_cmds = await _get_max_commands_from_editor_state(ctx)\nchunk_size = min(max_cmds, len(commands)) if commands else 0\nchunks = [commands[i:i + max_cmds] for i in range(0, len(commands), max_cmds)]","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Read the configured limit from editor_state before building batches to size them correctly.","Chunk large command lists into groups of <= 25 (or the configured limit).","Call invalidate_cached_max_commands() after changing the Unity-side setting at runtime."],"tags":["validation","batch-execute","limit","configurable","mcp-tool"],"backgroundTag":null,"analyzedSha":"c21bf496bca87d54e75bad048563c3adb1782081","analyzedAt":"2026-08-13T17:36:56.095Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}