Skip to content

test(e2e): keep proxy env backup in sandbox - #6156

Merged
apurvvkumaria merged 1 commit into
mainfrom
codex/use-local-proxy-env-backup
Jul 2, 2026
Merged

test(e2e): keep proxy env backup in sandbox#6156
apurvvkumaria merged 1 commit into
mainfrom
codex/use-local-proxy-env-backup

Conversation

@apurvvkumaria

@apurvvkumaria apurvvkumaria commented Jul 2, 2026

Copy link
Copy Markdown
Collaborator

Summary

Replace the issue-2478 E2E test's host-side Base64 snapshot transport with an atomic sandbox-local backup and restore. This removes the OpenShell single-argument size dependency while preserving the proxy environment's exact bytes, ownership, and mode across the process-only recovery scenario.

Related Issue

Refs #2478. Related to #6020 and #5595, which currently carry chunk-based workarounds for the same E2E failure.

Changes

  • Move /tmp/nemoclaw-proxy-env.sh to a hidden backup in the same sandbox before exercising the missing-file recovery path.
  • Atomically move the backup back to the canonical path before the restored-path restart and soak.
  • Remove Base64 encoding, captured proxy configuration output, host round-trips, chunking, and argument-size coupling.
  • Keep the backup in /tmp because this scenario restarts only the process tree; it does not recreate the sandbox or wipe /tmp.

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: the exact issue-2478-crash-loop-recovery live target exercises the backup, missing-file recovery, restore, five crash cycles, and five-minute stability soak.
  • Tests not applicable — justification:
  • Docs updated for user-facing behavior changes
  • Docs not applicable — justification: test-harness-only implementation; no command, default, runtime behavior, public API, target ID, or documented E2E interface changed.
  • 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: human review pending; no waiver requested.
  • Non-success, skipped, or missing CI check accepted by maintainer — check name, approval link, and follow-up issue: the broad local test-cli hook was not used as evidence after an unrelated host-toolchain failure; required CI remains authoritative.

Verification

  • PR description includes the DCO sign-off declaration and every commit appears as Verified in GitHub
  • Git hooks passed during commit and push, or npx prek run --from-ref main --to-ref HEAD passes
  • Targeted tests pass for changed behavior
  • Full npm test passes (broad runtime changes only)
  • 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)

Test Evidence

  • Full focused live E2E: 1/1 passed in 709.49s with 5 crash cycles, atomic backup/restore, 20 stable PID samples, 5 successful inference probes, and 0 inference failures.
  • Focused smoke: 1/1 passed in 270.21s with 1 crash cycle and a 15-second soak.
  • npm run typecheck:cli
  • npm run checks
  • npm run source-shape:check
  • npm run test-size:check
  • npx @biomejs/biome check test/e2e/live/issue-2478-crash-loop-recovery.test.ts
  • Pre-push CLI TypeScript and package-version checks passed.

Signed-off-by: Apurv Kumaria 36614+apurvvkumaria@users.noreply.github.com

Summary by CodeRabbit

  • Tests
    • Improved end-to-end crash-loop recovery coverage by making the proxy environment file backup and restore flow more reliable.
    • The test now uses a simpler file move approach to preserve state across recovery steps, reducing flakiness during recovery scenarios.

Signed-off-by: Apurv Kumaria <36614+apurvvkumaria@users.noreply.github.com>
@coderabbitai

coderabbitai Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

This PR modifies an e2e test to preserve /tmp/nemoclaw-proxy-env.sh across crash-loop recovery test phases using mv-based rename backup/restore helpers, replacing the previous base64 snapshot, delete, and rehydration approach.

Changes

Proxy-env backup/restore refactor

Layer / File(s) Summary
Backup/restore helpers and constants
test/e2e/live/issue-2478-crash-loop-recovery.test.ts
Adds path constants for the proxy-env file and its backup location, and introduces moveProxyEnvToBackup(...) and restoreProxyEnvFromBackup(...) helpers that use mv -f with exit-code assertions, replacing the prior snapshot/remove/restore logic.
Test flow wiring
test/e2e/live/issue-2478-crash-loop-recovery.test.ts
Updates the test sequence to call the new backup helper before the missing proxy-env scenario and the new restore helper before the restored proxy-env scenario.

Estimated code review effort: 2 (Simple) | ~10 minutes

