Files
peardata/docs/DESKTOP.md
T
Raven Scott bce96d6550
CI / test (push) Successful in 2m38s
Release rolling / release (push) Failing after 6m17s
FIX: QVAC (QuantumVerse Automatic Computer) Packing
2026-07-30 14:17:06 -04:00

217 lines
8.1 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Desktop (Pear) UI
The client shell is a **Pear desktop application** built with `pear-electron` + `pear-bridge`. The HTML UI runs inside a frameless-style window with in-content chrome.
## Entrypoints
| File | Role |
|------|------|
| `index.js` | Pear process entry — starts `pear-electron` Runtime + `pear-bridge` |
| `index.html` | GUI main (`pear.gui.main`) — titlebar + panels |
| `app.js` | UI logic (connect, fleet, live charts, invites, Data Manager wiring) |
| `ui/dashboard.js` | Charts tab master metrics wall |
| `ui/data-manager.js` | Settings → Data (retention / prune / storage usage) |
| `ui/logs.js` | System Log tab (journal default for admins) |
| `ui/qvac/*` | QVAC local AI tab (onboarding + tools; needs `@qvac/sdk` in this project) |
| `shared/taxonomy.js` | Section grouping for the metrics wall |
| `shared/container-names.js` | Human Docker/cgroup labels for the wall |
| `shared/format.js` | Overview KPI unit scaling |
| `shared/retention.js` | Retention presets shared with the agent |
| `ui/styles.css` | Layout, theme, **titlebar drag regions** |
| `client/*` | HyperDHT connection stack used by the UI |
| `docs/DASHBOARD.md` | Master Charts / metrics wall plan |
| `user-guide/` | End-user workflows (Correlate, Related, Logs, Containers, Settings, …) |
```bash
npm start # pear run -d .
npm run dev # same
pear run -d . # equivalent
```
Requires the [Pear](https://docs.pears.com) CLI installed and bootstrapped (`pear` once to fetch the runtime).
## Window configuration (`package.json` → `pear.gui`)
| Field | Template default | Purpose |
|-------|------------------|---------|
| `main` | `index.html` | HTML entry |
| `width` / `height` | `1280` / `860` | Initial size |
| `minWidth` / `minHeight` | `900` / `560` | Resize floor |
| `resizable` | `true` | Edge/corner resize |
| `movable` | `true` | Allow OS move (with drag region) |
| `minimizable` / `maximizable` / `closable` | `true` | Window buttons |
| `hasShadow` | `true` | Native shadow |
| `backgroundColor` | `#0a0c10` | Avoid white flash on boot |
| `pre` | `pear-electron/pre` | Runtime bootstrap (required) |
Platform overrides are supported:
```json
{
"pear": {
"gui": {
"darwin": { "resizable": true },
"linux": { "autoHideMenuBar": true },
"win32": { "autoHideMenuBar": true }
}
}
}
```
See [pear-electron README](https://github.com/holepunchto/pear-electron) for the full option list (`center`, `alwaysOnTop`, `transparent`, `closeHides`, etc.).
## Titlebar + `<pear-ctrl>`
Pear provides a custom element **`<pear-ctrl>`** for platform window controls:
- **macOS (`darwin`)** — layout for system traffic lights (hidden title bar chrome)
- **Windows / Linux** — minimize, maximize, close controls rendered by the runtime
### Required HTML shape
```html
<div id="titlebar" role="banner">
<div class="titlebar-left">
<pear-ctrl></pear-ctrl>
<div class="app-brand"></div>
</div>
<div class="titlebar-right">
<!-- status chips, non-drag interactive bits -->
</div>
</div>
```
Do **not** remove `<pear-ctrl>` unless you intentionally ship a different window frame model and understand OS differences.
### Drag to move
```css
#titlebar {
-webkit-app-region: drag;
height: var(--titlebar-h); /* 42px in this template */
}
/* Interactive controls must not start a drag */
#titlebar pear-ctrl,
#titlebar .chip,
#titlebar button,
#titlebar input,
#titlebar a {
-webkit-app-region: no-drag;
}
.no-drag {
-webkit-app-region: no-drag;
}
```
### Resize
- Enabled by `pear.gui.resizable: true` (default in this template).
- Users resize via the OS window edges/corners.
- Content layout should flex with the viewport (`#app` uses `height: calc(100vh - var(--titlebar-h))`).
### Platform spacing
Reserve space so brand/text never sits under traffic lights:
```css
#titlebar pear-ctrl[data-platform='darwin'] { min-width: 78px; }
#titlebar pear-ctrl[data-platform='win32'],
#titlebar pear-ctrl[data-platform='linux'] { min-width: 110px; }
```
## Client identity (desktop process)
When the UI dials servers it uses a **persistent Ed25519 identity**:
| Item | Value |
|------|--------|
| Path | `~/.config/peardata/identity.json` (or `$PEARDATA_HOME/.config/peardata/…` if you set `PEARDATA_HOME` as home root — see `client/identity.js`) |
| Mode | Directory `0700`, file `0600` |
| Contents | `{ version, seedHex, createdAt }` |
Same identity ⇒ same `peerId` across restarts (useful for peer-bound capabilities and revoke).
Override home with `PEARDATA_HOME` if you need isolation (CI, multi-profile).
## UI modules
| Module | Responsibility |
|--------|----------------|
| `client/paths.js` | Unified `~/.config/peardata` home |
| `client/jsonCache.js` | Atomic JSON writes + LS mirror |
| `client/settings.js` | UI prefs → `cache/settings.json` |
| `client/peerCache.js` | Multi-host roster + last-active |
| `client/bookmarks.js` | Compat shim over peerCache |
| `client/identity.js` | Load/create keypair on disk |
| `client/connection.js` | Single HyperDHT + protomux-rpc session |
| `client/manager.js` | Multi-peer map, active selection, reconnect |
| `client/errors.js` | Unwrap / normalize RPC errors for UI |
| `app.js` | Wire DOM to manager + protocol methods |
## Persistence (PearDock-style)
| Store | Path |
|-------|------|
| Settings | `~/.config/peardata/cache/settings.json` (+ `localStorage` `peardata.settings.v1` FOUC) |
| Peers / last-active | `~/.config/peardata/cache/peers.json` |
| Identity | `~/.config/peardata/identity.json` |
Override root with `PEARDATA_HOME`. Writes are atomic (`tmp` → rename, mode `0600`). Legacy `bookmarks.json` / `ui-settings.json` migrate on first load.
### Multi-agent
- Many peers can be dialed at once; **one active** owns Overview / Charts RPC.
- Boot restores saved peers in parallel (`skipActivate`), then prefers last-active.
- Reconnect never steals the active host unless that host was active.
- Agents view + fleet strip: set active / connect / forget.
- Settings → Connections: auto-restore toggle, reconnect budget, forget-all.
### Manager reconnect
- Default max tries: settings `reconnectMaxAttempts` or `PEARDATA_MAX_RECONNECT` / **20**
- `connect(input, { adminSeed, autoReconnect, skipActivate })`
- Input may be **64-hex public key** or **`pd1.` invite**
## LocalStorage mirrors
| Key | Purpose |
|-----|---------|
| `peardata.settings.v1` | Flat settings FOUC + offline mirror |
| `peardata-ui-boot` | Theme-only early paint |
| `peardata_active_peer_id` | Last active peer mirror |
| `peardata.cache.peers` | Peers envelope mirror |
## Development tips
1. Keep DevTools available via `pear run -d .`
2. After HTML/CSS/JS edits, reload the Pear window (or restart `npm start`)
3. Server changes require restarting `npm run start:server`
4. If the window cannot be moved: check `#titlebar` has `drag` and children that cover the bar incorrectly are not all `no-drag` without a parent drag region
5. If controls dont work: ensure `<pear-ctrl>` is present and not covered by another element with a higher z-index and full-width hit target
## Packaging beyond Pear
This template ships the **Pear run** path only. For Electron-forge / multi-arch standalone binaries, adapt packaging from a fuller product (e.g. peardocks forge + bare-standalone scripts) once the app stabilizes.
## Charts investigation (summary)
| Control | Doc |
|---------|-----|
| Metrics wall, time, board, gestures | [user-guide/charts.md](../user-guide/charts.md) · [DASHBOARD.md](./DASHBOARD.md) |
| **Correlate** (highlight → Find Correlations) | [user-guide/metric-correlations.md](../user-guide/metric-correlations.md) |
| **Related (⇢)** (taxonomy + Pearson) | [user-guide/related-metrics.md](../user-guide/related-metrics.md) |
| **Filters** menu (search / TOC / group / sort) | [user-guide/charts.md](../user-guide/charts.md) |
| **Logs** tab | [user-guide/logs.md](../user-guide/logs.md) |
Implementation: `ui/dashboard.js`, `ui/logs.js`, `server/services/weights.js`, `server/services/logs.js`, `shared/related-metrics.js`.
## Related
- [User guide](../user-guide/README.md)
- [GETTING-STARTED.md](./GETTING-STARTED.md)
- [ARCHITECTURE.md](./ARCHITECTURE.md)
- [CONFIGURATION.md](./CONFIGURATION.md)
- [EXTENDING.md](./EXTENDING.md)