Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 14 additions & 14 deletions internal/web/static/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -1265,9 +1265,9 @@ <h3>Activity</h3>
var epTitle = ep.title || (ep.state === 'open' ? 'Episode in progress\u2026' : 'Untitled Episode');
html += '<div class="episode-header"><span class="episode-title">' + escapeHtml(epTitle) + '</span>';
if (ep.outcome) {
html += '<span class="badge ' + outcomeBadge + '">' + ep.outcome + '</span>';
html += '<span class="badge ' + outcomeBadge + '">' + escapeHtml(ep.outcome) + '</span>';
} else {
html += '<span class="badge ' + stateBadge + '">' + (ep.state || 'open') + '</span>';
html += '<span class="badge ' + stateBadge + '">' + escapeHtml(ep.state || 'open') + '</span>';
}
html += '</div>';
if (ep.summary) {
Expand Down Expand Up @@ -1397,8 +1397,8 @@ <h3>Activity</h3>
var age = p.created_at ? timeAgo(p.created_at) : '';
var html = '<div class="pattern-card"><div class="pattern-title">' + escapeHtml(p.title || 'Untitled');
if (p.project) html += ' <span style="color:var(--accent-blue);font-size:0.8rem">[' + escapeHtml(p.project) + ']</span>';
html += '</div><span class="badge badge-type">' + (p.pattern_type || 'pattern') + '</span>';
if (p.state && p.state !== 'active') html += ' <span class="badge" style="background:var(--warning-bg);color:var(--warning-text)">' + p.state + '</span>';
html += '</div><span class="badge badge-type">' + escapeHtml(p.pattern_type || 'pattern') + '</span>';
if (p.state && p.state !== 'active') html += ' <span class="badge" style="background:var(--warning-bg);color:var(--warning-text)">' + escapeHtml(p.state) + '</span>';
html += '<div class="pattern-desc">' + escapeHtml(p.description || '') + '</div>';
html += '<div class="memory-meta-row"><div class="strength-bar"><div class="strength-fill" style="width:' + strengthPct + '%"></div></div>';
html += '<span style="font-size:0.75rem;color:var(--text-dim)">Strength ' + strengthPct + '%</span>';
Expand All @@ -1424,7 +1424,7 @@ <h3>Activity</h3>
var age = a.created_at ? timeAgo(a.created_at) : '';
var html = '<div class="abstraction-card"><div class="abstraction-title">' + escapeHtml(a.title || 'Untitled');
html += ' <span class="badge badge-level">' + levelLabel + '</span>';
if (a.state && a.state !== 'active') html += ' <span class="badge" style="background:var(--warning-bg);color:var(--warning-text)">' + a.state + '</span>';
if (a.state && a.state !== 'active') html += ' <span class="badge" style="background:var(--warning-bg);color:var(--warning-text)">' + escapeHtml(a.state) + '</span>';
html += '</div>';
html += '<div class="abstraction-desc">' + escapeHtml(a.description || '') + '</div>';
html += '<div class="memory-meta-row"><div class="strength-bar"><div class="strength-fill" style="width:' + confPct + '%;background:linear-gradient(90deg,var(--accent-violet),var(--accent-pink))"></div></div>';
Expand Down Expand Up @@ -1463,7 +1463,7 @@ <h3>Activity</h3>
state.graphData = data;
renderGraph(data);
state.graphInitialized = true;
} catch (e) { console.error('Failed to load graph:', e); }
} catch (e) { console.error('Failed to load graph:', e); showToast('Failed to load graph', 'error'); }
}