Possibly related PRs

  • NVIDIA/NemoClaw#4959: Both PRs relate to gateway recovery handling of /tmp/nemoclaw-proxy-env.sh during crash-loop recovery.

Suggested labels: area: sandbox, bug-fix

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
Title check ✅ Passed The title is concise and accurately reflects the main change: keeping the proxy env backup inside the sandbox.
✨ 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/use-local-proxy-env-backup

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

@github-code-quality

github-code-quality Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

Code Coverage Overview

Languages: TypeScript

TypeScript / code-coverage/plugin

The overall coverage in the codex/use-local-prox... branch is 96%. Coverage data for the main branch is not yet available.

Show a code coverage summary of the most covered files.
File main codex/use-local-prox... 5fce4a4 +/-
nemoclaw/src/se...cret-scanner.ts 100%
nemoclaw/src/commands/slash.ts 100%
nemoclaw/src/li...bprocess-env.ts 100%
nemoclaw/src/bl...eprint/state.ts 98%
nemoclaw/src/onboard/config.ts 98%
nemoclaw/src/bl...int/snapshot.ts 97%
nemoclaw/src/bl...print/runner.ts 95%
nemoclaw/src/co...ration-state.ts 94%
nemoclaw/src/bl...ate-networks.ts 94%
nemoclaw/src/index.ts 94%

TypeScript / code-coverage/cli

The overall coverage in the codex/use-local-prox... branch is 69%. Coverage data for the main branch is not yet available.

Show a code coverage summary of the most covered files.
File main codex/use-local-prox... 5fce4a4 +/-
src/lib/actions...dbox/rebuild.ts 82%
src/lib/actions...all/run-plan.ts 80%
src/lib/state/o...oard-session.ts 79%
src/lib/shields/index.ts 75%
src/lib/state/sandbox.ts 73%
src/lib/onboard/preflight.ts 69%
src/lib/onboard...er-gpu-patch.ts 59%
src/lib/actions...licy-channel.ts 58%
src/lib/policy/index.ts 56%
src/lib/onboard.ts 20%

Updated July 02, 2026 01:09 UTC
Code Coverage is in Public Preview. Learn more and provide us with your feedback.

@github-actions

github-actions Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

E2E Advisor Recommendation

Required E2E: None
Optional E2E: issue-2478-crash-loop-recovery

Dispatch hint: issue-2478-crash-loop-recovery

Workflow run

Full advisor summary

E2E Recommendation Advisor

Base: origin/main
Head: HEAD
Confidence: high

Required E2E

  • None. No merge-blocking E2E is required because this is a tests-only change to an existing live E2E test and cannot affect runtime user flows or production security/sandbox behavior.

Optional E2E

  • issue-2478-crash-loop-recovery (timeout-minutes: 30): Optional self-validation of the modified live E2E scenario for gateway recovery, proxy-env backup/restore behavior, guard-chain preservation, and inference.local soak checks.

New E2E recommendations

  • None.

Dispatch hint

  • Workflow: .github/workflows/e2e.yaml
  • jobs input: issue-2478-crash-loop-recovery

@github-actions

github-actions Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

E2E Target Recommendation

Required E2E targets: issue-2478-crash-loop-recovery
Optional E2E targets: None

Dispatch required E2E targets:

  • gh workflow run e2e.yaml --ref <pr-head-ref> --field jobs=issue-2478-crash-loop-recovery

Workflow run

Full E2E target advisor summary

E2E Target Advisor

Base: origin/main
Head: HEAD
Confidence: high

Required E2E targets

  • issue-2478-crash-loop-recovery: Focused free-standing E2E job wired for changed live test test/e2e/live/issue-2478-crash-loop-recovery.test.ts.
    • Dispatch: gh workflow run e2e.yaml --ref <pr-head-ref> --field jobs=issue-2478-crash-loop-recovery

Optional E2E targets

  • None.

Relevant changed files

  • test/e2e/live/issue-2478-crash-loop-recovery.test.ts

@apurvvkumaria apurvvkumaria changed the title [codex] test(e2e): keep proxy env backup in sandbox test(e2e): keep proxy env backup in sandbox Jul 2, 2026
@github-actions

github-actions Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

PR Review Advisor (Nemotron Ultra) — No blocking findings

Merge posture: No blocking advisor findings
Primary next action: Consider PRA-1: Simplified proxy env backup/restore from base64 to atomic mv.
Open items: 0 required · 0 warnings · 2 suggestions · 0 test follow-ups
Since last review: 0 prior items resolved · 0 still apply · 1 new item found

