This commit is contained in:
+57
-6
@@ -8,7 +8,8 @@ Lumbridge should be two cooperating Rust processes:
|
||||
native desktop UI
|
||||
| local authenticated IPC
|
||||
Lumbridge session runtime
|
||||
|-- PTYs and process trees
|
||||
|-- local PTYs and process trees
|
||||
|-- SSH/Tailscale transport to remote Lumbridge runtimes
|
||||
|-- ACP clients and adapters
|
||||
|-- repositories and worktrees
|
||||
|-- usage/event ledger
|
||||
@@ -30,13 +31,18 @@ messages should be real from the beginning.
|
||||
- `lumbridge-harness`: manifests, launch profiles, hooks, PTY fallback adapters.
|
||||
- `lumbridge-provider`: BYOK providers and provider-neutral usage records.
|
||||
- `lumbridge-storage`: SQLite migrations, event log, snapshots, retention.
|
||||
- `lumbridge-remote`: OpenSSH/Tailscale command construction, framed stdio,
|
||||
handshake, reconnect, heartbeat, and remote-runtime discovery.
|
||||
- `lumbridge-secrets`: Keychain/libsecret adapters and redaction.
|
||||
- `lumbridge-git`: repositories, worktrees, diffs, status, conflict state.
|
||||
- `lumbridge-buzz`: credential-free Buzz event/broker preparation and pane-share
|
||||
safety gates; platform adapters own signing and transport.
|
||||
- `lumbridge-ui`: native desktop state and rendering.
|
||||
- `lumbridge`: installable application entry point.
|
||||
|
||||
Only `lumbridge-core` and the entry point exist in the scaffold. New crates are
|
||||
added after their architecture spike passes.
|
||||
The scaffold currently contains `lumbridge-core`, `lumbridge-storage`,
|
||||
`lumbridge-buzz`, and the entry point. Larger runtime crates are added after
|
||||
their architecture spikes pass.
|
||||
|
||||
## Terminal path
|
||||
|
||||
@@ -57,13 +63,46 @@ Do not lock the project to a webview or to Zed's private implementation details
|
||||
before a measured spike. Compare:
|
||||
|
||||
1. GPUI for a Zed-like native model and excellent text-heavy interaction.
|
||||
2. Iced/wgpu plus a dedicated terminal renderer for stable Rust portability.
|
||||
3. Tauri only as a delivery-speed baseline, not the assumed winner.
|
||||
2. Floem for an independent native Rust model with existing editor primitives.
|
||||
|
||||
The winner must render six busy panes smoothly, keep input latency low, support
|
||||
IME/accessibility, package on macOS and both Linux targets, and avoid a license
|
||||
or upstream-stability trap.
|
||||
|
||||
## Local-first and remote session path
|
||||
|
||||
SQLite is device-local. It stores workspace metadata, pane layouts, event and
|
||||
usage history, remote routing profiles, and small snapshots. It never stores SSH
|
||||
private keys, Tailscale credentials, provider API keys, or subscription tokens.
|
||||
Secrets remain in the OS credential store or in the user's existing SSH agent.
|
||||
|
||||
A remote pane is not a local PTY wrapped around a long-lived `ssh` process. Its
|
||||
durable owner is a per-user `lumbridge-runtime` on the destination:
|
||||
|
||||
```text
|
||||
MacBook Lumbridge UI/runtime
|
||||
|
|
||||
| ssh host lumbridge remote connect --stdio
|
||||
| or: tailscale ssh host lumbridge remote connect --stdio
|
||||
v
|
||||
remote per-user Lumbridge runtime -- Unix socket -- PTYs, agents, worktrees
|
||||
|
|
||||
`-- remote SQLite + chunked scrollback on that machine
|
||||
```
|
||||
|
||||
The SSH child carries a versioned framed protocol over stdio. Normal OpenSSH
|
||||
remains the default because it honors the user's config, agent, host keys,
|
||||
ProxyJump, and Tailscale addresses. `tailscale ssh` is an explicit transport for
|
||||
users who want Tailscale's SSH proxy and host-key path. Lumbridge does not
|
||||
configure a tailnet, weaken ACLs, copy SSH keys, or require a listening TCP port.
|
||||
|
||||
The remote runtime assigns a stable session ID before acknowledging a launch.
|
||||
On network loss the local pane becomes disconnected, the remote PTY continues,
|
||||
and reconnect resumes from the last acknowledged output sequence. A second
|
||||
authorized Lumbridge installation can attach to the same remote session after
|
||||
the remote runtime arbitrates input ownership. Collaborative simultaneous input
|
||||
is not part of the first release.
|
||||
|
||||
## Harness integration
|
||||
|
||||
Each harness is described by a versioned manifest: executable discovery, launch
|
||||
@@ -88,6 +127,14 @@ usually expose token counts but cost still depends on cached tokens, reasoning,
|
||||
tool calls, and current pricing. Adapters normalize facts without erasing their
|
||||
source or uncertainty.
|
||||
|
||||
## Buzz collaboration
|
||||
|
||||
Buzz channel messages, replies, agents, and attachments use the upstream Rust
|
||||
SDK's signed Nostr semantics. SQLite stores a public identity and opaque
|
||||
credential-store handle, never the private identity key. Pane images cross the
|
||||
network only after local capture, redaction preview, explicit destination, and
|
||||
confirmation. See `BUZZ_INTEGRATION.md` for the contract and test plan.
|
||||
|
||||
## Persistence
|
||||
|
||||
SQLite in WAL mode stores metadata, commands/events, normalized usage, and small
|
||||
@@ -95,6 +142,11 @@ snapshots. Large scrollback chunks and binary attachments use content-addressed
|
||||
files. A write-ahead event is committed before an external mutation is reported
|
||||
as accepted. Startup replays incomplete operations and reconciles live children.
|
||||
|
||||
Default data roots are `~/Library/Application Support/ai.karti.lumbridge/` on
|
||||
macOS and `${XDG_DATA_HOME:-~/.local/share}/lumbridge/` on Linux. Backups and
|
||||
exports are explicit; Lumbridge does not synchronize the database through a
|
||||
hidden hosted account.
|
||||
|
||||
## Security
|
||||
|
||||
- macOS secrets: Keychain; Linux secrets: Secret Service/libsecret, with an
|
||||
@@ -113,4 +165,3 @@ Shared contracts cover PTY, process tree, notifications, secret store, paths,
|
||||
autostart, updater, and packaging. macOS uses `forkpty`/process groups and native
|
||||
Keychain. Ubuntu and Omarchy use Unix PTYs, cgroups/systemd scopes when available,
|
||||
and Secret Service. Omarchy is treated as Arch Linux, not as a separate kernel.
|
||||
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
# Buzz integration
|
||||
|
||||
## Product boundary
|
||||
|
||||
Buzz is Lumbridge's first-class collaboration surface, not its control plane.
|
||||
Lumbridge remains useful offline, owns its local workspace state, and never
|
||||
requires a Buzz account to open a terminal or run an agent.
|
||||
|
||||
The initial integration provides:
|
||||
|
||||
- connect an existing Buzz identity using an OS credential-store reference;
|
||||
- bind one or more Buzz channels to a Lumbridge workspace;
|
||||
- read and post channel messages and replies from a collaboration pane;
|
||||
- surface Buzz agents attached to a bound channel without pretending they are
|
||||
local processes;
|
||||
- share an approved pane image to an explicitly selected channel.
|
||||
|
||||
## Protocol shape
|
||||
|
||||
The pinned upstream is Block's Apache-2.0 Buzz repository at commit
|
||||
`cb3144999bebc4939cb15b2200b373281d493b52`. `buzz-sdk` constructs typed Nostr
|
||||
events and broker actions but deliberately owns neither identity keys nor
|
||||
network connections. Lumbridge follows that separation:
|
||||
|
||||
```text
|
||||
Lumbridge collaboration pane
|
||||
| typed local command
|
||||
lumbridge-buzz
|
||||
| Buzz SDK event/broker action
|
||||
identity signer + Buzz transport adapter
|
||||
| signed WebSocket / HTTPS upload
|
||||
Buzz relay and attachment storage
|
||||
```
|
||||
|
||||
The exact revision stays pinned until an audited upgrade. We use Buzz's signed
|
||||
protocol and SDK types rather than a parallel webhook format.
|
||||
|
||||
## Identity and local data
|
||||
|
||||
SQLite stores the account label, relay URL, public key, and an opaque secret
|
||||
store handle. The Nostr private key stays in macOS Keychain or Linux Secret
|
||||
Service. It must never enter SQLite, command arguments, crash reports, pane
|
||||
history, logs, or Git configuration.
|
||||
|
||||
An installed Buzz CLI identity may be imported only through an explicit user
|
||||
flow that transfers it into the OS credential store. Lumbridge must not search
|
||||
the filesystem for keys. Buzz's current NIP-AB device-pairing tooling is marked
|
||||
for interoperability testing upstream, so it is not a production login promise.
|
||||
|
||||
## Pane-image sharing
|
||||
|
||||
Sharing is a user-visible state machine:
|
||||
|
||||
1. Capture the selected pane only, excluding application chrome by default.
|
||||
2. Detect likely secrets and render a local preview with proposed redactions.
|
||||
3. Let the user adjust redactions, caption, and destination channel.
|
||||
4. Require confirmation of that exact preview and destination.
|
||||
5. Encode PNG or WebP, hash it, upload with the authenticated Buzz attachment
|
||||
flow, and receive a canonical URL.
|
||||
6. Build a kind-9 Buzz message with Markdown plus an `imeta` tag, sign it using
|
||||
the OS-held identity, and publish it.
|
||||
7. Persist only the resulting event ID, attachment metadata, destination, and
|
||||
local audit outcome. Never persist the unredacted capture.
|
||||
|
||||
Any change to the pixels, caption, or destination invalidates confirmation. A
|
||||
failed upload or publish is retryable but never reported as sent.
|
||||
|
||||
## Agent integration
|
||||
|
||||
Buzz agents and Lumbridge harnesses are different entities. A Buzz agent may be
|
||||
shown in the collaboration pane and may exchange messages through Buzz's broker
|
||||
contract. A local or remote Lumbridge harness remains owned by the Lumbridge
|
||||
runtime and communicates through ACP or a supervised PTY. Linking the two later
|
||||
requires an explicit capability grant, visible identity, and revocation path.
|
||||
|
||||
## Test plan
|
||||
|
||||
- deterministic unit tests for channel IDs, content limits, media metadata, and
|
||||
the review/confirmation gate;
|
||||
- signature tests with generated fixture identities only;
|
||||
- integration tests against a disposable local Buzz relay and attachment store;
|
||||
- disconnect, duplicate-delivery, cursor-resume, and publish-retry tests;
|
||||
- rendered tests proving destination and redactions remain visible at confirm;
|
||||
- a real-account smoke test only in a manually enabled, non-CI test profile.
|
||||
+29
-2
@@ -21,6 +21,24 @@ The product should feel faster and calmer as concurrency rises.
|
||||
5. Review file and Git changes by workspace or worktree.
|
||||
6. Understand usage, rate-limit windows, burn rate, and likely exhaustion time.
|
||||
7. Resume the entire workspace after the UI or machine restarts.
|
||||
8. Work from a laptop while selected panes and agents run durably on a
|
||||
user-owned machine reached through SSH or Tailscale.
|
||||
9. Follow a project's Buzz channel and intentionally share a redacted pane image
|
||||
without leaving the workspace.
|
||||
|
||||
## Local and remote workspaces
|
||||
|
||||
Every Lumbridge installation is useful on its own and owns its local settings,
|
||||
history, usage observations, and workspace views. A pane can execute locally or
|
||||
on a saved remote host. Remote hosts may be normal SSH destinations, entries in
|
||||
the user's SSH config, Tailscale MagicDNS names, or tailnet IPs.
|
||||
|
||||
For durable remote work, a per-user Lumbridge runtime on the destination owns
|
||||
the PTY and process tree. The desktop app connects to that runtime over an SSH
|
||||
stdio channel and can later reconnect without moving the process to a cloud
|
||||
service. The same remote workspace may be opened from another authorized
|
||||
Lumbridge installation, but local UI state is not silently merged between
|
||||
devices.
|
||||
|
||||
## Initial harnesses
|
||||
|
||||
@@ -64,13 +82,23 @@ harness-reported, locally measured, estimated, or unavailable. Lumbridge must
|
||||
not scrape browser cookies or reverse-engineer private account APIs to manufacture
|
||||
an exact remaining balance. When only local observations exist, the UI says so.
|
||||
|
||||
## Buzz collaboration
|
||||
|
||||
Buzz is optional and deeply integrated: an engineer can connect an existing
|
||||
identity, bind channels to workspaces, read and send messages, see channel
|
||||
agents, and share a pane image. Sharing always previews the exact capture,
|
||||
redactions, caption, and destination before upload. Buzz identity secrets stay
|
||||
in the operating-system credential store.
|
||||
|
||||
## Non-goals for the first release
|
||||
|
||||
- A new foundation-model training or inference service.
|
||||
- A hosted account or mandatory Lumbridge cloud.
|
||||
- Replacing every coding harness with one Lumbridge-owned agent loop.
|
||||
- Windows support.
|
||||
- Mobile control, collaborative cloud sessions, or remote execution.
|
||||
- Mobile control or collaborative hosted sessions.
|
||||
- Arbitrary third-party remote compute provisioning; the first release connects
|
||||
only to machines and SSH/Tailscale access the user already controls.
|
||||
- Bundling third-party subscriptions or reselling model tokens.
|
||||
|
||||
## Experience principles
|
||||
@@ -81,4 +109,3 @@ an exact remaining balance. When only local observations exist, the UI says so.
|
||||
- Approval and security boundaries stay visible.
|
||||
- Local and offline workflows remain useful.
|
||||
- Estimates are useful only when their uncertainty is honest.
|
||||
|
||||
|
||||
+8
-1
@@ -4,9 +4,13 @@
|
||||
|
||||
- Capture upstream snapshots, licenses, relevant modules, and architectural notes.
|
||||
- Benchmark UI candidates with six animated terminal panes.
|
||||
- Prove OpenSSH and `tailscale ssh` stdio transports against a disposable remote
|
||||
runtime, including disconnect and replay.
|
||||
- Spike PTY correctness and process-tree cleanup on macOS, Ubuntu, and Omarchy.
|
||||
- Connect the official ACP Rust SDK to two contrasting harnesses.
|
||||
- Audit actual usage/quota surfaces for every launch provider.
|
||||
- Prove Buzz SDK message, attachment, cursor, reconnect, and duplicate-delivery
|
||||
behavior against a disposable local relay.
|
||||
- Decide terminal core, UI stack, IPC transport, and schema evolution policy.
|
||||
|
||||
Exit: recorded decisions with working spikes and measured results.
|
||||
@@ -14,8 +18,12 @@ Exit: recorded decisions with working spikes and measured results.
|
||||
## Phase 1 — terminal workspace alpha
|
||||
|
||||
- Durable runtime, local IPC, workspaces, tabs, splits, shells, scrollback.
|
||||
- Saved SSH/Tailscale hosts and durable remote panes through a per-user remote
|
||||
runtime; reconnect from a second Lumbridge installation.
|
||||
- Session restore, crash recovery, command palette, keybindings, notifications.
|
||||
- Repository/worktree creation and basic Git status/diff.
|
||||
- Optional Buzz collaboration pane, workspace channel binding, and confirmed
|
||||
redacted pane-image sharing.
|
||||
- macOS, Ubuntu, and Omarchy development packages.
|
||||
|
||||
Exit: Lumbridge is worth using as a terminal multiplexer without AI features.
|
||||
@@ -44,4 +52,3 @@ Exit: usage displays are useful, auditable, and honest about uncertainty.
|
||||
- Signed/notarized macOS releases, `.deb`, AppImage, and Arch package.
|
||||
- Delta updater with signed manifests and rollback.
|
||||
- Accessibility, performance, soak, migration, and recovery qualification.
|
||||
|
||||
|
||||
@@ -0,0 +1,26 @@
|
||||
# Native UI spike scorecard
|
||||
|
||||
The GPUI and Floem programs under `spikes/` consume the same six-pane fixture.
|
||||
No product framework decision is accepted until both rows contain measurements
|
||||
from macOS and Linux and the hard gates pass.
|
||||
|
||||
| Criterion | Hard gate | GPUI | Floem |
|
||||
|---|---:|---:|---:|
|
||||
| Builds on macOS Apple Silicon | yes | pending | pending |
|
||||
| Builds on Ubuntu | yes | pending | pending |
|
||||
| Builds on Omarchy/Arch | yes | pending | pending |
|
||||
| Dependency/license closure permits Apache-2.0 distribution | yes | pending | pending |
|
||||
| Keyboard navigation + AccessKit tree | yes | pending | pending |
|
||||
| IME and composed Unicode input | yes | pending | pending |
|
||||
| Isolated system browser child | yes | pending | pending |
|
||||
| Cold startup, p50/p95 | record | pending | pending |
|
||||
| Idle RSS / six-stream RSS | record | pending | pending |
|
||||
| Key-to-present p50/p95 | record | pending | pending |
|
||||
| Six-stream frame p95/p99 | record | pending | pending |
|
||||
| Release binary/package size | record | pending | pending |
|
||||
| Native menu/window/clipboard/drag-and-drop | review | pending | pending |
|
||||
| API clarity and maintenance burden | review | pending | pending |
|
||||
|
||||
The current programs establish dependency, build, launch, and static layout
|
||||
baselines. The next iteration adds deterministic streaming, input timestamps,
|
||||
accessibility identifiers, a native Markdown editor, and one Wry browser child.
|
||||
@@ -0,0 +1,25 @@
|
||||
# 0003: Data is local; remote sessions live on the user's remote machine
|
||||
|
||||
Status: accepted for implementation.
|
||||
|
||||
Each Lumbridge installation owns a local SQLite database and content-addressed
|
||||
data directory. There is no mandatory Lumbridge account, hosted database, or
|
||||
silent multi-device synchronization. Credentials remain in platform credential
|
||||
stores, SSH agents, or upstream harnesses rather than SQLite.
|
||||
|
||||
Lumbridge supports local work and user-owned remote machines as equal execution
|
||||
targets. OpenSSH is the default transport and may reach a Tailscale MagicDNS name
|
||||
or tailnet address. An explicit `tailscale ssh` transport is also supported.
|
||||
Lumbridge consumes existing connectivity and authorization; it does not manage
|
||||
tailnet ACLs or private keys.
|
||||
|
||||
Durability belongs where the process runs. A remote per-user Lumbridge runtime
|
||||
owns remote PTYs, agents, worktrees, event history, and scrollback. Desktop apps
|
||||
connect over a framed SSH stdio stream and reconnect by stable session ID. This
|
||||
allows a MacBook to close or change networks without terminating work on metal
|
||||
or amd-server.
|
||||
|
||||
Another authorized Lumbridge installation may discover and attach to that remote
|
||||
workspace. Its device-local window layout and preferences remain local. The
|
||||
remote runtime arbitrates a single input owner in the first release; real-time
|
||||
collaborative editing is a separate future capability.
|
||||
Reference in New Issue
Block a user