Skip to content

fix(openclaw): prefer OpenShell loopback proxy#4005

Open
ericksoa wants to merge 4 commits into
mainfrom
fix/prefer-openshell-loopback-proxy
Open

fix(openclaw): prefer OpenShell loopback proxy#4005
ericksoa wants to merge 4 commits into
mainfrom
fix/prefer-openshell-loopback-proxy

Conversation

@ericksoa
Copy link
Copy Markdown
Contributor

@ericksoa ericksoa commented May 21, 2026

Summary

  • Prefer OPENSHELL_LOOPBACK_PROXY_URL for OpenClaw Discord config when OpenShell provides a valid loopback HTTP proxy URL.
  • Skip NemoClaw's temporary Discord loopback helper only when the OpenShell URL is loopback, the baked OpenClaw Discord config points at that exact URL, and the listener is reachable.
  • Default the temporary Discord helper port to NEMOCLAW_PROXY_PORT unless NEMOCLAW_DISCORD_PROXY_PORT is explicitly set, so fallback config and helper startup stay aligned.
  • Keep the existing NemoClaw helper as a compatibility fallback for older OpenShell releases/pins.

Dependency

Methodology

  • Re-read the OpenClaw config generation and NemoClaw startup fallback paths from the live PR branch.
  • Validated the expected contract with OpenShell fix(onboard): bake messaging channels into openclaw.json at build time #1501: OpenShell supplies OPENSHELL_LOOPBACK_PROXY_URL, and NemoClaw uses that value only when it is a valid loopback HTTP URL.
  • Ran an adversarial review across both PRs. That review found a fallback outage risk if NemoClaw skipped its helper based only on the env var while the baked Discord config still pointed elsewhere.
  • Ran a combined-validation pass using both PR branches under Colima, not Docker Desktop.

Findings Incorporated

  • NemoClaw now keeps config and fallback startup aligned: Discord proxy config defaults to NEMOCLAW_PROXY_PORT, and the helper uses the same default unless NEMOCLAW_DISCORD_PROXY_PORT is explicitly set.
  • NemoClaw only skips its helper when the OpenShell URL is valid loopback, the baked OpenClaw Discord config points at exactly that URL, and a TCP reachability probe succeeds.
  • The existing helper remains as a compatibility fallback for older OpenShell pins or mismatched/unhealthy managed listeners.
  • The no-secret invariant is preserved: Discord config still uses the placeholder token, not the real Discord token.

Combined Validation

  • Environment: Colima Docker runtime/socket, isolated temp HOME/XDG/npm state, gateway port 18080, dashboard port 18889, unique Docker network, and unique OpenShell Docker sandbox namespace.
  • OpenShell under test: fix(sandbox): add managed loopback proxy OpenShell#1501 head 083c0663187a3e93e60cd4d32b30053475cb0890, openshell 0.0.47-dev.3+gb75abad.
  • NemoClaw under test: this PR head dd022b578806aa3880b33ac2c3fe6a86f230ff33.
  • Docker supervisor under test: Linux arm64 openshell-sandbox built from the OpenShell PR and mounted through [openshell.drivers.docker].supervisor_bin.
  • Version-gate note: the run set NEMOCLAW_OPENSHELL_CHANNEL=dev, the existing NemoClaw dev-channel allowance for OpenShell dev builds above the current blueprint max.

What Is Proven

  • The target Discord Gateway issue is proven fixed in the combined OpenShell + NemoClaw path on Colima.
  • M9b proved generated openclaw.json bakes http://127.0.0.1:3128 into the Discord account proxy.
  • M13d-config proved the proxy URL read from openclaw.json reaches a fake Discord Gateway through OpenShell.
  • M13d/M13e proved the native WebSocket upgrade, HELLO, placeholder IDENTIFY, READY, and heartbeat ACK completed through the OpenShell path.
  • M13f proved the fake Gateway received the host-side Discord token while the sandbox-visible IDENTIFY used only the placeholder.
  • M13g proved an unregistered WebSocket credential placeholder is rejected before upstream token exposure.

Remaining E2E Caveat

  • The broad messaging E2E ended with 96 passed, 1 failed, 5 skipped.
  • The single failure was S1, an existing Slack guard probe that hardcodes internal port 18789. This isolated run intentionally used NEMOCLAW_DASHBOARD_PORT=18889 to avoid a local port collision, so that check probed the wrong port.
  • S2 still passed and showed the Slack guard caught the fake-token invalid_auth path without crashing the gateway. The S1 failure is outside the Discord loopback proxy and WebSocket credential-rewrite path proven above.