Action checklist

  • PRA-1 In-scope improvement: Simplified proxy env backup/restore from base64 to atomic mv in test/e2e/live/issue-2478-crash-loop-recovery.test.ts:295
  • PRA-2 In-scope improvement: Restored proxy env content verification now implicit via expectGuardChainActive in test/e2e/live/issue-2478-crash-loop-recovery.test.ts:486

Findings index

ID Severity Category Location Required action
PRA-1 Improvement correctness test/e2e/live/issue-2478-crash-loop-recovery.test.ts:295 Accept the simplification. The mv approach is simpler (shrink), uses stdlib shell commands, preserves file metadata, and maintains test coverage of the critical recovery path. No action needed.
PRA-2 Improvement correctness test/e2e/live/issue-2478-crash-loop-recovery.test.ts:486 No change required — expectGuardChainActive is stronger than byte-size check. If desired for defense-in-depth, add lightweight check that restored file contains expected guard require entries, but not required for merge.
Review findings by urgency: 0 required fixes, 0 items to resolve/justify, 2 in-scope improvements

⚠️ Resolve or justify before merge

Investigate these in the current review; either fix them, explain why they are not applicable, or document the accepted risk.

  • None.

💡 In-scope improvements

These are lower-risk, not throwaway. Prefer fixing them in this PR when they are local to changed code; defer only with rationale or a linked follow-up.

PRA-1 Improvement — Simplified proxy env backup/restore from base64 to atomic mv

  • Location: test/e2e/live/issue-2478-crash-loop-recovery.test.ts:295
  • Category: correctness
  • Problem: Replaced 4 helper functions (snapshotProxyEnv, removeProxyEnv, proxyEnvHasGuardMarkers, restoreProxyEnv) using base64 encoding/decoding with size verification, with 2 functions (moveProxyEnvToBackup, restoreProxyEnvFromBackup) using shell builtin `mv -f`. Both approaches correctly make /tmp/nemoclaw-proxy-env.sh missing during the 'missing proxy-env warning path' test phase, triggering the recovery warning 'restoring library guards from packaged preloads'. Functional assertions (expectGuardChainActive, waitForRecoveryWarning, soak stability) unchanged.
  • Impact: Reduces ~60 lines of test infrastructure code, eliminates base64 encoding/decoding pipeline, preserves file metadata (mode 444, root ownership) automatically, improves readability. No behavioral change to the test scenario.
  • Suggested action: Accept the simplification. The mv approach is simpler (shrink), uses stdlib shell commands, preserves file metadata, and maintains test coverage of the critical recovery path. No action needed.
  • Expected follow-up: Prefer a current-PR fix when local to changed code; defer only with rationale or linked follow-up.
  • Verification: Run the test locally or in CI: the 'missing-proxy-env-connect-probe-only' phase should still emit the warning 'restoring library guards from packaged preloads' and expectGuardChainActive should pass after both recovery cycles.
  • Missing regression test: No new test needed — existing test already covers the missing proxy env warning path and guard chain restoration. The simplification is infrastructure-only.
  • Done when: The local improvement is applied, or the PR notes why it should be deferred.
  • Evidence: Diff shows 4 helpers → 2 helpers, base64/wc-c/chmod/chown pipeline replaced with mv -f. Test evidence: 'Full focused live E2E: 1/1 passed in 709.49s with 5 crash cycles, atomic backup/restore, 20 stable PID samples, 5 successful inference probes, and 0 inference failures.'

PRA-2 Improvement — Restored proxy env content verification now implicit via expectGuardChainActive

  • Location: test/e2e/live/issue-2478-crash-loop-recovery.test.ts:486
  • Category: correctness
  • Problem: Old restoreProxyEnv explicitly verified restored file size matched snapshot OR guard markers present. New restoreProxyEnvFromBackup relies solely on expectGuardChainActive after the second recovery cycle, which validates the NODE_OPTIONS chain is wired — a stronger contract than byte-size verification.
  • Impact: Slightly less explicit test-time verification of proxy env file content, but higher-level contract (guard chain active) is more meaningful. No functional gap.
  • Suggested action: No change required — expectGuardChainActive is stronger than byte-size check. If desired for defense-in-depth, add lightweight check that restored file contains expected guard require entries, but not required for merge.
  • Expected follow-up: Prefer a current-PR fix when local to changed code; defer only with rationale or linked follow-up.
  • Verification: Verify test passes: after restoreProxyEnvFromBackup, the second killOpenclawTreeForRecovery + runProbeOnly + expectGuardChainActive sequence should succeed.
  • Missing regression test: Already covered by expectGuardChainActive in the test body (line ~496).
  • Done when: The local improvement is applied, or the PR notes why it should be deferred.
  • Evidence: Old code: restoredSize check + proxyEnvHasGuardMarkers fallback. New code: only expectGuardChainActive call after restore.
