The gateway now reports the alias of the account each call used. Keep it through the wire model, the result dict, both dispatch paths and the model-facing entry, and show the chosen alias in the tool label.
63 lines
3.0 KiB
Python
63 lines
3.0 KiB
Python
"""Route connector calls through the normal dispatch policy pipeline."""
|
|
|
|
import json
|
|
from dataclasses import asdict
|
|
|
|
from tools.registry import tool_error
|
|
from tools.connectors.gateway.config import MAX_CALLS_PER_DISPATCH
|
|
from tools.connectors.gateway.merge import assemble_results, fill_remote_failure, partition_calls
|
|
|
|
|
|
def dispatch_connector_call(name, arguments, tool_call_id):
|
|
from tools.connectors.gateway.bridge import run_remote
|
|
|
|
partition = partition_calls([{"name": name, "arguments": arguments}])
|
|
entries = run_remote(partition.remote, tool_call_id, availability=None, client_factory=None)
|
|
entry = entries[0]
|
|
return json.dumps({key: value for key, value in entry.items() if key in {"response", "error", "account"}},
|
|
ensure_ascii=False)
|
|
|
|
|
|
def dispatch_connector_batch(calls, ids, *, user_task, enabled_tools,
|
|
middleware_trace, enabled_toolsets, disabled_toolsets):
|
|
from model_tools import handle_function_call
|
|
from tools.interrupt import is_interrupted
|
|
|
|
if len(calls) > MAX_CALLS_PER_DISPATCH:
|
|
return tool_error(f"too many calls: {len(calls)} > max {MAX_CALLS_PER_DISPATCH}. "
|
|
"Retry with fewer calls per batch.")
|
|
partition = partition_calls(calls)
|
|
if partition.local:
|
|
from tools.tool_search_validation import local_batch_error
|
|
return tool_error(local_batch_error(calls))
|
|
entries = list(partition.errors)
|
|
for offset, plan in enumerate(partition.remote):
|
|
if is_interrupted():
|
|
# Check before every entry so /stop prevents unstarted remote side effects.
|
|
entries.extend(fill_remote_failure(
|
|
partition.remote[offset:], "Stopped by the user before this call was made.",
|
|
code="INTERRUPTED"))
|
|
break
|
|
# Each entry must run its own policy and middleware.
|
|
payload = handle_function_call(
|
|
plan.name, plan.arguments, **asdict(ids), user_task=user_task,
|
|
enabled_tools=enabled_tools, tool_request_middleware_trace=list(middleware_trace),
|
|
skip_pre_tool_call_hook=False, skip_tool_request_middleware=False,
|
|
skip_tool_execution_middleware=False,
|
|
enabled_toolsets=enabled_toolsets, disabled_toolsets=disabled_toolsets,
|
|
)
|
|
try:
|
|
value = json.loads(payload) if isinstance(payload, str) else payload
|
|
except ValueError:
|
|
value = payload
|
|
entry = {"index": plan.position, "name": plan.name}
|
|
if isinstance(value, dict) and "error" in value:
|
|
error = value["error"]
|
|
entry["error"] = error if isinstance(error, dict) else {"code": "TOOL_ERROR", "message": str(error)}
|
|
else:
|
|
entry["response"] = value.get("response", value) if isinstance(value, dict) else value
|
|
if isinstance(value, dict) and value.get("account"):
|
|
entry["account"] = value["account"]
|
|
entries.append(entry)
|
|
return json.dumps(assemble_results(len(calls), entries), ensure_ascii=False)
|