Test Plan

  • git diff --check
  • shellcheck scripts/nemoclaw-start.sh test/e2e/test-messaging-providers.sh
  • npm run source-shape:check
  • npm test -- --run test/generate-openclaw-config.test.ts test/nemoclaw-start.test.ts --testTimeout 20000
  • Combined OpenShell/NemoClaw Colima E2E target proof: M9b, M13d-config, M13d, M13f, M13g passed.

Summary by CodeRabbit

  • New Features
    • Added OPENSHELL_LOOPBACK_PROXY_URL support to prefer an OpenShell-provided loopback proxy for Discord gateway routing, with fallback to the sandbox proxy port.
  • Behavior
    • Startup now canonicalizes/validates loopback proxy URLs (including IPv6), probes reachability, and skips the local Discord helper when a compatible OpenShell proxy is present; otherwise it falls back with diagnostics.
  • Tests
    • New/updated tests cover URL normalization, reachability, matching logic, and fallback paths.
  • Documentation
    • Clarified compatibility notes around the OpenShell loopback listener.

Review Change Stack

@coderabbitai
Copy link
Copy Markdown
Contributor

coderabbitai Bot commented May 21, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 889869c6-9e1b-4269-8dc0-ddb5ebf5df63

📥 Commits

Reviewing files that changed from the base of the PR and between dd022b5 and c2ecf44.

📒 Files selected for processing (5)
  • scripts/generate-openclaw-config.py
  • scripts/nemoclaw-start.sh
  • test/e2e/test-messaging-providers.sh
  • test/generate-openclaw-config.test.ts
  • test/nemoclaw-start.test.ts

📝 Walkthrough

Walkthrough

Adds OPENSHELL_LOOPBACK_PROXY_URL (validated/normalized loopback HTTP URL), prefers it when generating Discord proxy entries, skips launching NemoClaw’s Discord loopback helper when OpenShell provides a matching reachable proxy, and updates tests and an inline Dockerfile comment.

Changes

Discord OpenShell loopback proxy

Layer / File(s) Summary
Configuration validation and preference
scripts/generate-openclaw-config.py, Dockerfile, test/generate-openclaw-config.test.ts
Documented OPENSHELL_LOOPBACK_PROXY_URL, added _valid_loopback_http_proxy_url() and updated build_config() to prefer a validated OpenShell loopback URL for discord_proxy_url; updated Dockerfile comment and added unit tests for default, override, schemeless normalization, and non-loopback ignore.
Discord helper runtime skip
scripts/nemoclaw-start.sh, test/e2e/test-messaging-providers.sh
Changed DISCORD_LOOPBACK_PROXY_PORT defaulting to prefer NEMOCLAW_DISCORD_PROXY_PORT/NEMOCLAW_PROXY_PORT; added canonicalization/reachability helpers and read_openclaw_discord_proxy_url(); modified start_discord_loopback_proxy() to skip launching NemoClaw’s helper when OpenShell provides a matching reachable loopback proxy; updated E2E Phase 3 comment and expected proxy computation.
Harness and compatibility tests
test/nemoclaw-start.test.ts
Added a Vitest suite that harnesses start_discord_loopback_proxy to assert behavior for reachable+matching, reachable+mismatch, unreachable, and IPv6 canonicalization cases.

Sequence Diagram(s)

sequenceDiagram
  participant OpenShell
  participant StartScript as start_discord_loopback_proxy
  participant OpenClaw as openclaw.json
  participant Probe as loopback_probe
  participant NemoClawHelper

  OpenShell->>StartScript: provide OPENSHELL_LOOPBACK_PROXY_URL
  StartScript->>OpenClaw: read discord_proxy_url
  StartScript->>Probe: probe OPENSHELL_LOOPBACK_PROXY_URL reachability
  Probe-->>StartScript: reachable / not reachable
  StartScript->>StartScript: canonicalize & compare OPENSHELL URL vs discord_proxy_url
  alt match & reachable
    StartScript-->>NemoClawHelper: skip launch ("Discord loopback proxy provided by OpenShell")
  else mismatch or unreachable
    StartScript->>NemoClawHelper: start helper (fallback)
  end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Possibly related PRs

  • NVIDIA/NemoClaw#3961: Modifies Discord loopback proxy wiring and helper startup logic, closely related to proxy-routing changes here.
  • NVIDIA/NemoClaw#3935: Updates generate-openclaw-config and E2E expectations for Discord account proxy wiring, overlapping test/config concerns.

Suggested labels

OpenShell, E2E, CI/CD, Networking, Sandbox, status: rfr

Suggested reviewers

  • jyaunches

Poem