Simplification opportunities: 2 possible cuts, net -55 lines possible

These are safe simplification checks only. Do not remove validation, security controls, data-loss prevention, or required tests.

  • PRA-1 shrink (test/e2e/live/issue-2478-crash-loop-recovery.test.ts:295): snapshotProxyEnv, removeProxyEnv, proxyEnvHasGuardMarkers, restoreProxyEnv (4 functions, ~60 lines using base64 + printf + wc-c + chmod + chown)
    • Replacement: moveProxyEnvToBackup, restoreProxyEnvFromBackup (2 functions, ~20 lines using mv -f)
    • Net: -40 lines
    • Safety boundary: expectGuardChainActive and waitForRecoveryWarning assertions must continue to pass — they validate the actual NODE_OPTIONS guard chain contract
  • PRA-2 shrink (test/e2e/live/issue-2478-crash-loop-recovery.test.ts:486): Explicit proxy env file size/marker verification in restoreProxyEnv
    • Replacement: Implicit verification via expectGuardChainActive
    • Net: -15 lines
    • Safety boundary: expectGuardChainActive must continue to assert the NODE_OPTIONS --require chain is present
Since last review details

Current findings, using the urgency labels above:

PRA-1 Improvement — Simplified proxy env backup/restore from base64 to atomic mv

  • Location: test/e2e/live/issue-2478-crash-loop-recovery.test.ts:295
  • Category: correctness
  • Problem: Replaced 4 helper functions (snapshotProxyEnv, removeProxyEnv, proxyEnvHasGuardMarkers, restoreProxyEnv) using base64 encoding/decoding with size verification, with 2 functions (moveProxyEnvToBackup, restoreProxyEnvFromBackup) using shell builtin `mv -f`. Both approaches correctly make /tmp/nemoclaw-proxy-env.sh missing during the 'missing proxy-env warning path' test phase, triggering the recovery warning 'restoring library guards from packaged preloads'. Functional assertions (expectGuardChainActive, waitForRecoveryWarning, soak stability) unchanged.
  • Impact: Reduces ~60 lines of test infrastructure code, eliminates base64 encoding/decoding pipeline, preserves file metadata (mode 444, root ownership) automatically, improves readability. No behavioral change to the test scenario.
  • Suggested action: Accept the simplification. The mv approach is simpler (shrink), uses stdlib shell commands, preserves file metadata, and maintains test coverage of the critical recovery path. No action needed.
  • Expected follow-up: Prefer a current-PR fix when local to changed code; defer only with rationale or linked follow-up.
  • Verification: Run the test locally or in CI: the 'missing-proxy-env-connect-probe-only' phase should still emit the warning 'restoring library guards from packaged preloads' and expectGuardChainActive should pass after both recovery cycles.
  • Missing regression test: No new test needed — existing test already covers the missing proxy env warning path and guard chain restoration. The simplification is infrastructure-only.
  • Done when: The local improvement is applied, or the PR notes why it should be deferred.
  • Evidence: Diff shows 4 helpers → 2 helpers, base64/wc-c/chmod/chown pipeline replaced with mv -f. Test evidence: 'Full focused live E2E: 1/1 passed in 709.49s with 5 crash cycles, atomic backup/restore, 20 stable PID samples, 5 successful inference probes, and 0 inference failures.'

