Commit Graph

49 Commits

Author SHA1 Message Date
Peter Steinberger 1353ce0995 feat: run Codex sessions on approved paired devices (#127202)
* feat(codex): execute paired-device sessions over node carrier

* fix(node-host): preserve approved invocation session identity

* fix(codex): observe paired-node execution leases before handshake

* fix: fence paired-device placement and Codex execution owners

* fix: satisfy paired-device placement CI ownership guards

* fix(codex): reject credentialed paired-node URL parameters

* fix(codex): fence nested remote HTTP session credentials

* fix(codex): scrub node process URLs and preserve plaintext HTTP

* test(codex): republish node inventory after capability approval
2026-08-21 12:50:26 -07:00
Peter Steinberger 0d555266e4 refactor(nodes): retire legacy runner inventory parsing (#126773) 2026-08-20 11:53:00 -07:00
Peter Steinberger bbbd70542b feat(sessions): recover offline device placements (#126284)
* feat(sessions): recover offline device placements

* chore(protocol): refresh session placement models

* perf(ui): lazy-load session placement recovery

* test(ui): remove dropdown timing assertion

* test(ui): await committed cloud recovery route

* fix(sessions): complete explicit abandonment locally

* fix(sessions): fence lists by runner availability

* fix(ui): preserve canonical session freshness

* fix(sessions): preserve recovery contracts after rebase

* test(ui): await durable cloud recovery entry

* test(gateway): complete current runner fixtures

* fix(gateway): publish runner availability edges

* fix(ui): preserve shared session freshness

* fix(ui): preserve canonical sidebar session state

* fix(sessions): preserve abandoned partials and run-owned replies

* fix(sessions): resume durable abandonment retries

* test(gateway): compose provisioning replay with runner availability

* fix(sessions): publish recovered move transitions
2026-08-20 09:59:59 -07:00
Peter Steinberger 2d13e16705 fix: harden node desktop carrier (#126425) 2026-08-19 12:57:26 -07:00
Peter Steinberger 80934e5639 feat(ui): dispatch sessions to paired devices (#126187) 2026-08-19 01:11:49 -07:00
Peter Steinberger 9924e2d7a7 feat(cli): prepare session-host onboarding (#125879)
* feat(cli): prepare session-host onboarding

* fix(cli): gate session-host installer capability
2026-08-18 16:08:48 -07:00
Peter Steinberger efaa867d93 feat(nodes): publish exact runner slots (#125708)
* feat(nodes): publish exact runner slots

* docs(runners): link slot inventory PR

* fix(ui): keep session menus clickable under previews

* perf(protocol): keep runner slot schema off broad barrel

* test(codex): tolerate elapsed media startup budget

* test(codex): type media client factory mocks

* fix(protocol): reject impossible runner slot counts

* test(ci): stabilize loaded lifecycle checks

* test(ui): allow loaded bulk-delete scheduling

* test(ui): stabilize loaded interaction checks

* test(ui): isolate loaded update notice checks

* test(ui): colocate bulk-delete lifecycle coverage

* test(gateway): publish session config before async setup
2026-08-18 07:08:06 -07:00
Peter Steinberger 9ba8671296 refactor(agents): unify exec approval routing (#125587)
* refactor(agents): unify exec approval routing

* docs(plan): record approval route cleanup
2026-08-17 21:40:31 -07:00
Peter Steinberger 4ed01969e8 refactor(agents): unify exec approval wait outcomes (#125524)
* refactor(agents): unify exec approval wait outcomes

* docs(plan): record approval wait cleanup
2026-08-17 20:23:10 -07:00
Peter Steinberger b485f0c627 refactor(agents): unify exec approval decisions (#125503)
* refactor(agents): unify exec approval decisions

* docs(plan): update runner deletion status
2026-08-17 19:06:28 -07:00
Peter Steinberger bb1ce58514 refactor(gateway): remove obsolete reverse worker tunnel (#125465)
* refactor(gateway): remove reverse worker tunnel

* test(gateway): align worker transport expectations

* docs(gateway): clarify cloud worker ingress
2026-08-17 18:19:52 -07:00
Peter Steinberger 45e6784338 feat(gateway): run disposable cloud workers through node transport (#125288)
* feat(gateway): converge cloud workers onto nodes

* fix(gateway): honor public URL for cloud enrollment

* fix(crabbox): execute cloud bootstrap package binary

* fix(gateway): bind cloud nodes in pairing transaction

* fix(crabbox): prefer exact installed cloud bootstrap

* fix(gateway): complete cloud node bootstrap

* fix(gateway): enforce cloud worker capability boundaries

* fix(gateway): complete cloud node migration

* fix(gateway): preserve paired node roles on teardown
2026-08-17 11:49:06 -07:00
Peter Steinberger 4d872fbfbc feat(nodes): expose installed worker bundle status (#124640)
* feat(nodes): expose installed worker bundle status

* perf(nodes): defer bundle status validation

* fix(nodes): tighten bundle status type contracts

* docs(gateway): document node worker bundle status

* refactor(gateway): split runner inventory runtime

* test(ui): keep healthy device status quiet

* fix(ui): preserve steer target ordering

* test(ui): isolate catalog handoff lifecycle
2026-08-16 10:04:46 -07:00
Peter Steinberger 18d130fc1b fix(workers): bound node bundle retention (#124590)
* fix(workers): bound node bundle retention

* docs(runners): track bundle retention
2026-08-16 06:25:05 -07:00
Peter Steinberger dbad5e385d refactor(workers): separate runner consent from capacity (#124356)
* refactor(workers): separate runner inventory state

* docs(runners): track inventory cleanup

* test(workers): use bundle-only launch wire

* test(workers): update optional inventory fixture

* test(workers): validate prewarm inventory capability

* fix(workers): version runner inventory cutover
2026-08-16 04:46:38 -07:00
Peter Steinberger 78502eda6d feat(workers): run device sessions from Gateway bundles (#124037)
* feat(workers): run device sessions from Gateway bundles

Install the current Gateway bundle before a device environment becomes ready, verify it at attach and tunnel boundaries, launch only from the immutable namespaced bundle directory, and retire stale environments for idempotent reprovisioning. Remove the local execution mode and preserve the node-local build claim only as temporary inventory metadata for the final projection/cleanup slice.

* docs(runners): record Gateway bundle cutover

* test(ci): repair runner validation fixtures

# Conflicts:
#	src/scripts/test-projects.test.ts

* fix(workers): surface outdated node recovery

Keep legacy runner inventory diagnostic-only while exposing the update-and-reconnect action through node, environment, provider, placement, and Control UI surfaces.

* fix(workers): reject legacy inventory with recovery

* fix(workers): bundle worker deploy closure

* test(workers): close bundle cutover gates

* fix(workers): compose browser runtime at build

* fix(workers): satisfy bundle cutover gates

* fix(workers): route temp runtime through infra

* docs(workers): align bundle host guidance

* fix(ui): fence outdated session destinations
2026-08-15 17:46:44 -07:00
Peter Steinberger 53074ae91a feat(workers): install Gateway bundles on nodes (#123985)
* feat(workers): install Gateway bundles on nodes

Add a private paired-channel install command backed by a one-use Gateway HTTP capability, bounded archive validation, script-disabled dependency materialization, and atomic gateway-namespaced publication. Existing device provisioning remains on the local-build path until the next cutover slice.

* docs(runners): record node bundle installer
2026-08-14 20:52:39 -07:00
Peter Steinberger 399f5a32e5 fix(workers): bound Gateway bundle cache growth (#123901)
* fix(workers): bound gateway bundle cache

* docs(plan): record Gateway bundle cache cleanup

* fix(workers): exclude terminal bundle diagnostics
2026-08-14 18:27:08 -07:00
Peter Steinberger d913796112 fix(runners): preserve node workspaces across restarts (#123889)
* fix(runners): retain node workspaces from gateway state

* docs(plan): record authoritative node retention
2026-08-14 16:59:19 -07:00
Peter Steinberger 3c5e2ff296 fix(gateway): retire worker placements without sessions (#123785)
* fix(gateway): retire placements without sessions

* fix(gateway): preserve unreadable placement evidence

* fix(gateway): drain placement retirement on shutdown

* test(sessions): auto-clean identity probe temp dirs

* fix(gateway): join placement sidecar shutdown
2026-08-14 14:07:24 -07:00
Peter Steinberger e44dde218f fix(gateway): revoke device workers when pairing is removed (#123696)
* fix(gateway): revoke device workers on unpair

* refactor(backup): split sqlite verification

* refactor(backup): narrow sqlite verifier exports

* test(gateway): track worker startup temp state

* refactor(backup): preserve sqlite architecture boundary

* test(gateway): follow worker startup logger binding

* fix(gateway): revoke workers during pairing pruning
2026-08-14 10:10:12 -07:00
Peter Steinberger d9211bf14d fix(runners): bound node workspace disk growth (#123700)
* fix(runners): prune superseded node workspaces

* docs(plan): record node retention progress

* fix(runners): drain workspace retention backlogs

* test(runners): await workspace retention cleanup
2026-08-14 08:27:59 -07:00
Peter Steinberger 7d8f066b81 feat(runners): expire dormant device leases (#123673) 2026-08-14 06:53:29 -07:00
Peter Steinberger 4ac9f4c5ec refactor(runners): prune terminal environments (#123665) 2026-08-14 06:27:49 -07:00
Peter Steinberger bbca520108 refactor(runners): prune terminal launch receipts (#123641)
* refactor(runners): prune terminal launch receipts

* perf(runners): index launch receipt expiry
2026-08-14 05:49:55 -07:00
Peter Steinberger 38379a9a2e feat(runners): enforce node worker capacity (#123612)
* feat(runners): enforce node worker capacity

* test(node-host): mock supervisor initialization

* fix(runners): surface capacity exhaustion
2026-08-14 04:49:47 -07:00
Peter Steinberger 7aac8ee04b fix: preserve device sessions while runner is offline (#123477)
* fix(runners): recover offline device placements

* test(runners): model reclaimed launch dispatch

* ci: serialize macOS Swift test retries

* test: wait for steering subscription readiness

* fix(gateway): restore authority-safe steering

* test(gateway): align authority projector fixture

* fix(gateway): dispatch leaf authority mismatches

* refactor: keep authority overlay contract leaf-only

* test(ui): close place popover before details
2026-08-14 03:31:19 -07:00
Peter Steinberger 860aeed8f6 feat(gateway): transfer node worker workspaces (#123280)
* feat(gateway): transfer node worker workspaces

* fix(gateway): harden node workspace transfer

* fix(gateway): isolate transfer HTTP contract

* fix(gateway): trim transfer HTTP exports
2026-08-13 21:00:44 -07:00
Peter Steinberger 438d035885 feat(gateway): launch workers on paired nodes (#123157)
* feat(gateway): launch workers on paired nodes

* docs(plan): track node worker launch wire

* fix(runners): restore node workspace ownership

Rehydrate durable workspace bindings after Gateway restart, fence timed-out node tunnel starts, and refuse incomplete clone fallback for submodule and Git LFS workspaces.

* test(runners): isolate node launch fixtures
2026-08-13 18:02:18 -07:00
Peter Steinberger 2dcd47d4f4 feat(runners): remember offline devices (#123198)
* feat(runners): remember offline devices

Persist exact node connection end timestamps and keep execution-capable offline devices visible with quiet lifecycle history in the session picker.

* test(ui): keep offline devices disabled
2026-08-13 13:49:00 -07:00
Peter Steinberger 6c9916a48a feat(runners): publish atomic device runner inventory (#123094)
* feat(runners): publish atomic node inventory

# Conflicts:
#	docs/.generated/plugin-sdk-api-baseline/agent-harness-runtime.json
#	src/gateway/server-methods/environments.ts
#	src/gateway/worker-environments/device-provider.test.ts

* fix(runners): refresh topology on inventory removal

* fix(runners): resolve session host type overlap

* fix(protocol): document mobile runner inventory event

* fix(runners): project authoritative session host state

* docs(nodes): clarify prepared session host status
2026-08-13 04:54:26 -07:00
Peter Steinberger 7a4b5a0a41 feat(gateway): provision paired node session hosts (#122966)
* feat(gateway): provision paired node worker installs

* docs: record node local-install PR chain

* chore(protocol): regenerate node worker manifest models

* fix(gateway): resolve node worker build through the device runtime

Repairs a rebase artifact: startup referenced a stale deviceNodeRegistry
binding; the device runtime now owns the connected-node lookup via
resolveWorkerBuild.
2026-08-13 01:56:19 -07:00
Peter Steinberger 5bdfa69e82 feat(worker): add durable node launch adapter (#123033)
* feat(worker): add durable node launch adapter

* docs(plan): track durable node launch adapter
2026-08-12 23:29:29 -07:00
Peter Steinberger 3f4d89505a feat(worker): expose supervised terminal outcomes (#123013)
* feat(worker): expose supervised terminal outcomes

* docs(plan): track supervisor terminal outcomes
2026-08-12 22:19:49 -07:00
Peter Steinberger 5e67beb02e feat(node-host): add negotiated private worker controls (#122939)
* feat(node-host): add private worker supervisor controls

* refactor(node-host): harden private worker controls

* refactor(node-host): simplify private worker controls

* docs(plan): track private worker controls

* fix(node-host): satisfy private control CI guards

* test(gateway): follow worker service construction boundary

* test(gateway): register private control release train

* fix(gateway): retain worker dialect across reapproval
2026-08-12 21:27:01 -07:00
Peter Steinberger cba8aff63f feat(ui): show useful environment facts in the picker (#122923)
* feat(ui): show environment facts in Where picker

Preserve environment platform, trust, session-host, and capability metadata through new-session discovery while keeping placement availability tied to live executable nodes. Render bounded quiet device/cloud facts and add mocked browser coverage for task #33.

* docs(plan): track picker environment facts

* refactor(ui): split place browser rendering
2026-08-12 19:32:34 -07:00
Peter Steinberger 08b134324f feat: continue web sessions in the terminal (#122870)
* feat: continue sessions in terminal

Add a credential-free Control UI continuation command and allow openclaw resume to reuse current-profile authentication only for byte-exact configured Gateway targets.

* fix(gateway): separate public origin TLS ownership

Allow exact public-origin resume targets to reuse local authentication without inheriting the direct local listener certificate fingerprint.

* fix(gateway): scope exact targets to gateway mode

Prevent remote profiles from reusing dormant local Gateway authentication for explicit loopback or public-origin targets.

* fix(cli): encode terminal resume handoffs

Replace shell-specific quoting with a strict credential-free base64url handoff, gate configured auth reuse to validated handoffs, and skip unused session discovery.

* fix(gateway): isolate handoff auth identity

Suppress ambient Gateway auth fallback for validated handoffs while preserving explicit credentials, configured SecretRefs, stored device auth, and exact-target TLS ownership.

* fix(cli): harden terminal resume handoffs

* fix(cli): parse terminal handoff outcomes

* fix(cli): bind handoffs to resolved agent

* test(ui): align terminal continuation proof

* docs(plan): track terminal continuation

* refactor(ui): keep terminal handoff result local
2026-08-12 17:07:48 -07:00
Peter Steinberger 7c7c7524ad feat: add paired-device worker provider foundation (#122769)
* feat(worker-provider): add core device lease foundation

* feat(gateway): dispatch sessions to paired devices

* test(gateway): cover node-ready lifecycle edge

* fix(gateway): defer device worker installation prep

* chore(plugin-sdk): refresh API baseline

* test(gateway): isolate worker turn state database

* docs(runners): refresh milestone table format

* test(gateway): track device dispatch temp state
2026-08-12 16:50:09 -07:00
Peter Steinberger 6b9bea84f0 feat(node-host): supervise durable worker launches (#122829)
* feat(node-host): add worker launch supervision

* fix(node-host): harden worker lifecycle ownership

* fix(node-host): harden worker execution boundary

* fix(node-host): preserve worker trust settings

* chore(plugin-sdk): refresh worker lifecycle baselines

* docs(plan): track runner implementation slices

* test(node-host): await runtime shutdown owner
2026-08-12 15:24:05 -07:00
Peter Steinberger 522f06ffc6 feat(worker): support direct Gateway connections (#122683)
* feat(worker): support direct gateway connections

* docs(plan): link node worker provider PR
2026-08-12 09:59:29 -07:00
Peter Steinberger 7179d21d97 feat(gateway): expose public worker ingress (#122643)
* feat(gateway): expose public worker ingress

* docs(plan): mark public worker ingress in progress

* fix(gateway): harden worker ingress provenance

* fix(gateway): preserve disabled worker ingress response
2026-08-12 09:41:45 -07:00
Peter Steinberger ad8f803311 feat(ui): connect machines from the Where picker (#122635)
* feat(ui): add connect machine dialog

* docs(plan): track connect machine picker

* fix(ui): harden connect-machine dialog lifecycle
2026-08-12 07:51:37 -07:00
Peter Steinberger 6e71e9b156 feat(gateway): expose public worker ingress (#122578)
* feat(gateway): expose public worker ingress

* docs(plan): link public worker ingress PR
2026-08-12 07:20:02 -07:00
Peter Steinberger ade3456dd4 feat: add one-paste node onboarding (#122499)
* feat(pairing): add short join onboarding

* fix(gateway): isolate device join routing tests
2026-08-12 06:17:39 -07:00
Peter Steinberger 40cb6f0e3b feat(ui): keep Where picker destinations live (#122531)
* feat(gateway): enrich environment summaries

* chore(sdk): refresh plugin API surface

surface drift approved: additive EnvironmentSummary enrichment (runners plan rev 2, milestone 4)

* feat(ui): keep where picker destinations live

* docs: link picker liveness milestone PR

* fix(ui): deduplicate picker locale keys

* test(ui): update picker section expectations

* fix(ssrf): narrow lookup resolver contract

* fix(gateway): publish authoritative environment facts
2026-08-12 05:11:46 -07:00
Peter Steinberger 0de17482ae feat(gateway,ui): quiet Where picker, placement chip, and projects read model (#120804)
* feat(gateway): projects.list groups known checkouts by repo identity

Implements docs/plan/runners.md milestone 4 derived projects read model.

* feat(ui): regroup the Where picker by gateway, devices, and cloud

* feat(ui): placement chip shows where a session runs with reclaim

Implements docs/plan/runners.md milestone 4 placement display and reclaim.
2026-08-12 00:21:23 -07:00
Peter Steinberger 127facd39f docs(plan): runners plan revision 2 — everything is a node (#122454)
* docs(plan): rewrite runners plan as revision 2 — everything is a node

Operator-decided direction change: paired nodes host full agent sessions
through the worker admission path; openclaw worker becomes a node-supervised
child; SSH is deleted as the device transport in favor of an outbound-only
two-connection shape (node control channel + direct-dial worker connection).
Folds in verified code reads (admission/tunnel/sync/node-channel/scopes), an
industry survey, an Amp CLI teardown, and a fresh adversarial review; scopes
milestone 6 honestly (transport/sync net-new, admission/placement reused) and
bounds v1 trust to admin-paired shared infrastructure.

* docs(plan): record revision-2 PR number in milestone table
2026-08-11 22:56:54 -07:00
Peter Steinberger 917fd92686 feat(cli): openclaw resume attaches the TUI to a recent session (#120664)
* feat(cli): openclaw resume attaches the TUI to a recent session

Implements docs/plan/runners.md milestone 2.

* fix(cli): resume covers global sessions and preflights TTY

* fix(cli): require a terminal before resume

* fix(cli): adapt resume gateway disconnect state

* fix(cli): preserve global resume ownership

* test(cli): prove qualified global resume crosses the gateway boundary
2026-08-09 02:52:06 -07:00
Peter Steinberger 5e66d9ee66 docs: runners plan — one placement model for sessions, devices, and cloud (#120657)
* docs: runners plan — one placement model for sessions, devices, and cloud

Proposal for unifying where sessions run: gateway/devices/cloud as runners
behind the existing worker admission stack; session-continuation ergonomics;
one-paste device pairing; derived projects read model; naming rulings
(session, devices); deletion ledger. Encodes the adversarial-review
kill-list as non-goals with code evidence.

* docs: unwrap PR refs so markdownlint MD018 passes
2026-08-08 11:29:08 -07:00