-
-
Notifications
You must be signed in to change notification settings - Fork 52.6k
Description
Summary
The "Fallbacks (comma-separated)" input field in the /agents overview panel is empty when the agent has no per-agent model config (agents.list entry) — even though agents.defaults.model.fallbacks is correctly configured and the summary label above ("Primary Model") correctly displays the fallback count (e.g., openai/gpt-5-nano (+1 fallback)).
Steps to reproduce
- Configure
agents.defaults.modelinopenclaw.jsonwith a primary and fallbacks array:"agents": { "defaults": { "model": { "primary": "openai/gpt-5-nano", "fallbacks": ["google/gemini-2.0-flash"] } } }
- Do not create an
agents.listentry (use only the implicit default agent). - Open Control UI at
/agents→ select the default agent → Overview tab. - Observe the "Fallbacks (comma-separated)" input field.
Expected behavior
The fallback input should display google/gemini-2.0-flash (inherited from agents.defaults.model.fallbacks), consistent with how the primary model field already inherits from defaults.
Actual behavior
The fallback input is empty (""), while the summary label correctly shows openai/gpt-5-nano (+1 fallback).
OpenClaw version
2026.2.19-2
Operating system
Ubuntu 24.04 (WSL2)
Install method
npm global
Logs, screenshots, and evidence
Root cause in ui/src/ui/views/agents.ts (renderAgentOverview):
// Line 393 — only checks entry, never falls back to defaults:
const modelFallbacks = resolveModelFallbacks(config.entry?.model);
const fallbackText = modelFallbacks ? modelFallbacks.join(", ") : "";Compare with the primary model resolution a few lines above, which correctly chains entry ?? defaults:
const modelPrimary =
resolveModelPrimary(config.entry?.model) || (...normalizeModelValue(model)...);
const defaultPrimary =
resolveModelPrimary(config.defaults?.model) || ...;
const effectivePrimary = modelPrimary ?? defaultPrimary ?? null;Fix: Apply the same ?? fallback pattern:
const modelFallbacks =
resolveModelFallbacks(config.entry?.model) ?? resolveModelFallbacks(config.defaults?.model);This is safe for all edge cases:
- No fallbacks configured anywhere →
null→ empty string ✅ - Fallbacks only in defaults → inherits correctly ✅
- Agent has own fallbacks → entry takes precedence ✅
- Agent explicitly sets
fallbacks: []→ respected (empty array is truthy,??does not fall through) ✅
Impact and severity
- Affected: All users relying on
agents.defaults.model.fallbackswithout per-agentagents.listentries (common in single-agent setups) - Severity: Low (display-only bug; backend fallback routing works correctly)
- Frequency: 100% reproducible
- Consequence: Confusing UX — users think their fallback is not configured when it actually is
Additional information
Related: #20924 (Save button stays disabled for default agent — same agents.defaults vs agents.list scenario).