Phase 3 Hub Enhancement Plan
Detailed breakdown of Phase 3 Hub Enhancement for greatVibe.local
Output
Phase 3: Hub Enhancement — greatVibe.local
Phase 3 transforms konui into greatVibe.local — a proper hub that can coordinate multiple gvShell agents with multi-viewer support.
📋 Current State (Phase 2 Complete)
- ✓ gvShell built in Go (647 tests, 33/50 steps)
- ✓ WebSocket hub client in gvShell
- ✓ Session streaming with acking
- ✓ Work queue integration
- ✓ OAuth device flow auth
- ● Hub (konui) still uses SSE, not WebSocket
🎯 Phase 3 Components
1. Agent Registry Protocol
Hub-side handling of agent connections
/gv/hub/src/agent-registry.ts ├── onAgentConnect(ws, capabilities) ├── onAgentDisconnect(agentId, reason) ├── routeWorkToAgent(sessionId, prompt) └── getAgentForSession(sessionId)
• Register agents with capability declaration
• Track agent health via heartbeat
• Route work to appropriate agent
2. Session Channels (Multi-Viewer)
One session, many viewers — real-time broadcast
/gv/hub/src/session-channel.ts
├── subscribe(sessionId, viewerId, ws)
├── unsubscribe(sessionId, viewerId)
├── broadcast(sessionId, event)
└── getViewers(sessionId) → [{id, device, joinedAt}]
• Start on mobile, continue on desktop
• All viewers see same events instantly
• Presence awareness (who's watching)
3. Work Queue
Hub-side work distribution and tracking
/gv/hub/src/work-queue.ts
├── enqueue(sessionId, prompt) → turnId
├── assignToAgent(turnId, agentId)
├── onProgress(turnId, progress)
├── onComplete(turnId, result)
└── getPending() → [{turnId, sessionId, enqueuedAt}]
• Queue persists across hub restarts
• Progress tracking (0-100%)
• Retry on agent disconnect
4. Presence Indicators
See who's watching, typing, and acting
- "johnathon is typing..." on other devices
- Viewer count badge on session card
- Input focus sharing (who has cursor)
- Last activity timestamp per viewer
📍 Migration Path
| Current (konui) | Phase 3 (greatVibe.local) |
|---|---|
| SSE for streaming | WebSocket (bidirectional) |
| konsole subprocess | gvShell agent (standalone) |
| Single viewer per session | Multi-viewer broadcast |
| Hub restarts lose context | Agent owns session state |
| No agent registry | Connected agent tracking |
🔄 Coexistence Strategy
Phase 3 runs alongside existing konsole — no production disruption:
- New endpoint:
/ws/agentfor gvShell connections - Feature flag: Enable per-session via toggle
- Route by capability: Sessions with advanced features → gvShell
- Gradual migration: Move sessions one by one
⏱️ Implementation Steps
| Step 1 | Add WebSocket endpoint to konui (/ws/agent) |
| Step 2 | Implement agent-registry.ts (registration, heartbeat) |
| Step 3 | Implement session-channel.ts (pub/sub, broadcast) |
| Step 4 | Implement work-queue.ts (enqueue, assign, complete) |
| Step 5 | Add presence indicators to dashboard UI |
| Step 6 | Test end-to-end: gvShell ↔ Hub ↔ Browser |
💡 Key Insight
The agent owns session state (SQLite + JSONL), the hub owns coordination (registry, queue, channels). This means hub restarts don't lose history — agents reconnect and replay.
What's Next?
Choose an action:
Quick Actions
Original Request
No layout configured
Details
Raw Data
{
"id": "7c49e38d-d789-48ce-97ea-640a2680a4d1",
"type": "general",
"status": "completed",
"title": "Phase 3 Hub Enhancement Plan",
"description": "Detailed breakdown of Phase 3 Hub Enhancement for greatVibe.local",
"context": {
"output": "<div style=\"background:#1e1e1e;color:#e0e0e0;padding:20px;border-radius:8px;font-family:system-ui,-apple-system,sans-serif;\">\n<h2 style=\"color:#fff;margin:0 0 16px 0;\">Phase 3: Hub Enhancement — greatVibe.local</h2>\n\n<p style=\"color:#9ca3af;margin-bottom:20px;\">Phase 3 transforms konui into <strong>greatVibe.local</strong> — a proper hub that can coordinate multiple gvShell agents with multi-viewer support.</p>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:20px;\">\n<h3 style=\"color:#3b82f6;margin:0 0 12px 0;\">📋 Current State (Phase 2 Complete)</h3>\n<ul style=\"margin:0;padding-left:20px;line-height:1.8;\">\n<li><span style=\"color:#22c55e;\">✓</span> gvShell built in Go (647 tests, 33/50 steps)</li>\n<li><span style=\"color:#22c55e;\">✓</span> WebSocket hub client in gvShell</li>\n<li><span style=\"color:#22c55e;\">✓</span> Session streaming with acking</li>\n<li><span style=\"color:#22c55e;\">✓</span> Work queue integration</li>\n<li><span style=\"color:#22c55e;\">✓</span> OAuth device flow auth</li>\n<li><span style=\"color:#f59e0b;\">●</span> Hub (konui) still uses SSE, not WebSocket</li>\n</ul>\n</div>\n\n<div id=\"arch-diagram\" style=\"background:#2d2d2d;padding:16px;border-radius:8px;margin-bottom:20px;min-height:200px;\">\n<div style=\"color:#888;\">Loading architecture diagram...</div>\n</div>\n<script>\n(function() {\n const definition = `\n%%{init: {'theme': 'dark'}}%%\ngraph TD\n subgraph Hub[\"greatVibe.local HUB\"]\n AR[Agent Registry]\n WQ[Work Queue]\n SC[Session Channels]\n SS[State Store]\n end\n\n subgraph Viewers[\"Multi-Viewer Support\"]\n M[📱 Mobile]\n D[🖥️ Desktop]\n T[📟 Terminal]\n end\n\n subgraph Agents[\"gvShell Agents\"]\n A1[🐧 Linux Agent]\n A2[🪟 Windows Agent]\n A3[🐘 postgres Agent]\n end\n\n M -->|WebSocket| SC\n D -->|WebSocket| SC\n T -->|WebSocket| SC\n\n A1 -->|WebSocket| AR\n A2 -->|WebSocket| AR\n A3 -->|WebSocket| AR\n\n AR --> WQ\n WQ --> SC\n SC --> SS\n\n style Hub fill:#1e3a5f,stroke:#3b82f6,color:#fff\n style AR fill:#22c55e,stroke:#16a34a,color:#000\n style WQ fill:#f59e0b,stroke:#d97706,color:#000\n style SC fill:#8b5cf6,stroke:#7c3aed,color:#fff\n style SS fill:#06b6d4,stroke:#0891b2,color:#000\n style A1 fill:#3b82f6,stroke:#2563eb,color:#fff\n style A2 fill:#3b82f6,stroke:#2563eb,color:#fff\n style A3 fill:#3b82f6,stroke:#2563eb,color:#fff\n`;\n window.renderMermaidDiagram('arch-diagram', definition);\n})();\n</script>\n\n<h3 style=\"color:#fff;margin:20px 0 12px 0;\">🎯 Phase 3 Components</h3>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:16px;\">\n<h4 style=\"color:#22c55e;margin:0 0 8px 0;\">1. Agent Registry Protocol</h4>\n<p style=\"color:#9ca3af;margin:0 0 8px 0;\">Hub-side handling of agent connections</p>\n<pre style=\"background:#1e1e1e;padding:12px;border-radius:4px;overflow-x:auto;color:#e5c07b;font-size:0.9rem;margin:0;\">\n/gv/hub/src/agent-registry.ts\n├── onAgentConnect(ws, capabilities)\n├── onAgentDisconnect(agentId, reason)\n├── routeWorkToAgent(sessionId, prompt)\n└── getAgentForSession(sessionId)\n</pre>\n<p style=\"color:#7f848e;margin:8px 0 0 0;font-size:0.85rem;\">• Register agents with capability declaration<br>• Track agent health via heartbeat<br>• Route work to appropriate agent</p>\n</div>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:16px;\">\n<h4 style=\"color:#f59e0b;margin:0 0 8px 0;\">2. Session Channels (Multi-Viewer)</h4>\n<p style=\"color:#9ca3af;margin:0 0 8px 0;\">One session, many viewers — real-time broadcast</p>\n<pre style=\"background:#1e1e1e;padding:12px;border-radius:4px;overflow-x:auto;color:#e5c07b;font-size:0.9rem;margin:0;\">\n/gv/hub/src/session-channel.ts\n├── subscribe(sessionId, viewerId, ws)\n├── unsubscribe(sessionId, viewerId)\n├── broadcast(sessionId, event)\n└── getViewers(sessionId) → [{id, device, joinedAt}]\n</pre>\n<p style=\"color:#7f848e;margin:8px 0 0 0;font-size:0.85rem;\">• Start on mobile, continue on desktop<br>• All viewers see same events instantly<br>• Presence awareness (who's watching)</p>\n</div>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:16px;\">\n<h4 style=\"color:#8b5cf6;margin:0 0 8px 0;\">3. Work Queue</h4>\n<p style=\"color:#9ca3af;margin:0 0 8px 0;\">Hub-side work distribution and tracking</p>\n<pre style=\"background:#1e1e1e;padding:12px;border-radius:4px;overflow-x:auto;color:#e5c07b;font-size:0.9rem;margin:0;\">\n/gv/hub/src/work-queue.ts\n├── enqueue(sessionId, prompt) → turnId\n├── assignToAgent(turnId, agentId)\n├── onProgress(turnId, progress)\n├── onComplete(turnId, result)\n└── getPending() → [{turnId, sessionId, enqueuedAt}]\n</pre>\n<p style=\"color:#7f848e;margin:8px 0 0 0;font-size:0.85rem;\">• Queue persists across hub restarts<br>• Progress tracking (0-100%)<br>• Retry on agent disconnect</p>\n</div>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:16px;\">\n<h4 style=\"color:#06b6d4;margin:0 0 8px 0;\">4. Presence Indicators</h4>\n<p style=\"color:#9ca3af;margin:0 0 8px 0;\">See who's watching, typing, and acting</p>\n<ul style=\"margin:0;padding-left:20px;color:#9ca3af;\">\n<li>\"johnathon is typing...\" on other devices</li>\n<li>Viewer count badge on session card</li>\n<li>Input focus sharing (who has cursor)</li>\n<li>Last activity timestamp per viewer</li>\n</ul>\n</div>\n\n<h3 style=\"color:#fff;margin:20px 0 12px 0;\">📍 Migration Path</h3>\n\n<table style=\"width:100%;border-collapse:collapse;margin-bottom:20px;\">\n<tr style=\"background:#3b82f6;\">\n<th style=\"padding:10px;text-align:left;color:#fff;\">Current (konui)</th>\n<th style=\"padding:10px;text-align:left;color:#fff;\">Phase 3 (greatVibe.local)</th>\n</tr>\n<tr style=\"background:#2d2d2d;\">\n<td style=\"padding:10px;color:#e0e0e0;\">SSE for streaming</td>\n<td style=\"padding:10px;color:#22c55e;\">WebSocket (bidirectional)</td>\n</tr>\n<tr style=\"background:#252525;\">\n<td style=\"padding:10px;color:#e0e0e0;\">konsole subprocess</td>\n<td style=\"padding:10px;color:#22c55e;\">gvShell agent (standalone)</td>\n</tr>\n<tr style=\"background:#2d2d2d;\">\n<td style=\"padding:10px;color:#e0e0e0;\">Single viewer per session</td>\n<td style=\"padding:10px;color:#22c55e;\">Multi-viewer broadcast</td>\n</tr>\n<tr style=\"background:#252525;\">\n<td style=\"padding:10px;color:#e0e0e0;\">Hub restarts lose context</td>\n<td style=\"padding:10px;color:#22c55e;\">Agent owns session state</td>\n</tr>\n<tr style=\"background:#2d2d2d;\">\n<td style=\"padding:10px;color:#e0e0e0;\">No agent registry</td>\n<td style=\"padding:10px;color:#22c55e;\">Connected agent tracking</td>\n</tr>\n</table>\n\n<h3 style=\"color:#fff;margin:20px 0 12px 0;\">🔄 Coexistence Strategy</h3>\n\n<p style=\"color:#9ca3af;margin-bottom:12px;\">Phase 3 runs <strong>alongside</strong> existing konsole — no production disruption:</p>\n\n<ol style=\"margin:0;padding-left:20px;color:#e0e0e0;line-height:2;\">\n<li><strong>New endpoint:</strong> <code style=\"background:#3b3b3b;padding:2px 6px;border-radius:3px;\">/ws/agent</code> for gvShell connections</li>\n<li><strong>Feature flag:</strong> Enable per-session via toggle</li>\n<li><strong>Route by capability:</strong> Sessions with advanced features → gvShell</li>\n<li><strong>Gradual migration:</strong> Move sessions one by one</li>\n</ol>\n\n<h3 style=\"color:#fff;margin:20px 0 12px 0;\">⏱️ Implementation Steps</h3>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-bottom:12px;\">\n<table style=\"width:100%;border-collapse:collapse;\">\n<tr style=\"border-bottom:1px solid #4b5563;\">\n<td style=\"padding:8px 0;width:40px;color:#22c55e;\">Step 1</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Add WebSocket endpoint to konui (<code>/ws/agent</code>)</td>\n</tr>\n<tr style=\"border-bottom:1px solid #4b5563;\">\n<td style=\"padding:8px 0;color:#22c55e;\">Step 2</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Implement agent-registry.ts (registration, heartbeat)</td>\n</tr>\n<tr style=\"border-bottom:1px solid #4b5563;\">\n<td style=\"padding:8px 0;color:#22c55e;\">Step 3</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Implement session-channel.ts (pub/sub, broadcast)</td>\n</tr>\n<tr style=\"border-bottom:1px solid #4b5563;\">\n<td style=\"padding:8px 0;color:#22c55e;\">Step 4</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Implement work-queue.ts (enqueue, assign, complete)</td>\n</tr>\n<tr style=\"border-bottom:1px solid #4b5563;\">\n<td style=\"padding:8px 0;color:#22c55e;\">Step 5</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Add presence indicators to dashboard UI</td>\n</tr>\n<tr>\n<td style=\"padding:8px 0;color:#22c55e;\">Step 6</td>\n<td style=\"padding:8px 0;color:#e0e0e0;\">Test end-to-end: gvShell ↔ Hub ↔ Browser</td>\n</tr>\n</table>\n</div>\n\n<div style=\"background:#1e3a5f;padding:16px;border-radius:6px;border:1px solid #3b82f6;\">\n<h4 style=\"color:#fff;margin:0 0 8px 0;\">💡 Key Insight</h4>\n<p style=\"color:#9ca3af;margin:0;\">The agent owns session state (SQLite + JSONL), the hub owns coordination (registry, queue, channels). This means hub restarts don't lose history — agents reconnect and replay.</p>\n</div>\n\n<div style=\"background:#2d2d2d;padding:16px;border-radius:6px;margin-top:16px;\">\n<h4 style=\"margin:0 0 8px 0;color:#fff;\">What's Next?</h4>\n<p style=\"color:#9ca3af;margin:0;\">Choose an action:</p>\n</div>\n</div>",
"choices": [
{
"label": "Start Step 1",
"value": "Start Phase 3 Step 1: Add WebSocket endpoint /ws/agent to konui for gvShell agent connections",
"primary": true
},
{
"label": "Show Phase 4",
"value": "What does Phase 4 (Integration) look like after Phase 3 Hub Enhancement?"
},
{
"label": "Review gvShell",
"value": "Show me the current gvShell progress and what's been built so far"
}
],
"requestedAt": "2026-01-07T07:30:00Z",
"requestId": "f438936f-e1f0-48fa-8178-24079f1dbad6",
"turnTiming": {
"totalMs": 75063,
"ttfeMs": 4321,
"thinkingMs": 70741,
"toolExecutionMs": 0,
"toolCallCount": 0,
"thinkingPct": 94,
"toolsPct": 0,
"ttfePct": 6
}
},
"createdBy": "claude",
"createdAt": "2026-01-07T13:12:06.395Z",
"updatedAt": "2026-01-07T13:12:12.914Z",
"requestId": "f438936f-e1f0-48fa-8178-24079f1dbad6",
"scope": "vibetools",
"tags": [
"gvshell",
"architecture",
"planning"
],
"targetUser": "claude"
}