40a940304b
- Create enhanced health endpoints with /health and /health/db - Add comprehensive docstrings to all API endpoints - Add Pydantic response models with Field descriptions - Create apps/api/README.md with setup guide - Create ADR-001 for session auth decision - Create ADR-002 for async SQLAlchemy decision - Quality gates: Python syntax OK, TypeScript OK
3.9 KiB
3.9 KiB
Tool Terminal - Design
Architecture
Browser Backend Container
│ │ │
│ WebSocket connect │ │
│─────────────────────────>│ │
│ │ docker exec -it bash │
│ │───────────────────────────>│
│ │ │
│ stdin (keystrokes) │ stdin │
│─────────────────────────>│───────────────────────────>│
│ │ │
│ stdout/stderr │ stdout/stderr │
│<─────────────────────────│<───────────────────────────│
│ │ │
│ resize (cols, rows) │ pty resize │
│─────────────────────────>│───────────────────────────>│
│ │ │
Component Design
Backend
TerminalManager:
- Manages active terminal sessions
- Maps WebSocket connections to container processes
- Handles session lifecycle (create, resize, cleanup)
WebSocket Endpoint:
GET /ws/tool-instances/{instance_id}/terminal- Authenticates user via session cookie
- Establishes bidirectional WebSocket
- Spawns
docker exec -itwith pseudo-TTY
Docker PTY:
- Uses
docker execwith TTY allocation - Streams stdin/stdout/stderr via subprocess
- Handles resize via
sttyor docker API
Frontend
TerminalComponent:
- Wraps xterm.js terminal
- Manages WebSocket connection
- Handles terminal resize
- Fits container to parent element
TerminalPage:
- Full-page terminal view
- Shows instance name in header
- Connection status indicator
- Reconnect on disconnect
Data Flow
- User clicks "Terminal" on running instance
- Frontend opens WebSocket connection
- Backend verifies ownership and spawns shell
- Bidirectional streaming begins
- User types → WebSocket → docker exec stdin
- Container output → docker exec stdout → WebSocket → xterm.js
- Resize events forwarded to adjust PTY dimensions
Session Lifecycle
Connect
│
▼
Authenticate ──> Reject (403)
│
▼
Spawn Shell
│
▼
Stream I/O ◄───> Resize
│
▼
Disconnect
│
▼
Cleanup Process
Access Control
- WebSocket handshake validates session cookie
- Backend verifies user owns the instance
- Reject connection with 403 if unauthorized
- Close connection if instance stops running
Technical Details
Backend Libraries:
asynciofor WebSocket handlingsubprocesswithdocker exec -itfcntlfor PTY resize (Linux)
Frontend Libraries:
xterm- Terminal emulatorxterm-addon-fit- Auto-fit to containerxterm-addon-web-links- Clickable URLs
Docker Commands:
# Spawn shell
docker exec -it {container_id} /bin/bash
# Alternative with explicit TTY
docker exec -i {container_id} sh -c 'exec bash'
Error Handling
- Connection refused → Show error message
- Container not running → Disable terminal button
- Shell spawn failed → Show error and close
- Network disconnect → Attempt reconnect
CSS Integration
.terminal-container {
width: 100%;
height: 100%;
min-height: 400px;
background: #1e1e1e;
border-radius: 8px;
overflow: hidden;
}
.terminal-container .xterm {
padding: 8px;
}