PRA-2 Improvement — Restored proxy env content verification now implicit via expectGuardChainActive

  • Location: test/e2e/live/issue-2478-crash-loop-recovery.test.ts:486
  • Category: correctness
  • Problem: Old restoreProxyEnv explicitly verified restored file size matched snapshot OR guard markers present. New restoreProxyEnvFromBackup relies solely on expectGuardChainActive after the second recovery cycle, which validates the NODE_OPTIONS chain is wired — a stronger contract than byte-size verification.
  • Impact: Slightly less explicit test-time verification of proxy env file content, but higher-level contract (guard chain active) is more meaningful. No functional gap.
  • Suggested action: No change required — expectGuardChainActive is stronger than byte-size check. If desired for defense-in-depth, add lightweight check that restored file contains expected guard require entries, but not required for merge.
  • Expected follow-up: Prefer a current-PR fix when local to changed code; defer only with rationale or linked follow-up.
  • Verification: Verify test passes: after restoreProxyEnvFromBackup, the second killOpenclawTreeForRecovery + runProbeOnly + expectGuardChainActive sequence should succeed.
  • Missing regression test: Already covered by expectGuardChainActive in the test body (line ~496).
  • Done when: The local improvement is applied, or the PR notes why it should be deferred.
  • Evidence: Old code: restoredSize check + proxyEnvHasGuardMarkers fallback. New code: only expectGuardChainActive call after restore.

Workflow run details

This is an automated, non-binding review; it still expects maintainers and agents to respond to each required or warning item. Treat suggestions as current-PR improvements when they touch changed code; defer only with maintainer rationale or a linked follow-up. A human maintainer must make the final merge decision.

@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.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
test/e2e/live/issue-2478-crash-loop-recovery.test.ts (1)

295-331: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

No guaranteed restore if an assertion between backup and restore throws.

moveProxyEnvToBackup (called at Line 474) and restoreProxyEnvFromBackup (called at Line 486) are separated by the "missing proxy-env" scenario assertions. If any assertion in between throws, the restore never runs and /tmp/nemoclaw-proxy-env.sh remains permanently backed up/missing for the rest of the sandbox lifetime, potentially cascading into failures in the restored-scenario and soak phases (or subsequent test runs reusing the sandbox).

Consider wrapping the missing-proxy-env scenario in try/finally (or registering an afterAll/afterEach cleanup) that calls restoreProxyEnvFromBackup unconditionally.

🔧 Example guard
-  await moveProxyEnvToBackup(sandbox, instance.sandboxName);
-  // ... missing-proxy-env assertions ...
-  await restoreProxyEnvFromBackup(sandbox, instance.sandboxName);
+  await moveProxyEnvToBackup(sandbox, instance.sandboxName);
+  try {
+    // ... missing-proxy-env assertions ...
+  } finally {
+    await restoreProxyEnvFromBackup(sandbox, instance.sandboxName);
+  }
🤖 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 `@test/e2e/live/issue-2478-crash-loop-recovery.test.ts` around lines 295 - 331,
The missing-proxy-env scenario can leave PROXY_ENV_PATH backed up if an
assertion fails before restore runs. Update the test around moveProxyEnvToBackup
and restoreProxyEnvFromBackup to use a try/finally (or equivalent cleanup hook)
so restoreProxyEnvFromBackup is always called after the temporary rename, even
when the assertions in the middle throw. Keep the fix localized to the
crash-loop recovery test flow that currently calls these helpers.
🧹 Nitpick comments (1)
test/e2e/live/issue-2478-crash-loop-recovery.test.ts (1)

295-322: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Duplicate inline sandbox parameter type.

moveProxyEnvToBackup and restoreProxyEnvFromBackup both declare the identical inline type for the sandbox parameter. Extract a shared type (e.g., SandboxExecClient) to avoid drift if the exec signature changes.