function renderGraph(data) {
Expand Down Expand Up @@ -1527,7 +1527,7 @@ <h3>Activity</h3>
var tooltip = document.getElementById('graphTooltip');
node.on('mouseover', function(event, d) {
tooltip.style.display = 'block';
tooltip.innerHTML = '<strong>' + escapeHtml((d.summary || '').slice(0, 60)) + '</strong><br><span style="color:var(--text-dim)">Salience: ' + (d.salience || 0).toFixed(2) + ' | State: ' + (d.state || '?') + '</span>' + (d.concepts ? '<br><span style="color:var(--accent-violet)">' + (d.concepts || []).slice(0, 4).join(', ') + '</span>' : '');
tooltip.innerHTML = '<strong>' + escapeHtml((d.summary || '').slice(0, 60)) + '</strong><br><span style="color:var(--text-dim)">Salience: ' + (d.salience || 0).toFixed(2) + ' | State: ' + escapeHtml(d.state || '?') + '</span>' + (d.concepts ? '<br><span style="color:var(--accent-violet)">' + escapeHtml((d.concepts || []).slice(0, 4).join(', ')) + '</span>' : '');
tooltip.style.left = (event.pageX + 12) + 'px';
tooltip.style.top = (event.pageY - 10) + 'px';
var connectedIds = new Set(); connectedIds.add(d.id);
Expand Down Expand Up @@ -1569,9 +1569,9 @@ <h3>Activity</h3>
var detail = document.getElementById('graphDetail');
detail.classList.add('open');
document.getElementById('graphDetailTitle').textContent = (d.summary || '').slice(0, 80);
var meta = '<div>State: ' + (d.state || '?') + ' &bull; Salience: ' + (d.salience || 0).toFixed(2) + '</div>';
if (d.concepts) meta += '<div style="margin-top:4px;color:var(--accent-violet)">' + (d.concepts || []).join(', ') + '</div>';
if (d.emotional_tone) meta += '<div style="margin-top:4px">Tone: ' + d.emotional_tone + '</div>';
var meta = '<div>State: ' + escapeHtml(d.state || '?') + ' &bull; Salience: ' + (d.salience || 0).toFixed(2) + '</div>';
if (d.concepts) meta += '<div style="margin-top:4px;color:var(--accent-violet)">' + escapeHtml((d.concepts || []).join(', ')) + '</div>';
if (d.emotional_tone) meta += '<div style="margin-top:4px">Tone: ' + escapeHtml(d.emotional_tone) + '</div>';
document.getElementById('graphDetailMeta').innerHTML = meta;
var conns = [];
edges.forEach(function(e) {
Expand All @@ -1580,7 +1580,7 @@ <h3>Activity</h3>
if (src === d.id) { var t = nodeMap.get(tgt); if (t) conns.push({ summary: t.summary, type: e.relation_type, strength: e.strength }); }
else if (tgt === d.id) { var s = nodeMap.get(src); if (s) conns.push({ summary: s.summary, type: e.relation_type, strength: e.strength }); }
});
document.getElementById('graphDetailConns').innerHTML = conns.length === 0 ? '<li style="color:var(--text-dim)">No connections</li>' : conns.map(function(c) { return '<li><span style="color:var(--accent-cyan)">' + c.type + '</span> &#8594; ' + escapeHtml((c.summary || '').slice(0, 50)) + ' <span style="color:var(--text-dim)">(' + (c.strength || 0).toFixed(2) + ')</span></li>'; }).join('');
document.getElementById('graphDetailConns').innerHTML = conns.length === 0 ? '<li style="color:var(--text-dim)">No connections</li>' : conns.map(function(c) { return '<li><span style="color:var(--accent-cyan)">' + escapeHtml(c.type) + '</span> &#8594; ' + escapeHtml((c.summary || '').slice(0, 50)) + ' <span style="color:var(--text-dim)">(' + (c.strength || 0).toFixed(2) + ')</span></li>'; }).join('');
}

function closeGraphDetail() { document.getElementById('graphDetail').classList.remove('open'); }
Expand Down Expand Up @@ -1640,7 +1640,7 @@ <h3>Activity</h3>
var detailStr = Object.entries(details).map(function(kv) { return kv[0] + ': ' + kv[1]; }).join(' &bull; ');
return '<div class="insight-item ' + sevClass + '"><div class="insight-type">' + escapeHtml(obs.observation_type || '') + '</div><div class="insight-detail">' + escapeHtml(detailStr) + '</div></div>';
}).join('');
} catch (e) {}
} catch (e) { console.error('Failed to load insights:', e); showToast('Failed to load insights', 'error'); }
}

// ── Stats ──
Expand Down Expand Up @@ -1673,7 +1673,7 @@ <h3>Activity</h3>
opt.value = p; opt.textContent = p;
select.appendChild(opt);
});
} catch (e) {}
} catch (e) { console.error('Failed to load projects:', e); }
}

// ── WebSocket ──
Expand Down Expand Up @@ -1703,7 +1703,7 @@ <h3>Activity</h3>
}
addEvent(type, desc, msg.timestamp || new Date().toISOString());
if (['memory_encoded', 'consolidation_completed', 'dream_cycle_completed'].includes(type) && state.currentView === 'graph') loadGraphData();
} catch (e) {}
} catch (e) { console.error('Failed to parse WebSocket message:', e); }
};
ws.onclose = function() {
var delay = Math.min(30000, 1000 * Math.pow(1.5, state.wsReconnectAttempts));
Expand Down