Show current LLM model next to each agent in the UI
- engine/agents.all_agents() now enriches each agent row with its currently-assigned model (model_for_agent) and provider (provider_for_model). Same source of truth as the LLM client. - web/app.js refreshAgentCards() shows a coloured tag next to the agent name: a green '💻 <model>' badge for local Ollama models, a yellow '☁ <model>' badge for OpenRouter models. The full model name is in the title attribute (hover). - web/style.css: .model-tag.local / .cloud colour palette. - Short name helper strips 'org/' prefix and ':latest' suffix for readability (e.g. 'anthropic/claude-3.5-haiku' -> 'claude-3.5-haiku'). All 100 tests still pass. Live: Anchor + Flora show '☁ claude-3.5-haiku' / '☁ gpt-4o-mini', Lovely + Spark show '💻 gemma4' (running on 192.168.1.245).
This commit is contained in:
parent
23c914d743
commit
2b943aed18
3 changed files with 32 additions and 1 deletions
|
|
@ -58,6 +58,17 @@ def bootstrap():
|
|||
|
||||
|
||||
def all_agents():
|
||||
"""Return live agents with their currently-assigned LLM model."""
|
||||
from . import llm as llm_mod
|
||||
agents = _all_agents_raw()
|
||||
for a in agents:
|
||||
a["model"] = llm_mod.model_for_agent(a["id"])
|
||||
a["provider"] = llm_mod.provider_for_model(a["model"])
|
||||
return agents
|
||||
|
||||
|
||||
def _all_agents_raw():
|
||||
import sqlite3
|
||||
c = sqlite3.connect(db.DB_PATH, check_same_thread=False)
|
||||
c.row_factory = sqlite3.Row
|
||||
try:
|
||||
|
|
|
|||
18
web/app.js
18
web/app.js
|
|
@ -80,6 +80,21 @@ function draw() {
|
|||
}
|
||||
}
|
||||
|
||||
function shortModel(name) {
|
||||
if (!name) return '';
|
||||
// Strip org/ prefix and :tag for compactness
|
||||
const s = name.replace(/^.*\//, '').replace(/:latest$/, '');
|
||||
return s;
|
||||
}
|
||||
|
||||
function modelTag(m, provider) {
|
||||
if (!m) return '';
|
||||
const isCloud = provider === 'openrouter' || (m || '').includes('/');
|
||||
const cls = isCloud ? 'cloud' : 'local';
|
||||
const label = isCloud ? '☁ ' + shortModel(m) : '💻 ' + shortModel(m);
|
||||
return `<span class="model-tag ${cls}" title="${m}">${label}</span>`;
|
||||
}
|
||||
|
||||
function refreshAgentCards() {
|
||||
const wrap = document.getElementById('agentList');
|
||||
wrap.innerHTML = '';
|
||||
|
|
@ -87,7 +102,8 @@ function refreshAgentCards() {
|
|||
const div = document.createElement('div');
|
||||
div.className = 'agent-card';
|
||||
div.innerHTML = `
|
||||
<h3>${a.name} <small>· ${a.role}</small></h3>
|
||||
<h3>${a.name}${modelTag(a.model, a.provider)}</h3>
|
||||
<div style="font-size:11px; color:#8aa1b6;">${a.role}</div>
|
||||
<div>at (${a.x}, ${a.y}) · ${a.mood}</div>
|
||||
<div class="bar energy"><i style="width:${a.energy}%"></i></div>
|
||||
<div class="bar knowledge"><i style="width:${a.knowledge}%"></i></div>
|
||||
|
|
|
|||
|
|
@ -53,6 +53,10 @@ aside h2 { font-size: 12px; text-transform: uppercase; letter-spacing: 1px;
|
|||
#feed li .why { color: #6c8aa6; font-style: italic; }
|
||||
.agent-card { background: #0a1018; border: 1px solid #1c2733; padding: 8px; margin: 6px 0; }
|
||||
.agent-card h3 { margin: 0 0 4px; font-size: 13px; }
|
||||
.agent-card .model-tag { display: inline-block; font-size: 9px; padding: 1px 5px; border-radius: 3px; margin-left: 4px; vertical-align: middle; font-weight: normal; }
|
||||
.agent-card .model-tag.local { background: #1a2a1a; color: #6cf0c2; border: 1px solid #2a3a2a; }
|
||||
.agent-card .model-tag.cloud { background: #2a2a1a; color: #ffd166; border: 1px solid #3a3a1a; }
|
||||
.agent-card .model-tag.short { background: #1c2733; color: #8aa1b6; }
|
||||
.agent-card .bar { height: 4px; background: #1c2733; margin: 2px 0; border-radius: 2px; }
|
||||
.agent-card .bar > i { display: block; height: 100%; border-radius: 2px; }
|
||||
.bar.energy > i { background: #ffd166; }
|
||||
|
|
|
|||
Loading…
Reference in a new issue