Files
desktop/PLUGIN.md
T
pastilhasandClaude Opus 5 b91d4df21d desktop, extracted from the platform
x11vnc against display :0 — the session the owner is actually logged into, not a second one Officer
installs. sidecar/, api/, web/ and the host setup script, moved out of src/ whole.

Dormant when it moved: the websocket was commented out in server.tsx and the router in hono.ts since
2026-08-13, and no officer-vnc process was running on any machine. Nothing regressed and nothing was
restored — this took switched-off code out of the platform.

The point of the move is what the platform stopped knowing. Its sidecar/protocol.ts carried a VNC
section — vnc:start, vnc:ensure-password, vnc:stop, four reply variants, VncStartParams,
VncSessionInfo — and sidecar-registry.ts carried startVnc, ensureVncPassword, stopVnc and
isVncConnected. That is the platform speaking a plugin's vocabulary, which CLAUDE.md names as a rule
and this was the clearest breach of. All of it is in sidecar/protocol.ts here now.

The permission made a round trip worth recording. It was kind: 'execution' — "runs as the server owner
and cannot be shared" — and a plugin permission has no kind, deliberately, because a permission nobody
can delegate is a contradiction. So the property is expressed as ownerOnly: ['/'] instead: every path
under this plugin refused to anyone but the owner. Same answer, reached from the paths rather than
from a kind, and the first real use of a mechanism that landed the same day. The property is real —
there is one physical screen and it is the owner's.

Not finished, and BLOCKERS.md says so rather than the commit implying otherwise: the websocket is
dormant because a plugin cannot claim a WebSocket provider, host setup needs a reboot and no manifest
can express that, and there is no artwork.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-21 00:41:24 +00:00

3.3 KiB

Desktop

This machine's physical screen, mirrored into the browser. Extracted from the platform on 2026-08-21.

What it is, and what it is not

x11vnc attached to display :0 — the session the owner is actually logged into, not a second one. Officer used to install a desktop of its own (XFCE on a TigerVNC Xvnc server) and stopped: mirroring the real session means what you see remotely is what is on the screen, and there is one place for a thing to be rather than two.

That choice is why the permission is owner-only. There is one screen; two accounts granted this would see the same one, and it is the owner's.

What moved

src/servers/sidecar/vnc/            → sidecar/     x11vnc lifecycle, password provisioning
src/servers/api/desktop/            → api/         one route, plus a dormant websocket
officerdev/src/apps/Desktop/        → web/         the noVNC panel, header, wrapper
scripts/setup-old/setup-desktop.sh  → setup/       host setup, still run by hand

It was dormant when it moved: the websocket was commented out in server.tsx and the router in hono.ts from 2026-08-13, and no officer-vnc process was running on any machine. This extraction moved switched-off code out of the platform. It did not break a working feature, and it did not restore one.

What the platform lost, which is the point

The platform's sidecar/protocol.ts had a // ── VNC ── section: vnc:start, vnc:ensure-password, vnc:stop, their four reply variants, and VncStartParams/VncSessionInfo. sidecar-registry.ts had startVnc, ensureVncPassword, stopVnc and isVncConnected.

That is the platform knowing what a plugin is about — CLAUDE.md names it as a rule and this was its clearest violation. All of it lives in sidecar/protocol.ts here now.

What replaced it is generic: sendSidecarCommand(kind, cmd) and isSidecarConnected(kind), which know that a command has a type and an id and a reply carries the same id, and nothing else. Any plugin's sidecar can be driven through them without a line changing in the platform.

Host setup is not automatic

setup/setup-desktop.sh is run by hand, and the plugin cannot run it. See BLOCKERS.md §1 — the short version is that it rewrites GDM's config and needs a reboot, and a manifest can declare packages, not a reconfigured display manager.

The manifest declares x11vnc alone, which is the one part that is a package check and the one whose absence produces a sidecar that starts and immediately fails.

Known gaps

BLOCKERS.md is the list. The two that matter:

  • the websocket is dormant and a plugin cannot claim a WebSocket provider, so /desktop does not work yet — it did not work before the move either
  • no artwork; the glyph and colour in the manifest are the fallback

Iris depends on the other half of this

plugins/iris captures pages using sessions from a browser profile at ~/.config/officer/browser-profile — the profile a browser running in this desktop signs into. Its wrapper says "install the desktop plugin" when it finds no Chrome-family browser.

The browser relay (src/servers/api/browser/, src/extensions/browser-relay/) is a separate extraction, agreed as its own plugin and not started. This plugin's setup-desktop.sh installs Brave, which is what iris actually needs on the host.