Add per-job run logs and separate vision/text model selection.
Capture pipeline stdout into job.log + API/UI so failed runs can be reviewed, and let users pick OpenRouter vision vs text models independently. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
+18
-3
@@ -23,6 +23,9 @@ _clients: Dict[str, OpenAI] = {}
|
||||
# call_json when routing a no-image (text) call. Module-global mirrors the
|
||||
# set_stage/cost pattern (single-user tool).
|
||||
_text_local = False
|
||||
# Optional per-run model overrides from the UI (empty = use config defaults).
|
||||
_vision_model_override: Optional[str] = None
|
||||
_text_model_override: Optional[str] = None
|
||||
|
||||
|
||||
def set_text_backend(local: bool) -> None:
|
||||
@@ -30,6 +33,13 @@ def set_text_backend(local: bool) -> None:
|
||||
global _text_local
|
||||
_text_local = bool(local)
|
||||
|
||||
|
||||
def set_model_overrides(vision: Optional[str] = None, text: Optional[str] = None) -> None:
|
||||
"""Per-run OpenRouter model picks. None/blank clears back to config defaults."""
|
||||
global _vision_model_override, _text_model_override
|
||||
_vision_model_override = (vision or "").strip() or None
|
||||
_text_model_override = (text or "").strip() or None
|
||||
|
||||
# --- per-job cost accounting -------------------------------------------------
|
||||
# OpenRouter returns the real USD cost of each call when we request usage
|
||||
# accounting. We accumulate it in a module-level counter; the runner resets it
|
||||
@@ -167,12 +177,16 @@ def _resolve_backend(has_images: bool, model_override: Optional[str]) -> Dict[st
|
||||
return {
|
||||
"base_url": config.LOCAL_BASE_URL,
|
||||
"api_key": config.LOCAL_API_KEY,
|
||||
"model": model_override or config.LOCAL_TEXT_MODEL or config.TEXT_MODEL,
|
||||
"model": (model_override or _text_model_override
|
||||
or config.LOCAL_TEXT_MODEL or config.TEXT_MODEL),
|
||||
"usage": False, # local has no OpenRouter usage accounting
|
||||
"local": True,
|
||||
}
|
||||
# Vision, or text-on-OpenRouter (default / fallback).
|
||||
default_model = config.MODEL if has_images else config.TEXT_MODEL
|
||||
if has_images:
|
||||
default_model = _vision_model_override or config.MODEL
|
||||
else:
|
||||
default_model = _text_model_override or config.TEXT_MODEL
|
||||
return {
|
||||
"base_url": config.AI_BASE_URL,
|
||||
"api_key": config.AI_API_KEY,
|
||||
@@ -340,7 +354,8 @@ def call_json(
|
||||
_models["text_local"].add(be["model"])
|
||||
_models["fallback_count"] += 1
|
||||
be = {"base_url": config.AI_BASE_URL, "api_key": config.AI_API_KEY,
|
||||
"model": config.TEXT_MODEL, "usage": True, "local": False}
|
||||
"model": _text_model_override or config.TEXT_MODEL,
|
||||
"usage": True, "local": False}
|
||||
cache_key = None # don't cache fallback under the local-model key
|
||||
fell_back = True
|
||||
continue
|
||||
|
||||
Reference in New Issue
Block a user