- Remove DistributedListSplitter and DistributedListCollector nodes - Remove /distributed/init_list_queue and /distributed/request_list_item endpoints - Clean up all references from prompt_transform, queue_orchestration, constants, and tests - Refactor and reorganize distributed modules for quality improvements
85 lines
3.2 KiB
Python
85 lines
3.2 KiB
Python
from dataclasses import dataclass
|
|
from typing import Any
|
|
|
|
try:
|
|
from ..utils.worker_ids import require_enabled_worker_ids
|
|
except ImportError: # pragma: no cover - supports direct module loading in isolated tests.
|
|
from utils.worker_ids import require_enabled_worker_ids
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class QueueRequestPayload:
|
|
prompt: dict[str, Any]
|
|
workflow_meta: dict[str, Any] | None
|
|
client_id: str
|
|
delegate_master: bool | None
|
|
enabled_worker_ids: list[str]
|
|
trace_execution_id: str | None
|
|
|
|
|
|
def parse_queue_request_payload(data: Any) -> QueueRequestPayload:
|
|
"""Parse and validate /distributed/queue payload into a normalized shape."""
|
|
if not isinstance(data, dict):
|
|
raise ValueError("Expected a JSON object body")
|
|
|
|
prompt = data.get("prompt")
|
|
# Auto-prepare is always on server-side; keep the field for wire compatibility.
|
|
if prompt is None:
|
|
workflow_payload = data.get("workflow")
|
|
if isinstance(workflow_payload, dict):
|
|
candidate_prompt = workflow_payload.get("prompt")
|
|
if isinstance(candidate_prompt, dict):
|
|
prompt = candidate_prompt
|
|
|
|
if not isinstance(prompt, dict):
|
|
raise ValueError("Field 'prompt' must be an object")
|
|
|
|
workflow_meta = data.get("workflow")
|
|
if workflow_meta is not None and not isinstance(workflow_meta, dict):
|
|
raise ValueError("Field 'workflow' must be an object when provided")
|
|
|
|
enabled_ids_raw = data.get("enabled_worker_ids")
|
|
workers_field = data.get("workers")
|
|
if enabled_ids_raw is None and workers_field is not None:
|
|
if not isinstance(workers_field, list):
|
|
raise ValueError("Field 'workers' must be a list when provided")
|
|
enabled_ids_raw = []
|
|
for entry in workers_field:
|
|
worker_id = entry.get("id") if isinstance(entry, dict) else entry
|
|
if worker_id is not None:
|
|
enabled_ids_raw.append(str(worker_id))
|
|
|
|
if enabled_ids_raw is None:
|
|
raise ValueError("enabled_worker_ids required")
|
|
else:
|
|
if not isinstance(enabled_ids_raw, list):
|
|
raise ValueError("enabled_worker_ids must be a list of worker IDs")
|
|
try:
|
|
enabled_ids = require_enabled_worker_ids(enabled_ids_raw)
|
|
except ValueError as exc:
|
|
raise ValueError(f"enabled_worker_ids invalid: {exc}") from exc
|
|
|
|
delegate_master = data.get("delegate_master")
|
|
if delegate_master is not None and not isinstance(delegate_master, bool):
|
|
raise ValueError("delegate_master must be a boolean when provided")
|
|
|
|
client_id = data.get("client_id")
|
|
if not isinstance(client_id, str) or not client_id.strip():
|
|
raise ValueError("client_id required")
|
|
client_id = client_id.strip()
|
|
|
|
trace_execution_id = data.get("trace_execution_id")
|
|
if trace_execution_id is not None:
|
|
if not isinstance(trace_execution_id, str):
|
|
raise ValueError("trace_execution_id must be a string when provided")
|
|
trace_execution_id = trace_execution_id.strip() or None
|
|
|
|
return QueueRequestPayload(
|
|
prompt=prompt,
|
|
workflow_meta=workflow_meta,
|
|
client_id=client_id,
|
|
delegate_master=delegate_master,
|
|
enabled_worker_ids=enabled_ids,
|
|
trace_execution_id=trace_execution_id,
|
|
)
|