Design Decision · August 17, 2026
The Work Room Is a Client, Not a Status Panel
Remote control needs a real conversation surface without making the browser a second runtime.
A one-message demo can make a coding agent look finished long before it has done anything useful. A proper acceptance run needs to inspect a workspace, write a small program, compile it, run tests, pause for a decision, and continue. That is when a product learns whether its interface is reporting work or merely accumulating boxes.
The decision
ConnectOnion Core is the one writer of native coding-provider state. The React package validates and normalizes that bounded OIP state. O Chat renders one compact parent card and one continuous remote client with attributed conversation, live work, provider controls, and a fixed composer.
One writer, defensive readers
Codex and Claude Code are native providers. Their adapters translate provider lifecycle into typed OIP events with a provider, invocation identity, revision, semantic activity, bounded message, approval and optional real image evidence. Core decides what is safe to expose. It does not send raw commands, paths, hidden prompts or terminal output to the browser.
@connectonion/react does not reconstruct that state from a chat transcript. It validates the envelope, rejects stale authority, and keeps the correlation needed for reconnect and direct input. O Chat does not implement a second provider adapter. It reads the normalized state and renders it.
Why the first simplification went too far
The first design put a conversation panel, a status card, a preview panel, an activity list and a composer next to one another. Each element was reasonable in isolation, but together they made the reader decide where to look before they could understand what Codex was doing.
The answer was hierarchy, not deletion. A Work Room is the remote client for a Codex or Claude Code session, so attributed user and provider messages, current lifecycle, meaningful work, and the provider-targeted input must remain recognizable. Earlier technical activity can fold away; the conversation cannot.
The current hierarchy asks what is happening now? at the top, then keeps the native conversation in one reading flow and the composer fixed at the bottom. Approval becomes the primary action, but it does not erase the conversation or input. If approval, Stop, reconnect, provider-busy, or an older Host prevents sending, the input remains visible and explains why it is disabled.
Evidence is not decoration
A Codex thumbnail is useful only when it is actual provider evidence for the current invocation revision. Text and terminal output must not be dressed up as a screenshot. If the provider has no verified raster, the card remains text-first. That is a truthful absence, not an incomplete simulation.
The same rule applies to direct messages. A Work Room message is not called sent because a host queued it. The browser retains its draft until live Codex accepts turn/steer, or a resumed native thread accepts a new turn/start. The acknowledgement therefore describes an event that happened, rather than a request that might happen later.
Voice input keeps that destination boundary. Codex and Claude Code use the same recording, transcription, and actionable microphone errors as the outer composer, but the transcript enters only the provider draft on screen. It is never rerouted or sent automatically. The user reviews it and presses Send; failures, approval, Stop, and reconnect uncertainty keep the draft recoverable.
Permission is not one generic dropdown
The first release-candidate review found a concrete mismatch: the outer COAI permission control was visible, but the opened Codex Work Room had no Codex-native profile selector. Those controls answer different questions. COAI sets the Host ceiling; the Work Room chooses provider behavior inside that ceiling; an individual approval decides one requested action.
Codex also proves why a single cross-provider enum is lossy. Ask for approval and Approve for me share the native :workspace sandbox but use different reviewers. Claude Code has its own Plan, Default, Accept edits, Auto, and Bypass permissions profiles. The shared shell therefore renders a finite provider-authored catalog while retaining native identity, reviewer policy, disabled choices, and the exact revision that made the choice effective.
A browser click is only a request. Host verifies the session owner, Operator role, current revision, outer ceiling, and a separate elevated-risk confirmation before acknowledging a newer state. The UI keeps the old label until that acknowledgement arrives. On phones the 48-pixel selector occupies its own header row and the menu is clamped to the viewport, so preserving authority does not recreate the crowded Work Room that the earlier simplification was trying to fix.
Why RC1 is allowed before stable
A release candidate is useful because it gives every layer one immutable version to test. It is not a declaration that the product is already stable. RC1 synchronizes Core, the React reader, and O Chat so the same installed bytes can be used for provider, browser, upgrade, rollback, security, and UI review. A failure creates another issue and candidate; it does not get explained away as a passing release.
Promotion therefore requires evidence outside the interface. A real co ai run must driveco browser through search and an actual download, build and run C, C++, and Rust work, delegate a native Codex project, exercise modes, Stop, Host restart, and reconnect, and leave sanitized logs plus hash-addressed screenshots. A separate reviewer must inspect every frame for new-user clarity, remote-client familiarity, conversation/composer continuity, live work, tool activity, and responsive layout. Stable 1.7 can use the RC bytes only if that unchanged candidate passes the complete window.
What the candidate must prove
- One compact parent-card action opens the Work Room.
- A long native run stays readable on desktop and a 375px phone width.
- User and provider messages remain attributed while earlier technical activity stays folded.
- Codex and Claude Code keep a provider-targeted text and voice input in every lifecycle state.
- Provider-native permission choices remain separate from outer COAI mode and individual approvals.
- Desktop, tablet, and phone layouts keep the permission menu fully inside the viewport.
- Approval, Stop and native direct input retain their own honest lifecycle boundaries.
- Initial semantic focus announces the task heading without styling that non-interactive text as a control; buttons and the composer keep visible keyboard focus.
- Only native Codex and Claude Code adapters participate in this release path.
This is intentionally a preview boundary, not a promise that every future coding feature belongs in the Work Room. Automatic approval and deeper autonomy need their own policy and review design. For now, the product proves that a real native run can remain calm, inspectable and truthful.
ConnectOnion