🐰 I sniffed a tiny loopback trail,
OpenShell tended it without fail.
No duplicate helpers in the fray,
One cozy proxy leads the way.
The rabbit hops home, content today.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 12.50% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'fix(openclaw): prefer OpenShell loopback proxy' accurately describes the primary objective of the changeset, which is to prefer OpenShell's loopback proxy URL for Discord configuration when available.
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.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ 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 fix/prefer-openshell-loopback-proxy

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

ESLint skipped: no ESLint configuration detected in root package.json. To enable, add eslint to devDependencies.


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

Comment thread scripts/nemoclaw-start.sh Fixed
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 21, 2026

E2E Advisor Recommendation

Required E2E: messaging-providers-e2e, network-policy-e2e
Optional E2E: channels-stop-start-e2e, openclaw-onboard-security-posture-e2e

Dispatch hint: messaging-providers-e2e,network-policy-e2e

Auto-dispatched E2E: messaging-providers-e2e, network-policy-e2e via nightly-e2e.yaml at c2ecf44aae75a0ab22d6728d557810113c48a7acnightly run

Workflow run

Full advisor summary

E2E Recommendation Advisor

Base: origin/main
Head: HEAD
Confidence: high

Required E2E

  • messaging-providers-e2e (high): Primary regression coverage for this PR. It validates Telegram/Discord/Slack/WeChat provider attachment, placeholder config, no secret leakage, Discord REST policy, and the hermetic Discord Gateway WebSocket path using the proxy URL baked into openclaw.json. This directly covers the changed Discord loopback proxy routing behavior.
  • network-policy-e2e (medium): The PR changes proxy routing and loopback validation at the sandbox egress boundary. Run the network policy E2E to ensure deny-by-default, whitelist, hot-reload, inference exemption, permissive mode, and SSRF protections still hold with the updated proxy environment/startup behavior.

Optional E2E

  • channels-stop-start-e2e (high): Useful adjacent coverage because Discord channel stop/start/rebuild flows can re-render or re-use channel configuration and providers across OpenClaw/Hermes. Not merge-blocking if messaging-providers-e2e passes, but valuable for lifecycle confidence.
  • openclaw-onboard-security-posture-e2e (medium): Optional confidence for the full OpenClaw onboard/start path and runtime guard assertions after changes in nemoclaw-start.sh. Messaging-specific coverage is stronger for this PR, so this is not required.

New E2E recommendations

  • messaging-providers-discord-proxy-routing (high): Existing messaging-providers-e2e validates the fallback loopback helper and computes the expected OPENSHELL_LOOPBACK_PROXY_URL if present, but the workflow does not explicitly force a reachable OpenShell-managed loopback listener. Add a dedicated E2E mode or subtest that runs with OPENSHELL_LOOPBACK_PROXY_URL injected, verifies openclaw.json uses it, verifies NemoClaw helper is skipped, and proves the Discord Gateway path through that managed listener.
    • Suggested test: Add a Discord managed-loopback proxy E2E subcase to test/e2e/test-messaging-providers.sh or a focused nightly job that provisions a reachable OPENSHELL_LOOPBACK_PROXY_URL and asserts helper-skip plus fake Gateway success.

Dispatch hint

  • Workflow: nightly-e2e.yaml
  • jobs input: messaging-providers-e2e,network-policy-e2e

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 2

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

Inline comments:
In `@scripts/generate-openclaw-config.py`:
- Around line 98-109: The function _valid_loopback_http_proxy_url currently
returns the original raw input which allows schemeless values like
"127.0.0.1:45211" to pass validation but be emitted without "http://"; change it
to return a canonical normalized URL string instead: after parsing with
_normalize_url_for_parse and confirming parsed.scheme, parsed.hostname and
loopback, construct and return a normalized URL using parsed.scheme (default to
"http" if missing), parsed.hostname, and parsed.port (include port only if
present) so callers always receive a full "http://host[:port]" string; update
the return path that currently returns value to return this constructed
canonical URL.