♻️ Suggested extraction
+type SandboxExecClient = {
+  exec(
+    name: string,
+    command: string[],
+    options?: Record<string, unknown>,
+  ): Promise<{ exitCode: number | null; stdout: string; stderr: string }>;
+};
+
-async function moveProxyEnvToBackup(
-  sandbox: {
-    exec(
-      name: string,
-      command: string[],
-      options?: Record<string, unknown>,
-    ): Promise<{ exitCode: number | null; stdout: string; stderr: string }>;
-  },
-  sandboxName: string,
-): Promise<void> {
+async function moveProxyEnvToBackup(
+  sandbox: SandboxExecClient,
+  sandboxName: string,
+): Promise<void> {

Apply the same substitution to restoreProxyEnvFromBackup.

🤖 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 `@test/e2e/live/issue-2478-crash-loop-recovery.test.ts` around lines 295 - 322,
The `sandbox` parameter type is duplicated in both `moveProxyEnvToBackup` and
`restoreProxyEnvFromBackup`, so extract the shared exec-capable type into a
reusable alias (for example, `SandboxExecClient`) and use it in both helper
signatures. Update the type definition near these helpers so the `exec` contract
is declared once, then replace both inline object types with the shared alias to
keep the two functions in sync if the signature changes.
🤖 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.

Outside diff comments:
In `@test/e2e/live/issue-2478-crash-loop-recovery.test.ts`:
- Around line 295-331: The missing-proxy-env scenario can leave PROXY_ENV_PATH
backed up if an assertion fails before restore runs. Update the test around
moveProxyEnvToBackup and restoreProxyEnvFromBackup to use a try/finally (or
equivalent cleanup hook) so restoreProxyEnvFromBackup is always called after the
temporary rename, even when the assertions in the middle throw. Keep the fix
localized to the crash-loop recovery test flow that currently calls these
helpers.

---

Nitpick comments:
In `@test/e2e/live/issue-2478-crash-loop-recovery.test.ts`:
- Around line 295-322: The `sandbox` parameter type is duplicated in both
`moveProxyEnvToBackup` and `restoreProxyEnvFromBackup`, so extract the shared
exec-capable type into a reusable alias (for example, `SandboxExecClient`) and
use it in both helper signatures. Update the type definition near these helpers
so the `exec` contract is declared once, then replace both inline object types
with the shared alias to keep the two functions in sync if the signature
changes.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 20187379-ab06-4e8e-8dae-805a2df4f1cb

📥 Commits

Reviewing files that changed from the base of the PR and between 0d9fc20 and 5fce4a4.

📒 Files selected for processing (1)
  • test/e2e/live/issue-2478-crash-loop-recovery.test.ts

@github-actions

github-actions Bot commented Jul 2, 2026

Copy link
Copy Markdown
Contributor

PR Review Advisor — No blocking findings

Merge posture: No blocking advisor findings
Primary next action: Add or justify PRA-T1 and any related test follow-ups.
Open items: 0 required · 0 warnings · 0 suggestions · 5 test follow-ups
Top item: No actionable code findings

Action checklist

  • PRA-T1 Add or justify test follow-up: Acceptance clause
  • PRA-T2 Add or justify test follow-up: Acceptance clause
  • PRA-T3 Add or justify test follow-up: Acceptance clause
  • PRA-T4 Add or justify test follow-up: Acceptance clause
  • PRA-T5 Add or justify test follow-up: Acceptance clause
Test follow-ups to resolve or justify

If these cover changed behavior, prefer adding them in this PR; otherwise state why existing coverage is enough or link the follow-up.

  • PRA-T1 Acceptance clause — `@homebridge/ciao` (the mDNS/Bonjour library OpenClaw bundles for local network discovery) calls `os.networkInterfaces()` during init. Inside the OpenShell sandbox the underlying syscall fails with EPERM, because seccomp is blocking the netlink socket family. — add test evidence or identify existing coverage. This test does not directly force the EPERM syscall path, but it preserves the guard-chain/preload regression checks that protect the gateway startup path affected by ciao.
  • PRA-T2 Acceptance clause — 1. Wrap the ciao NetworkManager calls in try/catch inside OpenClaw, fall back to no mDNS if `os.networkInterfaces()` throws. Probably the smallest diff. — add test evidence or identify existing coverage. This PR only changes the live E2E harness backup/restore mechanism; it does not modify OpenClaw production ciao handling.
  • PRA-T3 Acceptance clause — 2. Add an `OPENCLAW_DISABLE_MDNS=1` env var (or a config flag) that skips loading ciao entirely. Most explicit user-facing fix. — add test evidence or identify existing coverage. No production configuration surface changes are included in this single test-file PR.
  • PRA-T4 Acceptance clause — 3. Loosen the OpenShell sandbox seccomp profile to allow the netlink syscall family. Probably not what you want for an isolation-focused product, but listing it for completeness. — add test evidence or identify existing coverage. No sandbox seccomp or network policy files are changed; this security-sensitive alternative is outside the test-only diff.
  • PRA-T5 Acceptance clause — 4. As a stopgap until any of the above lands, expose `gateway.preload` or `gateway.env.*` in the NemoClaw config schema. That way users can persist the workaround through `nemoclaw config set` instead of running a script by hand. — add test evidence or identify existing coverage. No config schema changes are included; the changed E2E test continues verifying that the existing recovery/preload mechanism persists across gateway recovery.

Workflow run details

This is an automated, non-binding review; it still expects maintainers and agents to respond to each required or warning item. Treat suggestions as current-PR improvements when they touch changed code; defer only with maintainer rationale or a linked follow-up. A human maintainer must make the final merge decision.

@cjagwani cjagwani left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

LGTM

@apurvvkumaria
apurvvkumaria merged commit ba687cf into main Jul 2, 2026
49 of 51 checks passed
@apurvvkumaria
apurvvkumaria deleted the codex/use-local-proxy-env-backup branch July 2, 2026 01:12
Hadar301 pushed a commit to Hadar301/NemoClaw-OpenShift that referenced this pull request Jul 12, 2026
<!-- markdownlint-disable MD041 -->
## Summary

Replace the issue-2478 E2E test's host-side Base64 snapshot transport
with an atomic sandbox-local backup and restore. This removes the
OpenShell single-argument size dependency while preserving the proxy
environment's exact bytes, ownership, and mode across the process-only
recovery scenario.

## Related Issue

Refs NVIDIA#2478. Related to NVIDIA#6020 and NVIDIA#5595, which currently carry
chunk-based workarounds for the same E2E failure.

## Changes

- Move `/tmp/nemoclaw-proxy-env.sh` to a hidden backup in the same
sandbox before exercising the missing-file recovery path.
- Atomically move the backup back to the canonical path before the
restored-path restart and soak.
- Remove Base64 encoding, captured proxy configuration output, host
round-trips, chunking, and argument-size coupling.
- Keep the backup in `/tmp` because this scenario restarts only the
process tree; it does not recreate the sandbox or wipe `/tmp`.

## 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

- [x] Tests added or updated for changed behavior
- [x] Existing tests cover changed behavior — justification: the exact
`issue-2478-crash-loop-recovery` live target exercises the backup,
missing-file recovery, restore, five crash cycles, and five-minute
stability soak.
- [ ] Tests not applicable — justification:
- [ ] Docs updated for user-facing behavior changes
- [x] Docs not applicable — justification: test-harness-only
implementation; no command, default, runtime behavior, public API,
target ID, or documented E2E interface changed.
- [x] 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: human review pending;
no waiver requested.
- [ ] Non-success, skipped, or missing CI check accepted by maintainer —
check name, approval link, and follow-up issue: the broad local
`test-cli` hook was not used as evidence after an unrelated
host-toolchain failure; required CI remains authoritative.

## Verification

- [x] PR description includes the DCO sign-off declaration and every
commit appears as `Verified` in GitHub
- [ ] Git hooks passed during commit and push, or `npx prek run
--from-ref main --to-ref HEAD` passes
- [x] Targeted tests pass for changed behavior
- [ ] Full `npm test` passes (broad runtime changes only)
- [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)

### Test Evidence

- Full focused live E2E: 1/1 passed in 709.49s with 5 crash cycles,
atomic backup/restore, 20 stable PID samples, 5 successful inference
probes, and 0 inference failures.
- Focused smoke: 1/1 passed in 270.21s with 1 crash cycle and a
15-second soak.
- `npm run typecheck:cli`
- `npm run checks`
- `npm run source-shape:check`
- `npm run test-size:check`
- `npx @biomejs/biome check
test/e2e/live/issue-2478-crash-loop-recovery.test.ts`
- Pre-push CLI TypeScript and package-version checks passed.

---
Signed-off-by: Apurv Kumaria
<36614+apurvvkumaria@users.noreply.github.com>


<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->

## Summary by CodeRabbit

* **Tests**
* Improved end-to-end crash-loop recovery coverage by making the proxy
environment file backup and restore flow more reliable.
* The test now uses a simpler file move approach to preserve state
across recovery steps, reducing flakiness during recovery scenarios.

<!-- end of auto-generated comment: release notes by coderabbit.ai -->

Signed-off-by: Apurv Kumaria <36614+apurvvkumaria@users.noreply.github.com>
Co-authored-by: Apurv Kumaria <36614+apurvvkumaria@users.noreply.github.com>
@wscurran wscurran added area: e2e End-to-end tests, nightly failures, or validation infrastructure area: sandbox OpenShell sandbox lifecycle, runtime, config, or recovery labels Aug 1, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area: e2e End-to-end tests, nightly failures, or validation infrastructure area: sandbox OpenShell sandbox lifecycle, runtime, config, or recovery

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants