Skip to content

fix(sandbox): wait for managed supervisor on start - #8728

Merged
apurvvkumaria merged 2 commits into
mainfrom
codex/8726-managed-supervisor-startup
Aug 10, 2026
Merged

fix(sandbox): wait for managed supervisor on start#8728
apurvvkumaria merged 2 commits into
mainfrom
codex/8726-managed-supervisor-startup

Conversation

@apurvvkumaria

@apurvvkumaria apurvvkumaria commented Aug 10, 2026

Copy link
Copy Markdown
Collaborator

Summary

Ordinary stopped-sandbox startup now waits through only an exact transient missing-supervisor result, then repeats the complete startup recovery before readiness and forward verification. Definitive or unclassified failures remain terminal, and successful legacy supervisor relaunch recovery does not incur a settling delay.

Related Issue

Fixes #8726

Changes

  • Reuse the bounded authenticated managed-supervisor waiter after the first recovery returns exact SUPERVISOR_NOT_RUNNING.
  • Repeat full startup restoration after the supervisor appears so Shields, MCP, managed health, OpenShell readiness, and host forwards retain their existing checks.
  • Cover wait-to-success, persistent absence, second-pass failure, definitive and unclassified failures, and unchanged legacy relaunch behavior.

Type of Change

  • Code change (feature, bug fix, or refactor)
  • Code change with doc updates
  • Doc only (prose changes, no code sample modifications)
  • Doc only (includes code sample changes)

Quality Gates

  • Tests added or updated for changed behavior
  • Existing tests cover changed behavior — justification:
  • Tests not applicable — justification:
  • Docs updated for user-facing behavior changes
  • Docs not applicable — justification: Existing run, recovery, and command-reference pages already document full startup recovery, final readiness and forward checks, and fail-closed container preservation. This fix restores that contract for one transient race without changing commands, configuration, remediation, or stable output.
  • Sensitive paths changed (security, policy, credentials, preflight, onboarding, inference, runner, sandbox, or messaging)
  • Sensitive-path review completed or maintainer-approved waiver recorded — reviewer/approval link/justification: Security-rubric self-review confirmed that only the existing authenticated read-only waiter is reused, the retry gate requires the exact classified marker, the complete recovery boundary runs again, and definitive or unclassified results remain fail-closed.
  • Non-success, skipped, or missing CI check accepted by maintainer — check name, approval link, and follow-up issue:

Documentation Writer Review

  • Documentation writer subagent reviewed the completed changes
  • Result: no-docs-needed
  • Evidence: The change restores the already documented stopped-sandbox start recovery contract for one exact transient supervisor race. The final additional test only proves that a waiter exception preserves the existing fail-closed result; it does not change user-facing behavior or documentation ownership.
  • Agent: Codex Desktop

DGX Station Hardware Evidence

  • Tested on DGX Station
  • Tested commit:
  • Station profile/scenario:
  • Result:
  • Supporting evidence:

Verification

  • PR description includes a Signed-off-by: line and every commit appears as Verified in GitHub
  • Normal pre-commit, commit-msg, and pre-push hooks passed, or npm run validate:pr passed after refreshing origin/main when hooks were skipped or unavailable
  • Targeted behavior tests pass for the current change set, or tests are marked not applicable above — command/result or justification: npx vitest run --project cli src/lib/actions/sandbox/start.test.ts (28 passed) and npx vitest run --project integration test/process-recovery-supervisor-relaunch.test.ts (21 passed).
  • Applicable broad gate passed — npm test for broad runtime/test-harness changes; npm run check for repo-wide validation/coverage changes — command/result:
  • Quality Gates section completed with required justifications or waivers
  • No secrets, API keys, or credentials committed
  • npm run docs builds without warnings (doc changes only)
  • Doc pages follow the style guide (doc changes only)
  • New doc pages include SPDX header and frontmatter (new pages only)

Signed-off-by: Apurv Kumaria akumaria@nvidia.com

Summary by CodeRabbit

  • Bug Fixes
    • Improved sandbox startup recovery when the managed gateway supervisor is temporarily unavailable.
    • Startup now checks for supervisor readiness and retries recovery when the supervisor becomes available.
    • Preserved the original error when readiness checks fail or recovery cannot be completed.
    • Avoided unnecessary readiness checks for definitive or unrelated startup failures.

Signed-off-by: Apurv Kumaria <akumaria@nvidia.com>
@apurvvkumaria apurvvkumaria self-assigned this Aug 10, 2026
@coderabbitai

coderabbitai Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

Sandbox startup now waits for a missing managed supervisor before retrying recovery. The change exports the existing waiter, adds an optional startup dependency, preserves terminal failures, and adds targeted tests.

Changes

Managed supervisor startup recovery

Layer / File(s) Summary
Startup retry and waiter wiring
src/lib/actions/sandbox/start.ts, src/lib/actions/sandbox/connect.ts
Startup classifies the transient missing-supervisor failure, waits for readiness, and retries recovery when the wait succeeds. Probe failures preserve the initial error. The waiter is re-exported.
Startup retry behavior tests
src/lib/actions/sandbox/start.test.ts
Tests cover transient recovery, persistent absence, retry failure, excluded failures, call ordering, and unchanged legacy relaunch behavior.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Sequence Diagram(s)

sequenceDiagram
  participant SandboxStart
  participant waitForManagedGatewaySupervisor
  participant RecoveryAndGatewayVerification
  SandboxStart->>RecoveryAndGatewayVerification: initial recovery attempt
  SandboxStart->>waitForManagedGatewaySupervisor: wait after missing-supervisor failure
  waitForManagedGatewaySupervisor-->>SandboxStart: readiness result
  SandboxStart->>RecoveryAndGatewayVerification: retry recovery and verify gateway
Loading

Possibly related issues

Possibly related PRs

Suggested labels: area: sandbox, v0.0.106

Suggested reviewers: cv

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Linked Issues check ✅ Passed The changes implement the scoped retry, bounded supervisor wait, second recovery pass, fail-closed handling, and targeted tests required by [#8726].
Out of Scope Changes check ✅ Passed The changes are limited to the supervisor wait export, startup retry logic, and focused tests, with no unrelated refactoring or broad framework changes.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly and concisely describes the main change: waiting for the managed supervisor during sandbox startup.
✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/8726-managed-supervisor-startup

Comment @coderabbitai help to get the list of available commands.

@github-code-quality

github-code-quality Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

Code Coverage Overview

Languages: TypeScript

TypeScript / code-coverage/plugin

The overall coverage in commit a85a4a9 in the codex/8726-managed-s... branch remains at 96%, unchanged from commit dfef83e in the main branch.


Updated August 10, 2026 11:04 UTC

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
src/lib/actions/sandbox/start.test.ts (1)

201-215: 🎯 Functional Correctness | 🔵 Trivial | ⚡ Quick win

Cover a throwing managed-supervisor waiter.

Lines 150-158 in src/lib/actions/sandbox/start.ts preserve the first recovery failure when waitForManagedGatewaySupervisor throws. Add a test that makes the waiter throw. Assert that startup reports the first recovery failure, performs one recovery attempt, and does not call verifyGateway.

As per path instructions, review tests for behavioral confidence rather than implementation lock-in.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/lib/actions/sandbox/start.test.ts` around lines 201 - 215, Add a test
alongside the existing recovery-failure test that configures
waitForManagedGatewaySupervisor to throw after the initial recovery failure.
Assert startSandbox rejects with the first recovery failure, restoreStartupState
is called once, and verifyGateway is not called; avoid asserting internal
implementation details beyond this behavior.

Source: Path instructions

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Nitpick comments:
In `@src/lib/actions/sandbox/start.test.ts`:
- Around line 201-215: Add a test alongside the existing recovery-failure test
that configures waitForManagedGatewaySupervisor to throw after the initial
recovery failure. Assert startSandbox rejects with the first recovery failure,
restoreStartupState is called once, and verifyGateway is not called; avoid
asserting internal implementation details beyond this behavior.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: e26e2be3-6304-4217-8330-c3a803790f65

📥 Commits

Reviewing files that changed from the base of the PR and between 04e2644 and f1c925f.

📒 Files selected for processing (3)
  • src/lib/actions/sandbox/connect.ts
  • src/lib/actions/sandbox/start.test.ts
  • src/lib/actions/sandbox/start.ts

@github-actions

github-actions Bot commented Aug 10, 2026

Copy link
Copy Markdown
Contributor

PR Review Advisor — No blocking findings reported

Advisor assessment: No blocking advisor findings reported
Next action: No advisor follow-up needed.
Findings: 0 blockers · 0 warnings · 0 suggestions

Model lanes

  • GPT-5.6 Terra (primary): Completed · high confidence · 0 blockers · 0 warnings · 0 suggestions
  • Nemotron 3 Ultra (second opinion): Completed · high confidence · 0 blockers · 0 warnings · 0 suggestions
  • Model comparison: normalized findings match; normalized terminology decisions differ; normalized E2E selections differ; severity counts match.
3 terminology differences from the second opinion

Advisory only. These are normalized differences from the primary terminology receipt.

  • settling probe at src/lib/actions/sandbox/start.ts:157: primary classified it as justified; the second opinion classified it as define.
  • SUPERVISOR_NOT_RUNNING at src/lib/actions/sandbox/start.ts:67: selected only by the second-opinion lane as established.
  • transient at src/lib/actions/sandbox/start.test.ts:172: selected only by the second-opinion lane as established.
4 additional E2E selections from the second opinion

Advisory only. The primary lane did not select these E2E jobs or targets.

  • shields-config: The completed second-opinion lane identified E2E coverage that the primary lane omitted.
  • hermes-shields-config: The completed second-opinion lane identified E2E coverage that the primary lane omitted.
  • sandbox-operations: The completed second-opinion lane identified E2E coverage that the primary lane omitted.
  • sandbox-survival: The completed second-opinion lane identified E2E coverage that the primary lane omitted.

Second-opinion terminology and E2E selections are advisory. Live E2E does not run automatically for pull requests.

3 semantic terminology decisions

Terminology decisions are advisory. They affect the assessment only when a separate finding identifies concrete semantic impact.

  • established — managed supervisor at src/lib/actions/sandbox/start.test.ts:172: Keep the established term.
  • established — supervisor not running at src/lib/actions/sandbox/start.ts:67: Keep the established failure-layer term and exact marker contract.
  • justified — settling probe at src/lib/actions/sandbox/start.ts:157: Keep the modifier because it distinguishes the read-only probe from the subsequent recovery action.

E2E guidance

Advisory only. A maintainer can dispatch the default E2E suite against this exact revision.

Recommended E2E: onboard-repair, onboard-resume

Workflow run details

This automated review informs maintainers. Warnings and suggestions do not require a response. A maintainer decides whether to merge.

Signed-off-by: Apurv Kumaria <akumaria@nvidia.com>
@apurvvkumaria
apurvvkumaria merged commit c0d2efe into main Aug 10, 2026
83 of 88 checks passed
@apurvvkumaria
apurvvkumaria deleted the codex/8726-managed-supervisor-startup branch August 10, 2026 11:10
@github-actions github-actions Bot added the v0.0.106 Release target label Aug 10, 2026
apurvvkumaria added a commit that referenced this pull request Aug 10, 2026
<!-- markdownlint-disable MD041 -->
## Summary
Live onboarding now waits for the OpenShell create client to release
ownership before applying restart-safe Docker recreation. Previously the
active onboarding path bypassed the existing ownership barrier, so
recreation could race the still-running create process and leave fresh
sandboxes unready.

## Related Issue
Follow-up to #8720. This is complementary to the stopped-sandbox
recovery change in #8728.

## Changes
- Reuse `streamSandboxCreate`'s existing `waitForReadyTermination`
barrier in the active unmanaged, non-compatibility restart-safe path.
- Suppress the existing poll-time recreation in that path so the
existing `ensureApplied()` cutover runs only after create ownership is
released.
- Tighten the existing no-GPU Docker-route test to cover the barrier,
suppressed early patch, and deferred cutover without adding a new test
file.
- Leave stopped-sandbox recovery, timing thresholds, legacy upgrades,
and MCP coverage unchanged.

## Type of Change

- [x] Code change (feature, bug fix, or refactor)
- [ ] Code change with doc updates
- [ ] Doc only (prose changes, no code sample modifications)
- [ ] Doc only (includes code sample changes)

## Quality Gates
<!-- Check one tests line and one docs line. Check other lines when
applicable. Add every requested justification or approval reference. -->
- [x] Tests added or updated for changed behavior
- [ ] Existing tests cover changed behavior — justification:
- [ ] Tests not applicable — justification:
- [ ] Docs updated for user-facing behavior changes
- [x] Docs not applicable — justification: This restores the documented
onboarding-ready contract without changing commands, configuration,
remediation, or intended output.
- [x] Sensitive paths changed (security, policy, credentials, preflight,
onboarding, inference, runner, sandbox, or messaging)
- [x] Sensitive-path review completed or maintainer-approved waiver
recorded — reviewer/approval link/justification: The change only gates
the existing restart-safe recreation on release of create-process
ownership. Existing failure classification, managed lifecycle handling,
compatibility recreation, rollback, and readiness checks remain
unchanged.
- [ ] Non-success, skipped, or missing CI check accepted by maintainer —
check name, approval link, and follow-up issue:

## Documentation Writer Review
<!-- Required for code and documentation changes after the changes and
applicable validation are complete. Keep one review checkbox and one
instance of each visible or hidden field. For Evidence, list changed
documentation paths. For documentation-only changes, also state that the
writing rules and documentation style were reviewed. For other results,
explain why no documentation change is needed or why the review is
blocked. For Agent, use a consistent product and surface name, such as
Codex Desktop, Codex CLI, Claude Code, or Cursor. After committing all
review changes, put `git rev-parse --short HEAD` and `git rev-parse
--short HEAD:AGENTS.md` in the hidden metadata below. Rerun the review
and refresh that metadata after any new commit. This receipt is advisory
during the data-collection pilot. -->
- [x] Documentation writer subagent reviewed the completed changes
- Result: `no-docs-needed`
- Evidence: No documentation paths changed. Existing
`docs/reference/commands.mdx` and `docs/get-started/quickstart.mdx`
already own the unchanged create, ready, and dashboard contract.
- Agent: Codex Desktop
<!-- docs-review-head-sha: b13bb57 -->
<!-- docs-review-agents-blob-sha: c4923a3 -->

## DGX Station Hardware Evidence
<!-- Required only when scripts/prepare-dgx-station-host.sh changes.
Maintainers must review the linked evidence before approving or merging.
This is human-reviewed evidence, not authenticated hardware provenance.
Exceptional bypasses use existing repository governance and must be
documented on the PR. -->
- [ ] Tested on DGX Station
- Tested commit:
- Station profile/scenario:
- Result:
- Supporting evidence:

## Verification
<!-- Check each applicable item only when supported by the requested
evidence. Run targeted tests once per relevant change set and rerun
after later edits or hook autofixes that can affect the tested behavior.
Do not rerun hook-covered checks. -->
- [x] PR description includes a `Signed-off-by:` line and every commit
appears as `Verified` in GitHub
- [x] Normal `pre-commit`, `commit-msg`, and `pre-push` hooks passed, or
`npm run validate:pr` passed after refreshing `origin/main` when hooks
were skipped or unavailable
- [x] Targeted behavior tests pass for the current change set, or tests
are marked not applicable above — command/result or justification: `npx
vitest run --project cli src/lib/onboard/sandbox-gpu-create-flow.test.ts
src/lib/sandbox/create-stream.test.ts` (56 passed); `npm run
typecheck:cli` passed.
- [ ] Applicable broad gate passed — `npm test` for broad
runtime/test-harness changes; `npm run check` for repo-wide
validation/coverage changes — command/result: Not applicable; the change
is a focused two-file onboarding sequencing fix covered by targeted
tests and normal hooks.
- [x] Quality Gates section completed with required justifications or
waivers
- [x] No secrets, API keys, or credentials committed
- [ ] `npm run docs` builds without warnings (doc changes only)
- [ ] Doc pages follow the [style
guide](https://github.com/NVIDIA/NemoClaw/blob/main/docs/CONTRIBUTING.md)
(doc changes only)
- [ ] New doc pages include SPDX header and frontmatter (new pages only)

---
<!-- DCO sign-off is required in this PR description, and every commit
must appear as Verified in GitHub. Run: git config user.name && git
config user.email -->
Signed-off-by: Apurv Kumaria <akumaria@nvidia.com>

Signed-off-by: Apurv Kumaria <akumaria@nvidia.com>
@wscurran wscurran added bug-fix PR fixes a bug or regression area: sandbox OpenShell sandbox lifecycle, runtime, config, or recovery labels Aug 10, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area: sandbox OpenShell sandbox lifecycle, runtime, config, or recovery bug-fix PR fixes a bug or regression v0.0.106 Release target

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Wait for managed supervisor before failing stopped-sandbox startup

3 participants