In `@scripts/nemoclaw-start.sh`:
- Around line 1467-1471: The IPv6 loopback case in
is_openshell_loopback_proxy_url uses a case-pattern with unescaped brackets
(http://[::1]:*) which does not match literal URLs like http://[::1]:45211;
update the function to match IPv6 loopback correctly by either escaping the
literal brackets in the case pattern (so the pattern matches the literal '[' and
']') or replace that arm with a POSIX-compatible regex test (e.g., use grep -E
or bash =~) that matches ^http://\[::1\]:[0-9]+$; if you must keep the case form
and ShellCheck SC2102 still flags it, add a targeted suppression for that arm or
switch to the regex approach to avoid the ShellCheck warning.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 3ae6fd46-4fe5-46c9-ba61-ef4f906e5bb8

📥 Commits

Reviewing files that changed from the base of the PR and between d9d4510 and 2e8da85.

📒 Files selected for processing (6)
  • Dockerfile
  • scripts/generate-openclaw-config.py
  • scripts/nemoclaw-start.sh
  • test/e2e/test-messaging-providers.sh
  • test/generate-openclaw-config.test.ts
  • test/nemoclaw-start.test.ts

Comment thread scripts/generate-openclaw-config.py Outdated
Comment thread scripts/nemoclaw-start.sh Outdated
@github-actions
Copy link
Copy Markdown
Contributor

github-actions Bot commented May 21, 2026

PR Review Advisor

Recommendation: blocked
Confidence: high
Analyzed HEAD: c2ecf44aae75a0ab22d6728d557810113c48a7ac
Findings: 3 blocker(s), 3 warning(s), 0 suggestion(s)

This is an automated advisory review. A human maintainer must make the final merge decision.

Limitations: Review used supplied deterministic context and the provided diff; no PR scripts, package-manager commands, Docker builds, or tests were executed.; No passing messaging-providers-e2e or network-policy-e2e result for head SHA c2ecf44 is present in the supplied context.; No linked issues were provided, so acceptance mapping is based on PR body clauses, author follow-up comment clauses, and E2E Advisor comment clauses.; Runtime behavior of OpenShell-managed OPENSHELL_LOOPBACK_PROXY_URL depends on NVIDIA/OpenShell#1501 and the OpenShell version/pin used by CI images, which the supplied context does not verify.; Codebase drift assessment is based on supplied recent history and overlap metadata rather than live repository mutation checks.

Workflow run

Full advisor summary

PR Review Advisor

Base: origin/main
Head: HEAD
Analyzed SHA: c2ecf44aae75a0ab22d6728d557810113c48a7ac
Recommendation: blocked
Confidence: high

Blocked on hard gates: required CI context checks failed, mergeStateStatus is BLOCKED, and required E2E jobs are not shown passing for head SHA c2ecf44.

Gate status

  • CI: fail — Required status context(s) failed: checks. Non-required contexts still pending: 2; failed: 0. GraphQL status rollup shows checks COMPLETED with conclusion FAILURE and build-sandbox-images/build-sandbox-images-arm64 still IN_PROGRESS.
  • Mergeability: fail — mergeStateStatus=BLOCKED for headRefOid c2ecf44.
  • Review threads: pass — 5 review thread(s), all resolved. CodeRabbit comments report the normalization, IPv6, fallback log, and E2E expected-proxy findings addressed in c2ecf44.
  • Risky code tested: warning — Risky areas detected (credentials/inference/network, installer/bootstrap shell, onboarding/host glue). Unit tests and E2E script changed, but E2E Advisor required messaging-providers-e2e and network-policy-e2e for this head SHA and no passing result for c2ecf44 is present in the supplied context.

🔴 Blockers

  • Required CI context failed for current head: The PR cannot be considered ready while the required checks status context is failing for head SHA c2ecf44. The status rollup also shows sandbox image builds still in progress, so the final CI state is not clean.
    • Recommendation: Investigate and fix the failing checks job, then wait for all required contexts for c2ecf44 to complete successfully before merge consideration.
    • Evidence: Trusted gateStatus.ci: Required status context(s) failed: checks. Non-required contexts still pending: 2; failed: 0. GraphQL: checks COMPLETED/FAILURE; build-sandbox-images and build-sandbox-images-arm64 IN_PROGRESS.
  • Mergeability is blocked: GitHub reports the PR merge state as BLOCKED for the analyzed head SHA. This is a hard gate independent of the code review findings.
    • Recommendation: Do not merge until branch protection requirements are satisfied and mergeStateStatus is no longer BLOCKED.
    • Evidence: Trusted gateStatus.mergeability: mergeStateStatus=BLOCKED; GraphQL pullRequest.mergeStateStatus is BLOCKED.
  • Required E2E jobs are not proven for head SHA c2ecf44: The E2E Advisor requires messaging-providers-e2e and network-policy-e2e because this PR changes sandbox/network/credential routing behavior. The supplied context shows those jobs auto-dispatched for c2ecf44, but does not include passing results for that head SHA. Older selective messaging E2E passes were for prior SHAs and cannot satisfy this head.
    • Recommendation: Wait for both messaging-providers-e2e and network-policy-e2e to pass for c2ecf44. Treat older-SHA E2E results as non-authoritative for this head.
    • Evidence: E2E Advisor comment: Required E2E: messaging-providers-e2e, network-policy-e2e and auto-dispatched both at c2ecf44. Supplied selective E2E success is for dd022b5, not c2ecf44.

🟡 Warnings

  • Managed-loopback behavior still lacks deterministic E2E coverage (test/e2e/test-messaging-providers.sh:935): The E2E Advisor specifically recommends a new managed-loopback E2E mode that injects a reachable OPENSHELL_LOOPBACK_PROXY_URL, verifies openclaw.json uses it, verifies NemoClaw helper skip, and proves fake Discord Gateway routing through that listener. The diff updates expected-proxy selection but does not add a deterministic E2E subcase that provisions the OpenShell-managed listener and asserts helper skip in a live sandbox.
    • Recommendation: Add or schedule the recommended managed-loopback E2E subcase, or document why existing messaging-providers-e2e plus unit coverage is sufficient for this rollout. At minimum, ensure the required E2E jobs pass for c2ecf44.
    • Evidence: E2E Advisor New E2E recommendations: messaging-providers-discord-proxy-routing should force OPENSHELL_LOOPBACK_PROXY_URL and assert helper-skip plus fake Gateway success. Diff only mirrors validation in test/e2e/test-messaging-providers.sh expected proxy logic.
  • High codebase drift and overlap in active sandbox/OpenClaw files: The PR patches files with heavy recent activity and multiple open overlapping PRs, including Dockerfile, OpenClaw config generation, sandbox startup, and messaging E2E paths. This raises integration risk, especially around OpenShell/OpenClaw pins and proxy contracts.
  • Runtime behavior depends on external OpenShell managed-loopback contract: The PR depends on fix(sandbox): add managed loopback proxy OpenShell#1501 providing OPENSHELL_LOOPBACK_PROXY_URL and a reachable managed loopback listener. The NemoClaw fallback remains, which reduces risk, but the supplied trusted context does not prove that the OpenShell dependency has landed in the CI/runtime image used by the final E2E run.
    • Recommendation: Confirm the final CI/E2E environment includes the intended OpenShell behavior or that fallback-only behavior is acceptable until the OpenShell minimum pin moves. Keep the fallback until the minimum supported OpenShell version guarantees the listener.
    • Evidence: PR body states Depends on NVIDIA/OpenShell#1501 landing first; changed code falls back when OPENSHELL_LOOPBACK_PROXY_URL is absent, mismatched, invalid, or unreachable; no trusted result proves OpenShell#1501 is present for head c2ecf44.

🔵 Suggestions

  • None.

Acceptance coverage

  • met — Prefer OPENSHELL_LOOPBACK_PROXY_URL for OpenClaw Discord config when OpenShell provides a valid loopback HTTP proxy URL.: scripts/generate-openclaw-config.py adds OPENSHELL_LOOPBACK_PROXY_URL handling via _valid_loopback_http_proxy_url and uses it for discord_proxy_url when valid. Tests cover http://127.0.0.1:45211 preference, schemeless IPv6 normalization to http://[::1]:45211, and non-loopback fallback.
  • met — Skip NemoClaw's temporary Discord loopback helper only when the OpenShell URL is loopback, the baked OpenClaw Discord config points at that exact URL, and the listener is reachable.: scripts/nemoclaw-start.sh canonicalizes OPENSHELL_LOOPBACK_PROXY_URL, reads the baked Discord proxy from openclaw.json, compares exact canonical URL equality, and calls openshell_loopback_proxy_is_reachable before skipping. test/nemoclaw-start.test.ts covers skip, mismatch fallback, unreachable fallback, and IPv6 recognition.
  • met — Default the temporary Discord helper port to NEMOCLAW_PROXY_PORT unless NEMOCLAW_DISCORD_PROXY_PORT is explicitly set, so fallback config and helper startup stay aligned.: scripts/generate-openclaw-config.py sets discord_proxy_port = env.get("NEMOCLAW_DISCORD_PROXY_PORT") or proxy_port; scripts/nemoclaw-start.sh sets DISCORD_LOOPBACK_PROXY_PORT="${NEMOCLAW_DISCORD_PROXY_PORT:-${NEMOCLAW_PROXY_PORT:-3128}}"; tests assert the Discord loopback proxy port defaults to NEMOCLAW_PROXY_PORT.
  • met — Keep the existing NemoClaw helper as a compatibility fallback for older OpenShell releases/pins.: start_discord_loopback_proxy still launches the existing Node helper unless the OpenShell URL is valid, matches the baked Discord config, and is reachable. Config generation still falls back to http://127.0.0.1:${discord_proxy_port}.
  • unknown — Depends on fix(sandbox): add managed loopback proxy OpenShell#1501 landing first.: The PR body states this dependency, but the supplied trusted context does not prove whether fix(sandbox): add managed loopback proxy OpenShell#1501 has landed or whether the final CI/E2E environment includes that OpenShell managed-loopback listener.
  • met — The NemoClaw fallback remains in place until NemoClaw raises its minimum OpenShell pin beyond the release that includes the managed loopback proxy.: No OpenShell minimum pin change is shown in the changed files, and the fallback helper remains in scripts/nemoclaw-start.sh.
  • met — The no-secret invariant is preserved: Discord config still uses the placeholder token, not the real Discord token.: scripts/generate-openclaw-config.py keeps Discord token as openshell:resolve:env:DISCORD_BOT_TOKEN; test/e2e/test-messaging-providers.sh retains M9 checks that the Discord token does not match the host-side token.
  • unknowngit diff --check: The PR body and author follow-up comment state this was run, but the trusted context does not include command output for head SHA c2ecf44.
  • partialshellcheck scripts/nemoclaw-start.sh test/e2e/test-messaging-providers.sh: GraphQL shows ShellCheck and ShellCheck SARIF contexts SUCCESS for current head; the author follow-up also reports shellcheck. Marked partial because the exact local command output is not included and CI is still failing in the required checks context.
  • unknownnpm run source-shape:check: The PR body and author follow-up state this was run, but the supplied trusted context does not include the command output for c2ecf44.
  • partialnpm test -- --run test/generate-openclaw-config.test.ts test/nemoclaw-start.test.ts --testTimeout 20000: unit-vitest-linux is SUCCESS and the two changed unit test files add relevant coverage. The author follow-up reports 167 passed, but exact local command output is not in trusted context.
  • missing — Required E2E: messaging-providers-e2e, network-policy-e2e: E2E Advisor required both jobs and auto-dispatched them at c2ecf44, but no passing result for c2ecf44 is included in the supplied context.
  • unknown — Optional E2E: channels-stop-start-e2e, openclaw-onboard-security-posture-e2e: The E2E Advisor lists these as optional; the supplied context does not show them passing for the current head SHA.
  • missing — messaging-providers-discord-proxy-routing: Add a Discord managed-loopback proxy E2E subcase to test/e2e/test-messaging-providers.sh or a focused nightly job that provisions a reachable OPENSHELL_LOOPBACK_PROXY_URL and asserts helper-skip plus fake Gateway success.: The diff updates expected proxy validation, but no deterministic E2E mode is shown that provisions a reachable OpenShell-managed loopback listener and asserts helper skip plus fake Gateway success.

Security review

  • pass — 1. Secrets and Credentials: No hardcoded API keys, passwords, PEMs, or credential JSON are added. Discord and other messaging configs continue to use openshell:resolve:env placeholders; tests retain token non-leakage assertions. New logs print loopback proxy URLs, not credential material.
  • pass — 2. Input Validation and Data Sanitization: OPENSHELL_LOOPBACK_PROXY_URL is treated as untrusted input and canonicalized with parser-backed validation in both config generation and startup: only http scheme with localhost/::1/127.x loopback hosts is accepted, malformed ports raise and fall back, and non-loopback examples are tested. Shell glob-based validation from earlier review was replaced by Python canonicalization.
  • pass — 3. Authentication and Authorization: No new endpoints or authorization rules are introduced. Gateway auth, device auth, and credential placeholder authorization paths are not substantively changed.
  • pass — 4. Dependencies and Third-Party Libraries: No new package dependencies, registries, or version pins are introduced. Dockerfile changes are comments documenting the proxy behavior.
  • pass — 5. Error Handling and Logging: Invalid or unreachable managed-loopback inputs fall back to the NemoClaw helper rather than failing open. The latest diff splits mismatch and unreachable log cases, and no secrets are newly logged.
  • pass — 6. Cryptography and Data Protection: Not applicable — no cryptographic algorithms, key management, encryption-at-rest, or TLS validation behavior is changed.
  • warning — 7. Configuration and Security Headers: The change modifies security-sensitive Discord proxy routing at the sandbox egress boundary. The direction is loopback-only and fallback-safe, but the final posture depends on OpenShell#1501 availability and required E2E/network-policy proof for c2ecf44, which is not present in the supplied context.
  • warning — 8. Security Testing: Unit tests cover canonicalization, non-loopback fallback, port defaulting, helper skip, mismatch, unreachable listener, and IPv6 recognition. However, required messaging-providers-e2e and network-policy-e2e are not shown passing for c2ecf44, and the E2E Advisor recommends an additional managed-loopback subcase to prove helper skip and Discord Gateway routing through a reachable OpenShell listener.
  • warning — 9. Holistic Security Posture: Retaining the NemoClaw helper fallback while preferring an OpenShell-managed loopback proxy is directionally positive. Merge should remain blocked until CI is green, mergeability is unblocked, and required E2E jobs pass for the current head; otherwise a sandbox network-policy/credential-routing regression could ship without runtime proof.

Test / E2E status

  • Test depth: e2e_required — Runtime/sandbox/infrastructure paths need real execution coverage: Dockerfile documents the proxy contract, scripts/generate-openclaw-config.py changes Discord proxy config, scripts/nemoclaw-start.sh changes helper process lifecycle and reachability decisions, and test/e2e/test-messaging-providers.sh changes expected proxy behavior. Unit tests are useful but cannot prove live OpenShell listener behavior, Discord Gateway WebSocket routing, credential isolation, or network-policy/SSRF posture.
  • E2E Advisor: missing
  • Required E2E jobs: messaging-providers-e2e, network-policy-e2e
  • Missing for analyzed SHA: messaging-providers-e2e, network-policy-e2e

✅ What looks good

  • Compatibility fallback helper remains in place for older OpenShell releases and for invalid, mismatched, or unreachable managed-loopback inputs.
  • Config generation now canonicalizes schemeless and IPv6 loopback proxy URLs before writing openclaw.json.
  • Helper skip requires three conditions: valid canonical loopback URL, exact match with baked Discord config, and reachable listener.
  • Discord fallback helper port is aligned with NEMOCLAW_PROXY_PORT unless NEMOCLAW_DISCORD_PROXY_PORT is explicitly set.
  • Unit tests cover the key regression paths identified by earlier review comments, including non-loopback rejection, IPv6 canonicalization, mismatch fallback, and unreachable listener logging.
  • All review threads are reported resolved, and CodeRabbit reports the prior normalization/logging/E2E expected-proxy comments addressed in c2ecf44.

Review completeness

  • Review used supplied deterministic context and the provided diff; no PR scripts, package-manager commands, Docker builds, or tests were executed.
  • No passing messaging-providers-e2e or network-policy-e2e result for head SHA c2ecf44 is present in the supplied context.
  • No linked issues were provided, so acceptance mapping is based on PR body clauses, author follow-up comment clauses, and E2E Advisor comment clauses.
  • Runtime behavior of OpenShell-managed OPENSHELL_LOOPBACK_PROXY_URL depends on fix(sandbox): add managed loopback proxy OpenShell#1501 and the OpenShell version/pin used by CI images, which the supplied context does not verify.
  • Codebase drift assessment is based on supplied recent history and overlap metadata rather than live repository mutation checks.
  • Human maintainer review required: yes

@github-actions
Copy link
Copy Markdown
Contributor

Selective E2E Results — ✅ All requested jobs passed

Run: 26239803330
Target ref: 2e8da8594dc8790f693e5f9568bdf5041782d265
Workflow ref: main
Requested jobs: messaging-providers-e2e
Summary: 1 passed, 0 failed, 0 skipped

Job Result
messaging-providers-e2e ✅ success

Copy link
Copy Markdown
Contributor

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 2

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

Inline comments:
In `@scripts/nemoclaw-start.sh`:
- Around line 1534-1541: The current conditional misattributes causes when
configured_discord_proxy equals OPENSHELL_LOOPBACK_PROXY_URL but
openshell_loopback_proxy_is_reachable returns false to log a "does not match"
message; update the branching around configured_discord_proxy,
OPENSHELL_LOOPBACK_PROXY_URL and openshell_loopback_proxy_is_reachable so there
are three distinct outcomes: (1) equal AND reachable -> skip helper (existing
branch), (2) equal BUT NOT reachable -> log that the URL matches config but the
OpenShell loopback probe failed (use symbols configured_discord_proxy,
OPENSHELL_LOOPBACK_PROXY_URL, openshell_loopback_proxy_is_reachable), and (3)
not equal -> keep the current "does not match" or "could not be verified"
messages for non-empty or empty config respectively.

In `@test/e2e/test-messaging-providers.sh`:
- Around line 934-935: The test currently assigns expected_dc_proxy from
OPENSHELL_LOOPBACK_PROXY_URL without reusing the generator's loopback
validation, so supply the same validation used by build_config(): parse
OPENSHELL_LOOPBACK_PROXY_URL and only use it if it is a valid loopback HTTP URL
(scheme http, host is localhost/127.0.0.1/::1 or an explicit loopback IP, and
optionally includes a port); otherwise fall back to default_dc_proxy. Update the
expected_dc_proxy assignment to perform that validation (mirroring
build_config()'s logic) before choosing OPENSHELL_LOOPBACK_PROXY_URL,
referencing the variables default_dc_proxy and expected_dc_proxy and the
generator function build_config() as the source of truth for the validation
rules.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Enterprise

Run ID: 8a79762f-b03d-4c13-80dd-0e5aa53ecc24

📥 Commits

Reviewing files that changed from the base of the PR and between 2e8da85 and c8fec2e.

📒 Files selected for processing (5)
  • scripts/generate-openclaw-config.py
  • scripts/nemoclaw-start.sh
  • test/e2e/test-messaging-providers.sh
  • test/generate-openclaw-config.test.ts
  • test/nemoclaw-start.test.ts

Comment thread scripts/nemoclaw-start.sh Outdated
Comment thread test/e2e/test-messaging-providers.sh Outdated
@github-actions
Copy link
Copy Markdown
Contributor

Selective E2E Results — ✅ All requested jobs passed

Run: 26241223951
Target ref: c8fec2e60e86ff7355a423e7f22480a8812d9a7d
Workflow ref: main
Requested jobs: messaging-providers-e2e
Summary: 0 passed, 0 failed, 0 skipped

Job Result
messaging-providers-e2e ⚠️ cancelled

@github-actions
Copy link
Copy Markdown
Contributor

Selective E2E Results — ✅ All requested jobs passed

Run: 26241739522
Target ref: dd022b578806aa3880b33ac2c3fe6a86f230ff33
Workflow ref: main
Requested jobs: messaging-providers-e2e
Summary: 1 passed, 0 failed, 0 skipped

Job Result
messaging-providers-e2e ✅ success

@ericksoa
Copy link
Copy Markdown
Contributor Author

Follow-up for the CodeRabbit findings is pushed in c2ecf44.

What changed:

  • generate-openclaw-config.py now returns a canonical loopback HTTP proxy URL, so schemeless and IPv6 loopback inputs are emitted as full http://host[:port] URLs.
  • nemoclaw-start.sh now uses the same canonicalizer for OpenShell loopback detection, avoiding the IPv6 case-pattern issue and keeping skip/fallback decisions aligned with config generation.
  • The startup logs now distinguish the three cases CodeRabbit called out: matching + reachable skips the helper, matching + unreachable keeps fallback with an explicit reachability message, and mismatched or unverifiable config keeps the existing fallback messaging.
  • test/e2e/test-messaging-providers.sh now mirrors the generator validation before choosing the expected Discord proxy, so malformed or non-loopback OPENSHELL_LOOPBACK_PROXY_URL values fall back correctly.

Validation run:

  • python3 -m py_compile scripts/generate-openclaw-config.py
  • bash -n scripts/nemoclaw-start.sh test/e2e/test-messaging-providers.sh
  • shellcheck scripts/nemoclaw-start.sh test/e2e/test-messaging-providers.sh
  • git diff --check
  • npm run source-shape:check
  • npm test -- --run test/generate-openclaw-config.test.ts test/nemoclaw-start.test.ts --testTimeout 20000 (167 passed)

CI, CodeRabbit, and the E2E advisor are now re-running on the new head.

@github-actions
Copy link
Copy Markdown
Contributor

Selective E2E Results — ✅ All requested jobs passed

Run: 26246026845
Target ref: c2ecf44aae75a0ab22d6728d557810113c48a7ac
Workflow ref: main
Requested jobs: messaging-providers-e2e,network-policy-e2e
Summary: 2 passed, 0 failed, 0 skipped

Job Result
messaging-providers-e2e ✅ success
network-policy-e2e ✅ success

@wscurran wscurran added enhancement: integration PRs or issues proposing integration of a third-party product or service into NemoClaw. fix Integration: Discord Use this label to identify Discord bot integration issues with NemoClaw. NemoClaw CLI Use this label to identify issues with the NemoClaw command-line interface (CLI). OpenShell Support for OpenShell, a safe, private runtime for autonomous AI agents labels May 21, 2026
@wscurran
Copy link
Copy Markdown
Contributor

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement: integration PRs or issues proposing integration of a third-party product or service into NemoClaw. fix Integration: Discord Use this label to identify Discord bot integration issues with NemoClaw. NemoClaw CLI Use this label to identify issues with the NemoClaw command-line interface (CLI). OpenShell Support for OpenShell, a safe, private runtime for autonomous AI agents

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants