Dashboard-Performance: API-Endpoints konsolidieren
Backend:
- GET /api/sessions: Git-Status inline integriert (parallel pro Session)
- Neue Hilfsmethoden GetGitStatusSummaryAsync (Counts) und
GetGitStatusDetailedAsync (Dateinamen, für Einzel-Endpoint)
- GetSessionsWithStats gibt typisierte SessionWithStats zurück
- Neue Models: SessionWithStats, GitStatusSummary
- GET /api/agents: Skills inline pro Agent integriert
- SkillService als Parameter in HandleList
- Skills als Array mit slug/name/description
Frontend:
- Dashboard: 1 paralleler Promise.all statt sequentieller Requests
- Vorher: agents → sessions → N×git-status → M×agent-skills → cronjobs → shares
- Nachher: Promise.all([agents, sessions, cronjobs, shares]) (4 Requests)
- Git-Status direkt aus Session-Response, Skills aus Agent-Response
- Session-Page: Agent-Skills aus inline-Daten statt N×apiGetAgentSkills
Reduziert Dashboard-Requests von ~4+N+M auf 4 (fix).
This commit is contained in:
1 parent
0dcc05ebf9
commit
11acfde081
7 files changed
+265
-119
No files matched your search
@@ -35,12 +35,13 @@ registerPage('dashboard', {
|
||||
|
||||
// Telegram-Config parallel pro Session laden (sessions werden gleich geladen)
|
||||
|
||||
const agents = await apiGetAgents();
|
||||
const [agents, sessions, cronjobs, shares] = await Promise.all([
|
||||
apiGetAgents(), apiGetSessions(), apiGetCronjobs(), apiListShares()
|
||||
]);
|
||||
const agentMap = {};
|
||||
for (const a of agents) agentMap[a.agentId] = a;
|
||||
|
||||
// Sessions
|
||||
const sessions = await apiGetSessions();
|
||||
const grid = document.getElementById('sessionCards');
|
||||
grid.innerHTML = '';
|
||||
|
||||
@@ -48,6 +49,37 @@ registerPage('dashboard', {
|
||||
const agent = s.agentId ? agentMap[s.agentId] : null;
|
||||
const card = buildSessionCard(s, agent);
|
||||
|
||||
// Git-Status aus der Session-Response rendern (inline vom Backend)
|
||||
if (s.gitStatus) {
|
||||
const gs = s.gitStatus;
|
||||
const metaEl = card.querySelector('.card-meta');
|
||||
if (metaEl) {
|
||||
const parts = [];
|
||||
if (gs.add > 0) {
|
||||
const tip = `${gs.add} ${gs.add === 1 ? 'Datei' : 'Dateien'} hinzugefügt`;
|
||||
parts.push(`<span class="git-badge git-add" title="${esc(tip)}">+${gs.add}</span>`);
|
||||
}
|
||||
if (gs.edit > 0) {
|
||||
const tip = `${gs.edit} ${gs.edit === 1 ? 'Datei' : 'Dateien'} geändert`;
|
||||
parts.push(`<span class="git-badge git-edit" title="${esc(tip)}">~${gs.edit}</span>`);
|
||||
}
|
||||
if (gs.delete > 0) {
|
||||
const tip = `${gs.delete} ${gs.delete === 1 ? 'Datei' : 'Dateien'} gelöscht`;
|
||||
parts.push(`<span class="git-badge git-delete" title="${esc(tip)}">-${gs.delete}</span>`);
|
||||
}
|
||||
if (gs.outgoing > 0) {
|
||||
const tip = `${gs.outgoing} ${gs.outgoing === 1 ? 'Commit muss' : 'Commits müssen'} noch gepusht werden`;
|
||||
parts.push(`<span class="git-badge git-outgoing" title="${esc(tip)}"><i class="fa fa-arrow-up"></i> ${gs.outgoing}</span>`);
|
||||
}
|
||||
if (parts.length) {
|
||||
const gitEl = document.createElement('span');
|
||||
gitEl.className = 'card-meta-item card-git-status';
|
||||
gitEl.innerHTML = parts.join(' ');
|
||||
metaEl.appendChild(gitEl);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Menü zum title-row hinzufügen
|
||||
const titleRow = card.querySelector('.card-title-row');
|
||||
titleRow.insertAdjacentHTML('beforeend', `<div class="card-menu">
|
||||
@@ -105,44 +137,6 @@ registerPage('dashboard', {
|
||||
navigateTo('session', { id: s.sessionId });
|
||||
});
|
||||
grid.appendChild(card);
|
||||
|
||||
// Git-Status asynchron laden
|
||||
if (s.workspace) {
|
||||
apiGitStatus(s.sessionId).then(status => {
|
||||
if (!status || status.error) return;
|
||||
const addCount = (status.add || []).length;
|
||||
const editCount = (status.edit || []).length;
|
||||
const deleteCount = (status.delete || []).length;
|
||||
const outgoing = status.outgoing || 0;
|
||||
if (addCount + editCount + deleteCount + outgoing === 0) return;
|
||||
|
||||
const metaEl = card.querySelector('.card-meta');
|
||||
if (!metaEl) return;
|
||||
|
||||
const parts = [];
|
||||
if (addCount > 0) {
|
||||
const tip = `${addCount} ${addCount === 1 ? 'Datei' : 'Dateien'} hinzugefügt`;
|
||||
parts.push(`<span class="git-badge git-add" title="${esc(tip)}">+${addCount}</span>`);
|
||||
}
|
||||
if (editCount > 0) {
|
||||
const tip = `${editCount} ${editCount === 1 ? 'Datei' : 'Dateien'} geändert`;
|
||||
parts.push(`<span class="git-badge git-edit" title="${esc(tip)}">~${editCount}</span>`);
|
||||
}
|
||||
if (deleteCount > 0) {
|
||||
const tip = `${deleteCount} ${deleteCount === 1 ? 'Datei' : 'Dateien'} gelöscht`;
|
||||
parts.push(`<span class="git-badge git-delete" title="${esc(tip)}">-${deleteCount}</span>`);
|
||||
}
|
||||
if (outgoing > 0) {
|
||||
const tip = `${outgoing} ${outgoing === 1 ? 'Commit muss' : 'Commits müssen'} noch gepusht werden`;
|
||||
parts.push(`<span class="git-badge git-outgoing" title="${esc(tip)}"><i class="fa fa-arrow-up"></i> ${outgoing}</span>`);
|
||||
}
|
||||
|
||||
const gitEl = document.createElement('span');
|
||||
gitEl.className = 'card-meta-item card-git-status';
|
||||
gitEl.innerHTML = parts.join(' ');
|
||||
metaEl.appendChild(gitEl);
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -154,14 +148,8 @@ registerPage('dashboard', {
|
||||
const agentGrid = document.getElementById('agentCards');
|
||||
agentGrid.innerHTML = '';
|
||||
|
||||
// Skills pro Agent parallel laden
|
||||
const agentSkillsMap = {};
|
||||
await Promise.all(agents.map(async a => {
|
||||
agentSkillsMap[a.agentId] = await apiGetAgentSkills(a.agentId);
|
||||
}));
|
||||
|
||||
for (const a of agents) {
|
||||
const skills = agentSkillsMap[a.agentId] || [];
|
||||
const skills = a.skills || [];
|
||||
const card = buildAgentCard(a, skills);
|
||||
|
||||
// Menü zum title-row hinzufügen
|
||||
@@ -213,7 +201,6 @@ registerPage('dashboard', {
|
||||
document.getElementById('newAgentBtn').addEventListener('click', () => navigateTo('agent'));
|
||||
|
||||
// Cronjobs
|
||||
const cronjobs = await apiGetCronjobs();
|
||||
const cronjobGrid = document.getElementById('cronjobCards');
|
||||
cronjobGrid.innerHTML = '';
|
||||
|
||||
@@ -303,7 +290,6 @@ registerPage('dashboard', {
|
||||
document.getElementById('newCronjobBtn').addEventListener('click', () => navigateTo('cronjob'));
|
||||
|
||||
// Shared Links
|
||||
const shares = await apiListShares();
|
||||
const sharedSection = document.getElementById('sharedLinksSection');
|
||||
const sharedGrid = document.getElementById('sharedLinksCards');
|
||||
if (shares.length > 0) {
|
||||
|
||||
@@ -89,9 +89,9 @@ registerPage('session', {
|
||||
for (const a of agents) agentMap[a.agentId] = a;
|
||||
|
||||
const agentSkillsMap = {};
|
||||
await Promise.all(agents.map(async a => {
|
||||
agentSkillsMap[a.agentId] = await apiGetAgentSkills(a.agentId);
|
||||
}));
|
||||
for (const a of agents) {
|
||||
agentSkillsMap[a.agentId] = a.skills || [];
|
||||
}
|
||||
|
||||
function renderAgentInCard(cardEl, agent, emptyIcon, emptyText) {
|
||||
cardEl.innerHTML = '';
|
||||
|
||||
Reference in new issue
Block a user