Skip to content

feat(codex): replace CLI adapter with SDK runtime - #66

Merged
rapids-bot[bot] merged 11 commits into
NVIDIA:mainfrom
AjayThorve:ajay/fabric-50-codex-sdk-relay-cutover
Jul 16, 2026
Merged

feat(codex): replace CLI adapter with SDK runtime#66
rapids-bot[bot] merged 11 commits into
NVIDIA:mainfrom
AjayThorve:ajay/fabric-50-codex-sdk-relay-cutover

Conversation

@AjayThorve

@AjayThorve AjayThorve commented Jul 14, 2026

Copy link
Copy Markdown
Collaborator

Overview

Replace the legacy nvidia.fabric.codex.cli subprocess adapter with the official Codex Python SDK and the nvidia.fabric.codex adapter. Preserve one-shot and multi-turn execution, ChatGPT and API-key authentication, normalized results, and optional NeMo Relay observability while removing Fabric's CLI-output parsing and process-control implementation.

This revision also makes semantic Relay output an acceptance criterion. A Fabric-managed Codex run must produce structured LLM model metadata, token usage, and an ATIF agent response comparable to a direct nemo-relay codex run.

Details

  • Drive Codex through typed SDK thread, turn, interruption, and shutdown APIs. Persist one Codex thread ID per Fabric runtime and reject mismatched resume state.
  • Keep the Codex SDK as the execution driver. harness.settings.codex_bin is an explicit SDK binary override for compatibility testing; it does not restore the removed Fabric CLI adapter.
  • Keep Relay as an optional supervised gateway and hook forwarder. Fabric retains Codex's built-in openai provider and supplies the gateway through request-scoped openai_base_url, preserving both cached ChatGPT login and OPENAI_API_KEY authentication.
  • Define the shared Relay CLI contract centrally (>=0.6.0,<0.7.0), select exact per-agent hook sets, and disable Relay's nested Codex delegation hook so Fabric owns the single SDK execution lifecycle.
  • Require semantic Relay artifacts in live Claude and Codex tests: a structured LLM request/model, total token usage, and the expected ATIF agent response.
  • Treat request-content decoding as a Relay transport concern. Compressed Codex request bodies require NeMo Relay PR #452; Fabric intentionally has no compression-specific configuration or decoding path.
  • Preserve Claude SDK parity discovered during cross-adapter live validation: inherit the Unix USER selector for cached login, retain typed SDK error results, and update the pinned Claude Agent SDK to 0.2.120.
  • Document Codex and Claude authentication modes, SDK/runtime pinning, the Relay compatibility range, native Codex OTEL versus Relay OpenInference output, and the current Relay decoding dependency.

Validation

  • just --set no_uv true test-python after syncing the CI extras: 312 passed, 11 skipped
  • Focused common/Claude/Codex/example suite: 95 passed, 5 skipped
  • cargo check -p fabric-python --locked
  • pre-commit run --all-files --show-diff-on-failure
  • Docs generation and fern check: 0 errors (one pre-existing warning is not printed by default)
  • Live Codex SDK plus patched Relay, full one-shot semantic assertion and two-turn resume:
    • SDK-pinned Codex runtime 0.137.0a4: passed
    • Explicit latest Codex 0.144.5: passed
  • Live Claude direct and Claude plus Relay with cached managed login: passed
  • Mock Claude plus released Relay 0.6.0: passed
  • Relay decoding dependency: 54 focused gateway tests, Clippy with -D warnings, cargo deny check bans licenses sources, and the Rust attribution hook passed in NeMo Relay PR #452

Where should the reviewer start?

Start with adapters/codex/src/nemo_fabric_adapters/codex/adapter.py, then adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py and tests/e2e/test_codex.py. The central design boundary is that the SDK owns Codex execution, Fabric owns runtime/session orchestration, and Relay owns gateway transport decoding plus semantic observability.

Related Issues: (use one of the action keywords Closes / Fixes / Resolves / Relates to)

  • Relates to FABRIC-50

  • Relates to NeMo Relay PR #452

  • I confirm this contribution is my own work, or I have the right to submit it under this project's license.

  • I searched existing issues and open pull requests, and this does not duplicate existing work.

@linear

linear Bot commented Jul 14, 2026

Copy link
Copy Markdown

@coderabbitai

coderabbitai Bot commented Jul 14, 2026

Copy link
Copy Markdown

Review Change Stack

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review

Walkthrough

Replaces the Codex CLI integration with a Python SDK adapter, adds persistent thread execution and optional Relay orchestration, updates package and configuration wiring, revises documentation and examples, and adds unit, integration, and opt-in end-to-end coverage.

Changes

Codex SDK adapter migration

Layer / File(s) Summary
SDK adapter runtime and package contract
adapters/codex/*
Adds SDK invocation, validation, persistence, normalized results, timeout handling, package metadata, and adapter manifest wiring.
Relay contracts and agent-specific hooks
adapters/common/*, tests/adapters/test_adapters_common_relay_*
Adds validated Relay CLI contracts and separate Claude/Codex hook event sets.
Adapter selection and execution wiring
pyproject.toml, examples/*, tests/fixtures/*, crates/fabric-core/*, tests/integrations/*
Renames Codex package, adapter IDs, profiles, variants, settings, artifact paths, and Harbor integration expectations.
Claude Relay compatibility
adapters/claude/*, tests/adapters/test_claude_adapter.py, tests/e2e/test_claude.py
Updates Claude SDK and Relay contracts, preserves USER, handles terminal SDK errors, and validates semantic Relay artifacts.
Validation and documentation
tests/adapters/test_codex_adapter.py, tests/e2e/test_codex.py, docs/*, README.md, ATTRIBUTIONS-Python.md
Adds Codex SDK, Relay, planning, environment, timeout, and end-to-end coverage and documents authentication, execution, configuration, and Relay behavior.

Estimated code review effort: 4 (Complex) | ~60 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Fabric
  participant CodexAdapter
  participant RelayGateway
  participant CodexSDK
  Fabric->>CodexAdapter: normalized invocation
  CodexAdapter->>RelayGateway: start optional gateway
  CodexAdapter->>CodexSDK: start or resume thread
  CodexSDK-->>CodexAdapter: result and thread ID
  CodexAdapter->>RelayGateway: stop and collect artifacts
  CodexAdapter-->>Fabric: normalized response
Loading

Possibly related PRs

Suggested labels: documentation, enhancement

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 11.71% 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
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 follows Conventional Commits, is under 72 characters, and accurately summarizes the Codex CLI-to-SDK replacement.
Description check ✅ Passed The description includes all required sections and sufficiently covers the change, reviewer start point, related issues, and validation.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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

@github-actions

Copy link
Copy Markdown

Signed-off-by: Ajay Thorve <athorve@nvidia.com>
@AjayThorve
AjayThorve force-pushed the ajay/fabric-50-codex-sdk-relay-cutover branch from 138265c to 495a0aa Compare July 14, 2026 22:46

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 6

🤖 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 `@adapters/codex/README.md`:
- Around line 15-18: Add a complete introductory sentence before the shell
command block in the Codex adapter README, stating that the local wheels should
be built and the Codex adapter installed. Keep the existing commands unchanged.

In `@adapters/codex/src/nemo_fabric_adapters/codex/adapter.py`:
- Around line 259-287: Update child_environment to read
runtime_context.telemetry.env from the adapter invocation payload, validate that
its keys and values are strings, and merge it into values after the
parent-environment blanking so prepared telemetry variables are preserved. Keep
the existing configured harness.settings.env validation and subsequent overrides
intact.

In `@ATTRIBUTIONS-Python.md`:
- Around line 6230-6236: Update both new attribution blocks in
ATTRIBUTIONS-Python.md: add blank lines before and after each ### Licenses
heading and fenced block, and annotate each fence with an appropriate language
such as text. Keep the existing license content unchanged and apply the same
Markdown structure consistently to both package blocks.

In `@tests/adapters/test_codex_adapter.py`:
- Around line 140-142: Replace the `monkeypatch.setenv` calls for `CODEX_HOME`,
`CODEX_INTERNAL_ORIGINATOR_OVERRIDE`, `FABRIC_UNRELATED_SECRET`, and the
additionally affected environment assignments with direct `os.environ`
mutations. Preserve the existing variable names and values, relying on
`restore_environ_fixture` for cleanup.
- Around line 76-134: Replace FakeTurnHandle, FakeThread, and FakeAsyncCodex
with MagicMock/AsyncMock instances configured with spec= for the SDK’s
AsyncCodex, thread, and handle interfaces. Update fake_codex_fixture and
affected tests to use mock-prefixed names while preserving configured results,
call tracking, interruption behavior, and thread_start/thread_resume responses.
- Around line 378-408: Update
test_relay_cleanup_failure_changes_success_to_failure to remove the unused
fake_codex parameter and apply pytest.mark.usefixtures for fake_codex,
preserving the fixture’s patching side effect while satisfying the
unused-argument check.
🪄 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: ASSERTIVE

Plan: Enterprise

Run ID: c3dafc38-7e8e-4832-b292-ffcb6c83e9e7

📥 Commits

Reviewing files that changed from the base of the PR and between 7844307 and 138265c.

⛔ Files ignored due to path filters (3)
  • adapters/codex-cli/uv.lock is excluded by !**/*.lock
  • adapters/codex/uv.lock is excluded by !**/*.lock
  • uv.lock is excluded by !**/*.lock
📒 Files selected for processing (39)
  • .agents/skills/review-doc-style/SKILL.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • adapters/codex-cli/README.md
  • adapters/codex-cli/src/nemo_fabric_adapters/codex_cli/adapter.py
  • adapters/codex/LICENSE
  • adapters/codex/README.md
  • adapters/codex/fabric-adapter.json
  • adapters/codex/pyproject.toml
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/index.yml
  • docs/integrations/codex.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • examples/harbor/README.md
  • examples/harbor/demo/README.md
  • examples/harbor/demo/task/environment/Dockerfile
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • justfile
  • pyproject.toml
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_codex_adapter.py
  • tests/adapters/test_codex_cli.py
  • tests/e2e/test_codex.py
  • tests/e2e/test_codex_cli.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
💤 Files with no reviewable changes (4)
  • adapters/codex-cli/README.md
  • tests/e2e/test_codex_cli.py
  • tests/adapters/test_codex_cli.py
  • adapters/codex-cli/src/nemo_fabric_adapters/codex_cli/adapter.py
📜 Review details
⏰ Context from checks skipped due to timeout. (5)
  • GitHub Check: Test (Python 3.13, x86_64)
  • GitHub Check: Test (Python 3.14, x86_64)
  • GitHub Check: Test (Python 3.14, arm64)
  • GitHub Check: Test (Python 3.11, x86_64)
  • GitHub Check: Test (Python 3.12, arm64)
🧰 Additional context used
📓 Path-based instructions (40)
**/*

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*: All source files must include the specified SPDX copyright and Apache-2.0 license header using the comment syntax appropriate to the file type.
Release tags must use raw Rust-compatible SemVer without a leading v, such as 0.1.0 or 0.1.0-rc.1.

**/*: Before implementing, explicitly state assumptions, surface ambiguity and tradeoffs, present multiple interpretations when relevant, and ask for clarification rather than silently deciding or proceeding when requirements are unclear.
Prefer the minimum code needed to solve the requested problem: avoid speculative features, unnecessary abstractions, unrequested flexibility, and handling of impossible scenarios; simplify overcomplicated solutions.
When editing existing code, make surgical changes only: do not modify unrelated code, comments, formatting, or pre-existing dead code; match the existing style, and remove only unused imports, variables, or functions introduced by your changes.
Define verifiable success criteria for each task, such as writing regression tests for bugs and invalid-input tests for validation, then verify the implementation against those criteria. For multi-step work, state a brief plan with a verification check for each step.

**/*: Keep pull request branch scope coherent and reviewable.
Run relevant tests under validate-change before opening or updating a pull request.
Format changed files with the language-native formatter.
Update documentation and examples for public behavior changes.
Update dependent maintainer or consumer guidance when code changes affect APIs, bindings, commands, paths, packaging guidance, or best practices.
Use Conventional Commit style for pull request titles: <type>: <concise imperative summary>, choosing the type from the actual change surface. Use fix only for user-facing or runtime product-code bug fixes.
A pull request body must include #### Overview, #### Details, #### Validation, #### Where should the reviewer start?, and `#### Related ...

Files:

  • adapters/codex/LICENSE
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • docs/index.yml
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • docs/getting-started/overview.mdx
  • adapters/codex/pyproject.toml
  • examples/harbor/README.md
  • examples/code_review_agent/__main__.py
  • examples/harbor/demo/task/environment/Dockerfile
  • docs/integrations/harbor.mdx
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • README.md
  • docs/getting-started/install.mdx
  • examples/code_review_agent/config.py
  • docs/integrations/codex.mdx
  • crates/fabric-core/src/doctor.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • justfile
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • ATTRIBUTIONS-Python.md
  • adapters/codex/fabric-adapter.json
  • adapters/codex/README.md
  • crates/fabric-core/src/config.rs
  • tests/e2e/test_codex.py
  • pyproject.toml
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{adapters/**,examples/**}

⚙️ CodeRabbit configuration file

{adapters/**,examples/**}: Review adapter and example changes for command correctness, config/schema consistency, artifact handling, and compatibility with the public Fabric contracts.

Files:

  • adapters/codex/LICENSE
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • adapters/codex/pyproject.toml
  • examples/harbor/README.md
  • examples/code_review_agent/__main__.py
  • examples/harbor/demo/task/environment/Dockerfile
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • examples/code_review_agent/config.py
  • examples/harbor/demo/README.md
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/codex/fabric-adapter.json
  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.py

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.py: Python public APIs must use type annotations, and native Python binding declarations must remain synchronized with their Rust implementations.
Python files must begin with the specified # SPDX copyright and Apache-2.0 license header.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,py}: Use snake_case for Rust and Python functions and variables; use PascalCase for Rust types and Python classes.
Run tests for every language surface affected by a change. Changes touching the Rust core or public schemas require both Rust and Python test suites.
Public contract changes must keep native Python binding declarations synchronized with their Rust implementations.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/doctor.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • crates/fabric-core/src/config.rs
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py,pyi,json,yaml,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Determine and update every affected public surface, including the CLI, PyO3 bindings, Python SDK, type stubs, schemas, and adapter contract, so they remain in parity.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • docs/index.yml
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/doctor.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/codex/fabric-adapter.json
  • crates/fabric-core/src/config.rs
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{py,pyi}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When Python code or a Python-facing adapter changes, run just test-python.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py,pyi,toml}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When the PyO3 bridge or package metadata changes, run just build-python and cargo check -p fabric-python --locked.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__init__.py
  • adapters/codex/pyproject.toml
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/doctor.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • crates/fabric-core/src/config.rs
  • tests/e2e/test_codex.py
  • pyproject.toml
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{toml,yaml,yml,sh,bash}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

TOML, YAML, and shell files must use the specified SPDX header with # comments.

Files:

  • docs/index.yml
  • adapters/codex/pyproject.toml
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • pyproject.toml
{README.md,docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Keep package names, repository references, and build commands current in documentation and examples.

Files:

  • docs/index.yml
  • examples/code_review_agent/README.md
  • docs/getting-started/overview.mdx
  • examples/harbor/README.md
  • docs/integrations/harbor.mdx
  • README.md
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
{README.md,docs/index.yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update README.md or docs/index.yml when documentation entry points or example reading paths change.

Files:

  • docs/index.yml
  • README.md
{docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update relevant getting-started, reference, adapter, and example documentation when the corresponding examples or adapters change.

Files:

  • docs/index.yml
  • examples/code_review_agent/README.md
  • docs/getting-started/overview.mdx
  • examples/harbor/README.md
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
docs/**/*.{md,mdx,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Run just docs when the documentation site changes.

Files:

  • docs/index.yml
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • docs/sdk/python.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Use the current install, import, build, test, clean, and documentation commands consistently in documentation, examples, CI workflows, and just recipes.

Files:

  • docs/index.yml
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • justfile
  • docs/sdk/python.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Reflect public packaging changes in release-facing documentation and examples.

Files:

  • docs/index.yml
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • docs/sdk/python.mdx
docs/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

For documentation or examples changes, run just docs when practical and verify documented commands against the current repository.

Files:

  • docs/index.yml
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • docs/sdk/python.mdx
{docs/**,README.md,AGENTS.md}

⚙️ CodeRabbit configuration file

{docs/**,README.md,AGENTS.md}: Review documentation for technical accuracy against the current API, command correctness, and consistency with generated schemas.

Files:

  • docs/index.yml
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • README.md
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • docs/sdk/python.mdx
**/*.{md,mdx,html}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Changes affecting public behavior, adapters, examples, or workspace structure must update the corresponding documentation; public API changes require updated SDK or API reference documentation.

Files:

  • examples/code_review_agent/README.md
  • docs/getting-started/overview.mdx
  • examples/harbor/README.md
  • docs/integrations/harbor.mdx
  • README.md
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Update an adapter or example README.md when that adapter or example surface changes.

Files:

  • examples/code_review_agent/README.md
  • examples/harbor/README.md
  • README.md
  • examples/harbor/demo/README.md
  • adapters/codex/README.md
**/*.{md,mdx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

For docs site changes, run just docs to regenerate Python and Rust API references and validate Fern configuration.

**/*.{md,mdx}: Ensure commands, package names, file paths, APIs, bindings, support claims, examples, and procedures are accurate and match current NeMo Fabric behavior and repository layout.
Update relevant entry-point documentation when public behavior changes, including README files, docs/index.yml references, package or crate READMEs, and adapter or integration READMEs.
Use {/* ... */} delimiters for top-of-file SPDX comments in MDX files.
Capitalize NVIDIA correctly and use consistent current repository terminology, product names, model names, and bindings.
Format commands, code elements, expressions, file names, paths, and filenames as inline code where appropriate.
Use title case for technical-documentation headings.
Introduce code blocks, tables, and lists with complete lead-in sentences.
Use descriptive link text instead of raw URLs or generic labels such as “here.”
Prefer active voice, present tense, short sentences, plain English, and precise wording.
Write procedures as imperative, parallel, easy-to-scan steps and split overly long sequences into smaller tasks.
Use “after” instead of “once” when expressing temporal order, and use “can” instead of “may” when describing possibility rather than permission.
Use unambiguous dates and avoid ordinal dates in body text.
Ensure code blocks are introduced by full sentences and that examples match current APIs and build commands.
For learning-oriented documentation, do not add trademark symbols unless the source document explicitly requires them.

Files:

  • examples/code_review_agent/README.md
  • docs/getting-started/overview.mdx
  • examples/harbor/README.md
  • docs/integrations/harbor.mdx
  • README.md
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/*.{html,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

HTML and Markdown files must use the specified SPDX header in an HTML comment.

Files:

  • examples/code_review_agent/README.md
  • examples/harbor/README.md
  • README.md
  • examples/harbor/demo/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/*.{md,rst}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Update documentation and examples in the same branch as the public API change.

Verify README and documentation entry points, package names, paths, examples, and public commands remain current after changes.

Files:

  • examples/code_review_agent/README.md
  • examples/harbor/README.md
  • README.md
  • examples/harbor/demo/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/*.{md,mdx,rst}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-guide.md)

**/*.{md,mdx,rst}: For NeMo Fabric documentation, verify technical claims against the current repository, public API, or documented command before reviewing style.
Always spell NVIDIA in all caps; do not use Nvidia, nvidia, or NV.
Format commands, code elements, expressions, package names, file names, and paths as inline code.
Use descriptive link text; avoid raw URLs and weak anchors such as here or read more.
Use title case consistently for technical documentation headings.
Introduce code blocks, lists, tables, and images with complete sentences.
Write procedures as imperative, parallel steps; split long procedures into smaller tasks.
Prefer active voice, present tense, short sentences, contractions, and plain English while preserving necessary technical precision.
Use can for possibility and reserve may for permission.
Use after for temporal relationships instead of once, and prefer refer to over see when directing readers to another resource.
Avoid culture-specific idioms, unnecessary Latinisms, jokes, and marketing exaggeration in technical documentation.
Spell out months in body text, avoid ordinal dates, and use clear time zones.
Spell out whole numbers from zero through nine unless they are technical values, parameters, versions, or UI values; use numerals for 10 or greater and commas in thousands.
Do not add trademark symbols to learning-oriented documentation unless the source, platform, or legal guidance explicitly requires them.
Do not replace precise technical terms with simpler words when doing so would lose precision.
Do not flag passive voice when the actor is unknown or the action is the important part.
Do not rewrite API names, package names, command flags, or code literals for style.

**/*.{md,mdx,rst}: Use consistent title case for technical-document headings and table headers; avoid quotation marks, ampersands, and exclamation marks in headings, while preserving official product, event, research, and whitepaper title ...

Files:

  • examples/code_review_agent/README.md
  • docs/getting-started/overview.mdx
  • examples/harbor/README.md
  • docs/integrations/harbor.mdx
  • README.md
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • examples/harbor/demo/README.md
  • docs/sdk/python.mdx
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/*.{md,rst,txt,adoc}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-language-mechanics.md)

**/*.{md,rst,txt,adoc}: For technical documentation, use professional, active, conversational, engaging, precise, and plain-English prose. Prefer active voice, present tense, short sentences, and scannable paragraphs. Avoid casual or imprecise language, swearing, threats, insults, jokes, puns, culture-specific idioms, marketing exaggeration, and unsupported third-party comparisons.
Use can for possibility and reserve may for permission; use after for temporal order; use refer to for cross-references; prefer short direct sentences and specific verbs; avoid unnecessary please in technical documentation.
Prefer active voice when the actor matters. Passive voice is acceptable when the actor is unknown or irrelevant, when the action or result is the focus, or in programmer documentation.
Use natural contractions in conversational technical prose, but do not force them in formal legal copy, API references, or generated text.
Prefer simpler English over Latinisms: use for example or such as instead of e.g., and so on instead of etc., that is instead of i.e., compared to instead of vs., and by, through, or using instead of via. Use industry-standard terms such as in silico, in vitro, and in vivo when appropriate, and italicize them in running text.
Use that without commas for essential clauses, and which with commas for nonessential clauses.
Format dates and times clearly: spell out months in body text; use forms such as June 12, 2025; avoid numeric or ordinal dates; capitalize days; use 12-hour time when appropriate; include a space before a.m. or p.m.; use ET and PT for needed time zones; avoid 24/7; and prefer from 12:30 to 1:00 p.m. for prose ranges.
Format numbers consistently: spell out zero through nine in body text, use numerals for 10 or greater and for technical values, use commas in thousands, do not begin a sentence with a numeral, spell out ordinals, and use numerals consistently within a category wh...

Files:

  • examples/code_review_agent/README.md
  • examples/harbor/README.md
  • README.md
  • examples/harbor/demo/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
**/*.mdx

📄 CodeRabbit inference engine (CONTRIBUTING.md)

MDX files must use the specified SPDX header in a JSX comment.

In MDX files, use JSX comment delimiters ({/* and */}) for top-of-file comments, including SPDX headers; do not use HTML comments.

Files:

  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/getting-started/install.mdx
  • docs/integrations/codex.mdx
  • docs/sdk/python.mdx
**/*.{rs,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,toml}: Rust code must be formatted with cargo fmt --all; formatting can be checked with cargo fmt --all -- --check, and Rust workspaces must compile with cargo check --workspace --locked.
Rust files must begin with the specified // SPDX copyright and Apache-2.0 license header.

When Rust code or Rust project configuration changes, run cargo fmt --all -- --check and just test-rust.

Files:

  • adapters/codex/pyproject.toml
  • crates/fabric-core/src/doctor.rs
  • crates/fabric-core/src/config.rs
  • pyproject.toml
**/pyproject.toml

📄 CodeRabbit inference engine (.agents/skills/update-project-version/SKILL.md)

Run just build-python to verify that all Python package metadata resolves.

Files:

  • adapters/codex/pyproject.toml
  • pyproject.toml
README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

The root README.md must reflect the current workspace, supported adapters, and top-level documentation.

Update README.md when a small Fabric bug fix changes public behavior.

Files:

  • README.md
**/*.rs

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Implement new runtime or binding behavior in the shared Rust core first.

For any Rust change, run just test-rust and cargo fmt --all -- --check.

Run cargo check --workspace --locked after version changes.

Files:

  • crates/fabric-core/src/doctor.rs
  • crates/fabric-core/src/config.rs
crates/fabric-core/**/*

📄 CodeRabbit inference engine (.agents/skills/prepare-pr/SKILL.md)

For changes under crates/fabric-core, run both the Rust and Python test suites.

When crates/fabric-core changes in a way exposed through Python, run both the Rust and Python test suites.

Files:

  • crates/fabric-core/src/doctor.rs
  • crates/fabric-core/src/config.rs
crates/fabric-core/src/**/*.rs

⚙️ CodeRabbit configuration file

crates/fabric-core/src/**/*.rs: Review the Rust core for runtime lifecycle correctness, handle validation, capability routing accuracy, schema stability, and error semantics.
Public API changes should match committed schemas, tests, and documentation.

Files:

  • crates/fabric-core/src/doctor.rs
  • crates/fabric-core/src/config.rs
tests/**/*.py

📄 CodeRabbit inference engine (.agents/skills/python-tests/SKILL.md)

tests/**/*.py: Use Pytest to run Python tests.
Do not add @pytest.mark.asyncio to tests; async tests are automatically detected by the async runner.
Do not add -> None return annotations to test functions.
When mocking a class, use unittest.mock.MagicMock or AsyncMock, supplying spec when necessary; do not define a new mock class.
Prefix mocked class names with mock, not fake.
Prefer pytest fixtures over helper methods.
Define shared fixtures in conftest.py rather than repeating them across test files.
Define fixtures using @pytest.fixture(name="<fixture_name>"[, scope="<scope>"]) and a <fixture_name>_fixture function; specify scope only when it is not function.
Prefer pytest.mark.parametrize over separate tests for different input types.
Use @pytest.mark.usefixtures when a fixture is needed but its return value is unused.
Use os.environ to modify environment variables in tests; do not use monkeypatch.setenv, because the autouse restore_environ_fixture in tests/conftest.py restores the environment after each test.
Avoid defensive programming in tests; access expected data directly so missing data raises a clear error instead of being silently tolerated.
Run focused tests with uv run pytest -k "<pattern>" and all tests with uv run pytest.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
tests/adapters/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When an adapter or integration changes, run its focused tests under tests/adapters, followed by just test-python.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_codex_adapter.py
{tests/**,python/tests/**}

⚙️ CodeRabbit configuration file

{tests/**,python/tests/**}: Tests should cover the behavior promised by the changed API surface, including error paths, lifecycle cleanup, and SDK/native parity where relevant.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
{.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile,pyproject.toml,python/pyproject.toml,Cargo.toml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

CI workflows must reference the same package names and commands used by local build and installation workflows.

Files:

  • justfile
  • pyproject.toml
justfile

📄 CodeRabbit inference engine (.agents/skills/small-fix/SKILL.md)

Use or update the repository’s justfile when it provides the focused validation path for a small Fabric bug fix.

The set-version recipe must update source metadata and then run just lock-python.

Files:

  • justfile
**/*.{json,jsonc}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Public contract changes must keep checked-in JSON Schema snapshots synchronized.

Files:

  • adapters/codex/fabric-adapter.json
{Cargo.toml,pyproject.toml,python/pyproject.toml,python/src/nemo_fabric/**}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

{Cargo.toml,pyproject.toml,python/pyproject.toml,python/src/nemo_fabric/**}: Keep Rust package names, Python package/import paths, and native module names internally consistent across Cargo and Python packaging metadata and source paths.
Ensure generated native and Python artifacts are placed where downstream consumers expect them.

Files:

  • pyproject.toml
{Cargo.toml,pyproject.toml,python/pyproject.toml,Cargo.lock,uv.lock}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Keep workspace, Rust, Python, and lockfile versions aligned where required.

Files:

  • pyproject.toml
{pyproject.toml,python/pyproject.toml,Cargo.toml,python/src/nemo_fabric/**}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

The editable maturin build must continue to produce the nemo_fabric._native extension.

Files:

  • pyproject.toml
{Cargo.toml,Cargo.lock,pyproject.toml,python/pyproject.toml,uv.lock,docs/package.json,docs/package-lock.json}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Maintain package metadata and dependency resolution consistently across Rust, Python, documentation tooling, and their lockfiles.

Files:

  • pyproject.toml
🧠 Learnings (3)
📓 Common learnings
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:42:31.796Z
Learning: During documentation reviews, identify changed docs, examples, and public-facing strings; verify behavior against the current repository; consult the NVIDIA style guide and only focused supporting documents; and report actionable findings in severity order with file references and concrete rewrites.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:42:31.796Z
Learning: Prioritize factual accuracy and current repository behavior over copy polish, while applying NVIDIA technical-writing guidance without reducing technical precision.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:42:31.796Z
Learning: When no issues are found, state that explicitly and mention residual risks, such as commands or examples that were not executed.
📚 Learning: 2026-07-09T22:28:51.689Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 43
File: adapters/claude-sdk/src/nemo_fabric_adapters/claude_sdk/adapter.py:164-168
Timestamp: 2026-07-09T22:28:51.689Z
Learning: In the NeMo-Fabric adapters, treat path values used in Fabric adapter configuration (including logic like `_resolve_path` in adapter.py) as config-root-relative. Do not apply `Path.expanduser()` (or otherwise apply `~`/home or shell-style expansion), because it will make the resolved paths normalize inconsistently across adapters. Also, do not rely on or add any resolution behavior that uses `harness.settings.cwd` as an override point for these adapter paths—`harness.settings.cwd` is explicitly unsupported in this adapter context.

Applied to files:

  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
📚 Learning: 2026-06-29T22:34:52.407Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 27
File: adapters/codex-cli/fabric-adapter.json:13-15
Timestamp: 2026-06-29T22:34:52.407Z
Learning: In NeMo-Fabric adapter manifest files (e.g., `*/fabric-adapter.json`), keep `config.accepts` limited to the top-level Fabric capability sections that `resolve_capability_plan` consumes (such as `models`, `tools`, `mcp`, `skills`, `telemetry`). Do not add adapter-owned `harness.settings` keys to `config.accepts`; `harness.settings` should remain adapter-owned and be passed through unchanged.

Applied to files:

  • adapters/codex/fabric-adapter.json
🧬 Code graph analysis (4)
crates/fabric-core/src/doctor.rs (1)
crates/fabric-core/src/config.rs (1)
  • resolve_run_plan (1172-1175)
tests/e2e/test_codex.py (1)
examples/code_review_agent/config.py (1)
  • with_relay (188-210)
tests/adapters/test_codex_adapter.py (1)
adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)
  • RelayGatewayLaunch (31-38)
  • RelayGatewayError (26-27)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (2)
adapters/common/src/nemo_fabric_adapters/common/utils.py (6)
  • load_relay_plugin_config (193-217)
  • load_payload (76-82)
  • settings_payload (108-110)
  • native_telemetry_config (161-163)
  • environment_payload (104-105)
  • models_payload (113-114)
adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)
  • RelayGatewayLaunch (31-38)
  • RelayGatewayError (26-27)
🪛 ast-grep (0.44.1)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py

[warning] 492-492: Do not make http calls without encryption
Context: f"http://{bind}"
Note: [CWE-319] Cleartext Transmission of Sensitive Information.

(requests-http)


[info] 340-343: use jsonify instead of json.dumps for JSON output
Context: json.dumps(
{"runtime_id": fabric_runtime_id, "codex_thread_id": codex_thread_id},
sort_keys=True,
)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)


[info] 360-360: use jsonify instead of json.dumps for JSON output
Context: json.dumps(value, allow_nan=False)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)


[info] 894-894: use jsonify instead of json.dumps for JSON output
Context: json.dumps(output, sort_keys=True)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)

🪛 markdownlint-cli2 (0.23.0)
ATTRIBUTIONS-Python.md

[warning] 6230-6230: Headings should be surrounded by blank lines
Expected: 1; Actual: 0; Below

(MD022, blanks-around-headings)


[warning] 6234-6234: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 6234-6234: Fenced code blocks should have a language specified

(MD040, fenced-code-language)


[warning] 6240-6240: Headings should be surrounded by blank lines
Expected: 1; Actual: 0; Below

(MD022, blanks-around-headings)


[warning] 6244-6244: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 6244-6244: Fenced code blocks should have a language specified

(MD040, fenced-code-language)

🪛 Ruff (0.15.21)
tests/adapters/test_codex_adapter.py

[warning] 77-77: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 91-91: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 96-96: Missing type annotation for **kwargs

(ANN003)


[warning] 102-102: Mutable default value for class attribute

(RUF012)


[warning] 106-106: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 114-114: Missing type annotation for **kwargs

(ANN003)


[warning] 119-119: Missing type annotation for **kwargs

(ANN003)


[warning] 264-264: Missing return type annotation for private function thread_resume

(ANN202)


[warning] 264-264: Missing type annotation for **kwargs

(ANN003)


[warning] 379-379: Unused function argument: fake_codex

(ARG001)


[warning] 474-474: Missing return type annotation for private function run

Add return type annotation: None

(ANN202)


[warning] 478-478: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 482-482: Missing return type annotation for private function thread_start

(ANN202)


[warning] 482-482: Missing type annotation for **kwargs

(ANN003)


[error] 559-559: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py

[warning] 30-30: Use from nemo_fabric_adapters.common import relay_gateway in lieu of alias

Replace with from nemo_fabric_adapters.common import relay_gateway

(PLR0402)


[warning] 31-31: Use from nemo_fabric_adapters.common import relay_hooks in lieu of alias

Replace with from nemo_fabric_adapters.common import relay_hooks

(PLR0402)


[warning] 130-130: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 262-262: Unnecessary dict comprehension for iterable; use dict.fromkeys instead

Replace with dict.fromkeys(iterable))

(C420)


[warning] 314-314: Prefer TypeError exception for invalid type

(TRY004)


[warning] 314-314: Abstract raise to an inner function

(TRY301)


[warning] 314-314: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 316-316: Abstract raise to an inner function

(TRY301)


[warning] 316-316: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 319-319: Abstract raise to an inner function

(TRY301)


[warning] 319-319: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 320-320: Consider moving this statement to an else block

(TRY300)


[warning] 359-359: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 359-359: Dynamically typed expressions (typing.Any) are disallowed in _json_value

(ANN401)


[warning] 603-603: Too many return statements (7 > 6)

(PLR0911)


[warning] 603-603: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 603-603: Dynamically typed expressions (typing.Any) are disallowed in _json_safe

(ANN401)


[warning] 628-628: Dynamically typed expressions (typing.Any) are disallowed in **metadata

(ANN401)


[warning] 678-678: Dynamically typed expressions (typing.Any) are disallowed in result

(ANN401)


[warning] 717-717: Dynamically typed expressions (typing.Any) are disallowed in handle

(ANN401)


[warning] 791-791: Do not catch blind exception: Exception

(BLE001)


[warning] 880-880: Do not catch blind exception: Exception

(BLE001)


[warning] 889-889: Do not catch blind exception: Exception

(BLE001)

🔇 Additional comments (36)
.agents/skills/review-doc-style/SKILL.md (1)

36-36: LGTM!

README.md (1)

147-151: LGTM!

Also applies to: 181-183

adapters/codex/README.md (1)

1-14: LGTM!

Also applies to: 19-143

examples/harbor/README.md (1)

63-63: LGTM!

Also applies to: 194-194

examples/harbor/demo/README.md (1)

143-149: LGTM!

Also applies to: 169-171

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

310-310: LGTM!

docs/getting-started/install.mdx (1)

64-75: LGTM!

docs/getting-started/overview.mdx (1)

13-13: LGTM!

Also applies to: 54-54

docs/index.yml (1)

17-18: LGTM!

docs/integrations/codex.mdx (2)

1-9: LGTM!

Also applies to: 14-66


10-12: 🎯 Functional Correctness

No change needed The wording already distinguishes the SDK-managed pinned app-server runtime from the legacy codex CLI adapter.

			> Likely an incorrect or invalid review comment.
docs/integrations/harbor.mdx (1)

12-12: LGTM!

Also applies to: 73-73

docs/sdk/python.mdx (1)

195-195: LGTM!

Also applies to: 410-410

examples/code_review_agent/README.md (1)

62-62: LGTM!

tests/adapters/test_codex_adapter.py (1)

137-274: LGTM!

Also applies to: 410-511, 514-559

tests/e2e/test_codex.py (1)

1-119: LGTM!

tests/integrations/test_harbor_runner.py (2)

4-7: LGTM!

Also applies to: 28-31, 254-288


294-300: 🎯 Functional Correctness

No issue.

tests/python/test_code_review_example.py (1)

15-15: LGTM!

Also applies to: 28-44, 76-92

adapters/codex/LICENSE (1)

1-1: LGTM!

adapters/codex/pyproject.toml (1)

11-13: LGTM!

Also applies to: 28-29, 39-50

adapters/codex/src/nemo_fabric_adapters/codex/__init__.py (1)

4-4: LGTM!

adapters/codex/fabric-adapter.json (1)

3-8: LGTM!

adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (1)

10-15: LGTM!

Also applies to: 31-42, 64-69

tests/adapters/test_adapters_common_relay_hooks.py (1)

12-13: LGTM!

Also applies to: 28-54, 68-77

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)

1-258: LGTM!

Also applies to: 288-901

crates/fabric-core/src/config.rs (1)

2304-2315: LGTM!

crates/fabric-core/src/doctor.rs (1)

532-554: LGTM!

examples/harbor/demo/task/environment/fabric/configs/codex.yaml (1)

8-15: LGTM!

examples/harbor/demo/task/environment/Dockerfile (1)

8-8: LGTM!

Also applies to: 17-17

justfile (1)

13-13: LGTM!

pyproject.toml (1)

41-42: LGTM!

Also applies to: 57-58, 92-92, 122-130

tests/fixtures/file-config-agent/profiles/codex.yaml (1)

5-13: LGTM!

Also applies to: 28-28, 30-33

examples/code_review_agent/config.py (1)

102-123: LGTM!

examples/code_review_agent/__init__.py (1)

9-9: LGTM!

Also applies to: 23-23

examples/code_review_agent/__main__.py (1)

17-25: LGTM!

Comment thread adapters/codex/README.md
Comment thread adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
Comment thread ATTRIBUTIONS-Python.md
Comment thread tests/adapters/test_codex_adapter.py Outdated
Comment thread tests/adapters/test_codex_adapter.py Outdated
Comment thread tests/adapters/test_codex_adapter.py

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 1

Caution

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

⚠️ Outside diff range comments (1)
tests/python/test_code_review_example.py (1)

31-41: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Cover Codex configuration independence in this test.

The test now exercises codex_config(), but only verifies that the Hermes configuration is independent from base. Add equivalent Codex identity assertions so a shared configuration or harness object cannot regress unnoticed.

Proposed test assertions
     assert hermes is not base
     assert hermes.harness is not base.harness
+    assert codex is not base
+    assert codex.harness is not base.harness
     assert codex.harness.adapter_id == "nvidia.fabric.codex"

As per path instructions, tests should cover behavior promised by the changed API surface.

🤖 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 `@tests/python/test_code_review_example.py` around lines 31 - 41, Extend the
test around codex_config() to verify Codex is independent from the base
configuration and harness, matching the existing Hermes identity assertions. Add
identity checks for codex versus base and codex.harness versus base.harness
while preserving the existing adapter_id assertion.

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.

Inline comments:
In `@tests/e2e/test_codex.py`:
- Line 6: Update the focused test command for the Codex integration tests to run
through the managed uv environment, using the repository’s uv run pytest
convention with an appropriate -k pattern instead of invoking pytest directly.

---

Outside diff comments:
In `@tests/python/test_code_review_example.py`:
- Around line 31-41: Extend the test around codex_config() to verify Codex is
independent from the base configuration and harness, matching the existing
Hermes identity assertions. Add identity checks for codex versus base and
codex.harness versus base.harness while preserving the existing adapter_id
assertion.
🪄 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: ASSERTIVE

Plan: Enterprise

Run ID: 21ba67b1-6285-4e94-ac8c-ea5e7f812c52

📥 Commits

Reviewing files that changed from the base of the PR and between 138265c and 495a0aa.

⛔ Files ignored due to path filters (3)
  • adapters/codex-cli/uv.lock is excluded by !**/*.lock
  • adapters/codex/uv.lock is excluded by !**/*.lock
  • uv.lock is excluded by !**/*.lock
📒 Files selected for processing (39)
  • .agents/skills/review-doc-style/SKILL.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • adapters/codex-cli/README.md
  • adapters/codex-cli/src/nemo_fabric_adapters/codex_cli/adapter.py
  • adapters/codex/LICENSE
  • adapters/codex/README.md
  • adapters/codex/fabric-adapter.json
  • adapters/codex/pyproject.toml
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/index.yml
  • docs/integrations/codex.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • examples/harbor/README.md
  • examples/harbor/demo/README.md
  • examples/harbor/demo/task/environment/Dockerfile
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • justfile
  • pyproject.toml
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_codex_adapter.py
  • tests/adapters/test_codex_cli.py
  • tests/e2e/test_codex.py
  • tests/e2e/test_codex_cli.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • tests/integrations/test_harbor_runner.py
  • tests/python/test_code_review_example.py
💤 Files with no reviewable changes (4)
  • adapters/codex-cli/README.md
  • tests/e2e/test_codex_cli.py
  • adapters/codex-cli/src/nemo_fabric_adapters/codex_cli/adapter.py
  • tests/adapters/test_codex_cli.py
📜 Review details
🧰 Additional context used
📓 Path-based instructions (41)
**/*

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*: All source files must include the specified SPDX copyright and Apache-2.0 license header using the comment syntax appropriate to the file type.
Release tags must use raw Rust-compatible SemVer without a leading v, such as 0.1.0 or 0.1.0-rc.1.

**/*: Before implementing, explicitly state assumptions, surface ambiguity and tradeoffs, present multiple interpretations when relevant, and ask for clarification rather than silently deciding or proceeding when requirements are unclear.
Prefer the minimum code needed to solve the requested problem: avoid speculative features, unnecessary abstractions, unrequested flexibility, and handling of impossible scenarios; simplify overcomplicated solutions.
When editing existing code, make surgical changes only: do not modify unrelated code, comments, formatting, or pre-existing dead code; match the existing style, and remove only unused imports, variables, or functions introduced by your changes.
Define verifiable success criteria for each task, such as writing regression tests for bugs and invalid-input tests for validation, then verify the implementation against those criteria. For multi-step work, state a brief plan with a verification check for each step.

**/*: Keep pull request branch scope coherent and reviewable.
Run relevant tests under validate-change before opening or updating a pull request.
Format changed files with the language-native formatter.
Update documentation and examples for public behavior changes.
Update dependent maintainer or consumer guidance when code changes affect APIs, bindings, commands, paths, packaging guidance, or best practices.
Use Conventional Commit style for pull request titles: <type>: <concise imperative summary>, choosing the type from the actual change surface. Use fix only for user-facing or runtime product-code bug fixes.
A pull request body must include #### Overview, #### Details, #### Validation, #### Where should the reviewer start?, and `#### Related ...

Files:

  • adapters/codex/LICENSE
  • docs/index.yml
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/harbor/README.md
  • examples/code_review_agent/__init__.py
  • justfile
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • crates/fabric-core/src/config.rs
  • examples/harbor/demo/README.md
  • examples/harbor/demo/task/environment/Dockerfile
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • adapters/codex/README.md
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • ATTRIBUTIONS-Python.md
  • crates/fabric-core/src/doctor.rs
  • README.md
  • adapters/codex/fabric-adapter.json
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • pyproject.toml
  • adapters/codex/pyproject.toml
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • docs/integrations/codex.mdx
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{adapters/**,examples/**}

⚙️ CodeRabbit configuration file

{adapters/**,examples/**}: Review adapter and example changes for command correctness, config/schema consistency, artifact handling, and compatibility with the public Fabric contracts.

Files:

  • adapters/codex/LICENSE
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/harbor/README.md
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/README.md
  • examples/harbor/demo/README.md
  • examples/harbor/demo/task/environment/Dockerfile
  • adapters/codex/README.md
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • adapters/codex/fabric-adapter.json
  • adapters/codex/pyproject.toml
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{toml,yaml,yml,sh,bash}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

TOML, YAML, and shell files must use the specified SPDX header with # comments.

Files:

  • docs/index.yml
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • pyproject.toml
  • adapters/codex/pyproject.toml
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
**/*.{rs,py,pyi,json,yaml,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Determine and update every affected public surface, including the CLI, PyO3 bindings, Python SDK, type stubs, schemas, and adapter contract, so they remain in parity.

Files:

  • docs/index.yml
  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/code_review_agent/__init__.py
  • crates/fabric-core/src/config.rs
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • adapters/codex/fabric-adapter.json
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/harbor/demo/task/environment/fabric/configs/codex.yaml
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{README.md,docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Keep package names, repository references, and build commands current in documentation and examples.

Files:

  • docs/index.yml
  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • README.md
  • docs/integrations/codex.mdx
{README.md,docs/index.yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update README.md or docs/index.yml when documentation entry points or example reading paths change.

Files:

  • docs/index.yml
  • README.md
{docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update relevant getting-started, reference, adapter, and example documentation when the corresponding examples or adapters change.

Files:

  • docs/index.yml
  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
docs/**/*.{md,mdx,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Run just docs when the documentation site changes.

Files:

  • docs/index.yml
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Use the current install, import, build, test, clean, and documentation commands consistently in documentation, examples, CI workflows, and just recipes.

Files:

  • docs/index.yml
  • justfile
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Reflect public packaging changes in release-facing documentation and examples.

Files:

  • docs/index.yml
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
docs/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

For documentation or examples changes, run just docs when practical and verify documented commands against the current repository.

Files:

  • docs/index.yml
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
{docs/**,README.md,AGENTS.md}

⚙️ CodeRabbit configuration file

{docs/**,README.md,AGENTS.md}: Review documentation for technical accuracy against the current API, command correctness, and consistency with generated schemas.

Files:

  • docs/index.yml
  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • README.md
  • docs/integrations/codex.mdx
**/*.py

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.py: Python public APIs must use type annotations, and native Python binding declarations must remain synchronized with their Rust implementations.
Python files must begin with the specified # SPDX copyright and Apache-2.0 license header.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/code_review_agent/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,py}: Use snake_case for Rust and Python functions and variables; use PascalCase for Rust types and Python classes.
Run tests for every language surface affected by a change. Changes touching the Rust core or public schemas require both Rust and Python test suites.
Public contract changes must keep native Python binding declarations synchronized with their Rust implementations.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/code_review_agent/__init__.py
  • crates/fabric-core/src/config.rs
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{py,pyi}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When Python code or a Python-facing adapter changes, run just test-python.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/code_review_agent/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py,pyi,toml}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When the PyO3 bridge or package metadata changes, run just build-python and cargo check -p fabric-python --locked.

Files:

  • adapters/codex/src/nemo_fabric_adapters/codex/__init__.py
  • examples/code_review_agent/__init__.py
  • crates/fabric-core/src/config.rs
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • pyproject.toml
  • adapters/codex/pyproject.toml
  • examples/code_review_agent/config.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{md,mdx,html}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Changes affecting public behavior, adapters, examples, or workspace structure must update the corresponding documentation; public API changes require updated SDK or API reference documentation.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • docs/integrations/codex.mdx
**/README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Update an adapter or example README.md when that adapter or example surface changes.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • examples/harbor/demo/README.md
  • adapters/codex/README.md
  • README.md
**/*.{md,mdx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

For docs site changes, run just docs to regenerate Python and Rust API references and validate Fern configuration.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • docs/integrations/codex.mdx
**/*.{html,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

HTML and Markdown files must use the specified SPDX header in an HTML comment.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • examples/harbor/demo/README.md
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
**/*.{md,rst}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Update documentation and examples in the same branch as the public API change.

Verify README and documentation entry points, package names, paths, examples, and public commands remain current after changes.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • examples/harbor/demo/README.md
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
**/*.{md,mdx,rst}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-guide.md)

**/*.{md,mdx,rst}: For NeMo Fabric documentation, verify technical claims against the current repository, public API, or documented command before reviewing style.
Always spell NVIDIA in all caps; do not use Nvidia, nvidia, or NV.
Format commands, code elements, expressions, package names, file names, and paths as inline code.
Use descriptive link text; avoid raw URLs and weak anchors such as here or read more.
Use title case consistently for technical documentation headings.
Introduce code blocks, lists, tables, and images with complete sentences.
Write procedures as imperative, parallel steps; split long procedures into smaller tasks.
Prefer active voice, present tense, short sentences, contractions, and plain English while preserving necessary technical precision.
Use can for possibility and reserve may for permission.
Use after for temporal relationships instead of once, and prefer refer to over see when directing readers to another resource.
Avoid culture-specific idioms, unnecessary Latinisms, jokes, and marketing exaggeration in technical documentation.
Spell out months in body text, avoid ordinal dates, and use clear time zones.
Spell out whole numbers from zero through nine unless they are technical values, parameters, versions, or UI values; use numerals for 10 or greater and commas in thousands.
Do not add trademark symbols to learning-oriented documentation unless the source, platform, or legal guidance explicitly requires them.
Do not replace precise technical terms with simpler words when doing so would lose precision.
Do not flag passive voice when the actor is unknown or the action is the important part.
Do not rewrite API names, package names, command flags, or code literals for style.

**/*.{md,mdx,rst}: Use consistent title case for technical-document headings and table headers; avoid quotation marks, ampersands, and exclamation marks in headings, while preserving official product, event, research, and whitepaper title ...

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • docs/integrations/codex.mdx
**/*.{md,rst,txt,adoc}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-language-mechanics.md)

**/*.{md,rst,txt,adoc}: For technical documentation, use professional, active, conversational, engaging, precise, and plain-English prose. Prefer active voice, present tense, short sentences, and scannable paragraphs. Avoid casual or imprecise language, swearing, threats, insults, jokes, puns, culture-specific idioms, marketing exaggeration, and unsupported third-party comparisons.
Use can for possibility and reserve may for permission; use after for temporal order; use refer to for cross-references; prefer short direct sentences and specific verbs; avoid unnecessary please in technical documentation.
Prefer active voice when the actor matters. Passive voice is acceptable when the actor is unknown or irrelevant, when the action or result is the focus, or in programmer documentation.
Use natural contractions in conversational technical prose, but do not force them in formal legal copy, API references, or generated text.
Prefer simpler English over Latinisms: use for example or such as instead of e.g., and so on instead of etc., that is instead of i.e., compared to instead of vs., and by, through, or using instead of via. Use industry-standard terms such as in silico, in vitro, and in vivo when appropriate, and italicize them in running text.
Use that without commas for essential clauses, and which with commas for nonessential clauses.
Format dates and times clearly: spell out months in body text; use forms such as June 12, 2025; avoid numeric or ordinal dates; capitalize days; use 12-hour time when appropriate; include a space before a.m. or p.m.; use ET and PT for needed time zones; avoid 24/7; and prefer from 12:30 to 1:00 p.m. for prose ranges.
Format numbers consistently: spell out zero through nine in body text, use numerals for 10 or greater and for technical values, use commas in thousands, do not begin a sentence with a numeral, spell out ordinals, and use numerals consistently within a category wh...

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • examples/harbor/demo/README.md
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
**/*.{md,mdx,rst,txt}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/SKILL.md)

**/*.{md,mdx,rst,txt}: Prioritize factual accuracy over copy polish in documentation and public-facing text.
Verify commands, package names, APIs, bindings, file paths, repository paths, and support claims against current NeMo Fabric behavior.
Update user-facing entry-point documentation when public behavior changes, including README.md, docs/index.yml, package or crate READMEs, and relevant adapter or integration READMEs.
Capitalize NVIDIA correctly as NVIDIA.
Format code, commands, paths, filenames, and code elements as inline code where appropriate.
Use descriptive link text instead of raw URLs or generic labels such as here.
Prefer active voice, present tense, short sentences, and plain English.
Use consistent terminology for the same concept throughout a document.
Write procedures as imperative, parallel, easy-to-scan steps, splitting long sequences into smaller tasks.
Use after instead of once when expressing temporal sequence.
Use can rather than may when the intended meaning is possibility rather than permission.
Avoid ambiguous numeric dates and ordinal dates in body text.
For learning-oriented documentation, do not force trademark symbols unless the source document explicitly requires them.

Files:

  • examples/harbor/README.md
  • examples/code_review_agent/README.md
  • docs/getting-started/install.mdx
  • examples/harbor/demo/README.md
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • adapters/codex/README.md
  • ATTRIBUTIONS-Python.md
  • README.md
  • docs/integrations/codex.mdx
{.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile,pyproject.toml,python/pyproject.toml,Cargo.toml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

CI workflows must reference the same package names and commands used by local build and installation workflows.

Files:

  • justfile
  • pyproject.toml
justfile

📄 CodeRabbit inference engine (.agents/skills/small-fix/SKILL.md)

Use or update the repository’s justfile when it provides the focused validation path for a small Fabric bug fix.

The set-version recipe must update source metadata and then run just lock-python.

Files:

  • justfile
**/*.mdx

📄 CodeRabbit inference engine (CONTRIBUTING.md)

MDX files must use the specified SPDX header in a JSX comment.

In MDX files, use JSX comment delimiters ({/* and */}) for top-of-file comments, including SPDX headers; do not use HTML comments.

Use {/* ... */} delimiters for top-of-file MDX SPDX comments, not HTML comment delimiters.

Files:

  • docs/getting-started/install.mdx
  • docs/getting-started/overview.mdx
  • docs/integrations/harbor.mdx
  • docs/sdk/python.mdx
  • docs/integrations/codex.mdx
**/*.{rs,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,toml}: Rust code must be formatted with cargo fmt --all; formatting can be checked with cargo fmt --all -- --check, and Rust workspaces must compile with cargo check --workspace --locked.
Rust files must begin with the specified // SPDX copyright and Apache-2.0 license header.

When Rust code or Rust project configuration changes, run cargo fmt --all -- --check and just test-rust.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
  • pyproject.toml
  • adapters/codex/pyproject.toml
**/*.rs

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Implement new runtime or binding behavior in the shared Rust core first.

For any Rust change, run just test-rust and cargo fmt --all -- --check.

Run cargo check --workspace --locked after version changes.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
crates/fabric-core/**/*

📄 CodeRabbit inference engine (.agents/skills/prepare-pr/SKILL.md)

For changes under crates/fabric-core, run both the Rust and Python test suites.

When crates/fabric-core changes in a way exposed through Python, run both the Rust and Python test suites.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
crates/fabric-core/src/**/*.rs

⚙️ CodeRabbit configuration file

crates/fabric-core/src/**/*.rs: Review the Rust core for runtime lifecycle correctness, handle validation, capability routing accuracy, schema stability, and error semantics.
Public API changes should match committed schemas, tests, and documentation.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
tests/**/*.py

📄 CodeRabbit inference engine (.agents/skills/python-tests/SKILL.md)

tests/**/*.py: Use Pytest to run Python tests.
Do not add @pytest.mark.asyncio to tests; async tests are automatically detected by the async runner.
Do not add -> None return annotations to test functions.
When mocking a class, use unittest.mock.MagicMock or AsyncMock, supplying spec when necessary; do not define a new mock class.
Prefix mocked class names with mock, not fake.
Prefer pytest fixtures over helper methods.
Define shared fixtures in conftest.py rather than repeating them across test files.
Define fixtures using @pytest.fixture(name="<fixture_name>"[, scope="<scope>"]) and a <fixture_name>_fixture function; specify scope only when it is not function.
Prefer pytest.mark.parametrize over separate tests for different input types.
Use @pytest.mark.usefixtures when a fixture is needed but its return value is unused.
Use os.environ to modify environment variables in tests; do not use monkeypatch.setenv, because the autouse restore_environ_fixture in tests/conftest.py restores the environment after each test.
Avoid defensive programming in tests; access expected data directly so missing data raises a clear error instead of being silently tolerated.
Run focused tests with uv run pytest -k "<pattern>" and all tests with uv run pytest.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
tests/adapters/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When an adapter or integration changes, run its focused tests under tests/adapters, followed by just test-python.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_codex_adapter.py
{tests/**,python/tests/**}

⚙️ CodeRabbit configuration file

{tests/**,python/tests/**}: Tests should cover the behavior promised by the changed API surface, including error paths, lifecycle cleanup, and SDK/native parity where relevant.

Files:

  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/fixtures/file-config-agent/profiles/codex.yaml
  • tests/python/test_code_review_example.py
  • tests/e2e/test_codex.py
  • tests/integrations/test_harbor_runner.py
  • tests/adapters/test_codex_adapter.py
README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

The root README.md must reflect the current workspace, supported adapters, and top-level documentation.

Update README.md when a small Fabric bug fix changes public behavior.

Files:

  • README.md
**/*.{json,jsonc}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Public contract changes must keep checked-in JSON Schema snapshots synchronized.

Files:

  • adapters/codex/fabric-adapter.json
{Cargo.toml,pyproject.toml,python/pyproject.toml,python/src/nemo_fabric/**}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

{Cargo.toml,pyproject.toml,python/pyproject.toml,python/src/nemo_fabric/**}: Keep Rust package names, Python package/import paths, and native module names internally consistent across Cargo and Python packaging metadata and source paths.
Ensure generated native and Python artifacts are placed where downstream consumers expect them.

Files:

  • pyproject.toml
{Cargo.toml,pyproject.toml,python/pyproject.toml,Cargo.lock,uv.lock}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Keep workspace, Rust, Python, and lockfile versions aligned where required.

Files:

  • pyproject.toml
{pyproject.toml,python/pyproject.toml,Cargo.toml,python/src/nemo_fabric/**}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

The editable maturin build must continue to produce the nemo_fabric._native extension.

Files:

  • pyproject.toml
{Cargo.toml,Cargo.lock,pyproject.toml,python/pyproject.toml,uv.lock,docs/package.json,docs/package-lock.json}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Maintain package metadata and dependency resolution consistently across Rust, Python, documentation tooling, and their lockfiles.

Files:

  • pyproject.toml
**/pyproject.toml

📄 CodeRabbit inference engine (.agents/skills/update-project-version/SKILL.md)

Run just build-python to verify that all Python package metadata resolves.

Files:

  • pyproject.toml
  • adapters/codex/pyproject.toml
🧠 Learnings (3)
📓 Common learnings
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:49:51.495Z
Learning: Keep documentation changes scoped, surface assumptions, and define focused validation before editing.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:49:51.495Z
Learning: When reviewing documentation, report findings in severity order with file references, line references, explanations, and concrete rewrites or directions.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-14T22:49:51.495Z
Learning: Classify documentation review findings as `Must fix`, `Should fix`, or `Nice to have`; explicitly state when no issues are found and mention residual risk.
📚 Learning: 2026-07-09T22:28:51.689Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 43
File: adapters/claude-sdk/src/nemo_fabric_adapters/claude_sdk/adapter.py:164-168
Timestamp: 2026-07-09T22:28:51.689Z
Learning: In the NeMo-Fabric adapters, treat path values used in Fabric adapter configuration (including logic like `_resolve_path` in adapter.py) as config-root-relative. Do not apply `Path.expanduser()` (or otherwise apply `~`/home or shell-style expansion), because it will make the resolved paths normalize inconsistently across adapters. Also, do not rely on or add any resolution behavior that uses `harness.settings.cwd` as an override point for these adapter paths—`harness.settings.cwd` is explicitly unsupported in this adapter context.

Applied to files:

  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
📚 Learning: 2026-06-29T22:34:52.407Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 27
File: adapters/codex-cli/fabric-adapter.json:13-15
Timestamp: 2026-06-29T22:34:52.407Z
Learning: In NeMo-Fabric adapter manifest files (e.g., `*/fabric-adapter.json`), keep `config.accepts` limited to the top-level Fabric capability sections that `resolve_capability_plan` consumes (such as `models`, `tools`, `mcp`, `skills`, `telemetry`). Do not add adapter-owned `harness.settings` keys to `config.accepts`; `harness.settings` should remain adapter-owned and be passed through unchanged.

Applied to files:

  • adapters/codex/fabric-adapter.json
🧬 Code graph analysis (4)
crates/fabric-core/src/doctor.rs (1)
crates/fabric-core/src/config.rs (1)
  • resolve_run_plan (1172-1175)
tests/e2e/test_codex.py (1)
examples/code_review_agent/config.py (1)
  • with_relay (188-210)
tests/adapters/test_codex_adapter.py (1)
adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)
  • RelayGatewayLaunch (31-38)
  • RelayGatewayError (26-27)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (2)
adapters/common/src/nemo_fabric_adapters/common/utils.py (6)
  • load_relay_plugin_config (193-217)
  • load_payload (76-82)
  • settings_payload (108-110)
  • native_telemetry_config (161-163)
  • environment_payload (104-105)
  • models_payload (113-114)
adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)
  • RelayGatewayLaunch (31-38)
  • RelayGatewayError (26-27)
🪛 ast-grep (0.44.1)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py

[info] 340-343: use jsonify instead of json.dumps for JSON output
Context: json.dumps(
{"runtime_id": fabric_runtime_id, "codex_thread_id": codex_thread_id},
sort_keys=True,
)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)


[info] 360-360: use jsonify instead of json.dumps for JSON output
Context: json.dumps(value, allow_nan=False)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)


[info] 894-894: use jsonify instead of json.dumps for JSON output
Context: json.dumps(output, sort_keys=True)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)


[warning] 492-492: Do not make http calls without encryption
Context: f"http://{bind}"
Note: [CWE-319] Cleartext Transmission of Sensitive Information.

(requests-http)

🪛 markdownlint-cli2 (0.23.0)
ATTRIBUTIONS-Python.md

[warning] 6230-6230: Headings should be surrounded by blank lines
Expected: 1; Actual: 0; Below

(MD022, blanks-around-headings)


[warning] 6234-6234: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 6234-6234: Fenced code blocks should have a language specified

(MD040, fenced-code-language)


[warning] 6240-6240: Headings should be surrounded by blank lines
Expected: 1; Actual: 0; Below

(MD022, blanks-around-headings)


[warning] 6244-6244: Fenced code blocks should be surrounded by blank lines

(MD031, blanks-around-fences)


[warning] 6244-6244: Fenced code blocks should have a language specified

(MD040, fenced-code-language)

🪛 Ruff (0.15.21)
tests/adapters/test_codex_adapter.py

[warning] 77-77: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 91-91: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 96-96: Missing type annotation for **kwargs

(ANN003)


[warning] 102-102: Mutable default value for class attribute

(RUF012)


[warning] 106-106: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 114-114: Missing type annotation for **kwargs

(ANN003)


[warning] 119-119: Missing type annotation for **kwargs

(ANN003)


[warning] 264-264: Missing return type annotation for private function thread_resume

(ANN202)


[warning] 264-264: Missing type annotation for **kwargs

(ANN003)


[warning] 379-379: Unused function argument: fake_codex

(ARG001)


[warning] 474-474: Missing return type annotation for private function run

Add return type annotation: None

(ANN202)


[warning] 478-478: Missing return type annotation for special method __init__

Add return type annotation: None

(ANN204)


[warning] 482-482: Missing return type annotation for private function thread_start

(ANN202)


[warning] 482-482: Missing type annotation for **kwargs

(ANN003)


[error] 559-559: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py

[warning] 30-30: Use from nemo_fabric_adapters.common import relay_gateway in lieu of alias

Replace with from nemo_fabric_adapters.common import relay_gateway

(PLR0402)


[warning] 31-31: Use from nemo_fabric_adapters.common import relay_hooks in lieu of alias

Replace with from nemo_fabric_adapters.common import relay_hooks

(PLR0402)


[warning] 130-130: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 262-262: Unnecessary dict comprehension for iterable; use dict.fromkeys instead

Replace with dict.fromkeys(iterable))

(C420)


[warning] 314-314: Prefer TypeError exception for invalid type

(TRY004)


[warning] 314-314: Abstract raise to an inner function

(TRY301)


[warning] 314-314: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 316-316: Abstract raise to an inner function

(TRY301)


[warning] 316-316: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 319-319: Abstract raise to an inner function

(TRY301)


[warning] 319-319: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 320-320: Consider moving this statement to an else block

(TRY300)


[warning] 359-359: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 359-359: Dynamically typed expressions (typing.Any) are disallowed in _json_value

(ANN401)


[warning] 603-603: Too many return statements (7 > 6)

(PLR0911)


[warning] 603-603: Dynamically typed expressions (typing.Any) are disallowed in value

(ANN401)


[warning] 603-603: Dynamically typed expressions (typing.Any) are disallowed in _json_safe

(ANN401)


[warning] 628-628: Dynamically typed expressions (typing.Any) are disallowed in **metadata

(ANN401)


[warning] 678-678: Dynamically typed expressions (typing.Any) are disallowed in result

(ANN401)


[warning] 717-717: Dynamically typed expressions (typing.Any) are disallowed in handle

(ANN401)


[warning] 791-791: Do not catch blind exception: Exception

(BLE001)


[warning] 880-880: Do not catch blind exception: Exception

(BLE001)


[warning] 889-889: Do not catch blind exception: Exception

(BLE001)

🔇 Additional comments (52)
crates/fabric-core/src/config.rs (1)

2296-2341: LGTM!

crates/fabric-core/src/doctor.rs (1)

530-556: LGTM!

Confirmed binary_command_setting_key("fabric-doctor-test") normalizes to fabric_doctor_test_command, matching the updated assertion.

justfile (1)

13-13: LGTM!

pyproject.toml (2)

41-43: LGTM!

Also applies to: 58-58, 92-92, 126-132


122-124: Verified: prerelease pin matches upstream Codex SDK requirement.

Confirmed via upstream openai/codex release notes that PR "#26216 [codex] Pin Python SDK to runtime 0.137.0a4" pins exactly this prerelease version. The narrow constraint-dependencies scoping (rather than enabling prereleases globally) is the correct approach.
[dependency_check]

tests/fixtures/file-config-agent/profiles/codex.yaml (1)

5-33: LGTM!

tests/integrations/test_harbor_runner.py (3)

28-31: LGTM!


254-287: LGTM!

Assertions correctly match the SDK adapter helpers (selected_model, sandbox, _reasoning_effort, thread_config) shown in the graph context for adapters/codex/src/nemo_fabric_adapters/codex/adapter.py.


290-300: LGTM!

examples/code_review_agent/__init__.py (1)

9-9: LGTM!

Also applies to: 23-23

examples/code_review_agent/__main__.py (1)

17-25: LGTM!

examples/code_review_agent/config.py (1)

102-127: LGTM!

examples/harbor/demo/task/environment/fabric/configs/codex.yaml (1)

8-15: LGTM!

examples/harbor/demo/task/environment/Dockerfile (1)

8-8: LGTM!

Also applies to: 17-17

tests/python/test_code_review_example.py (1)

15-15: LGTM!

Also applies to: 79-92

ATTRIBUTIONS-Python.md (1)

6230-6245: Duplicate: format both new attribution blocks for Markdown lint.

The ### Licenses headings and fenced blocks still need blank-line spacing and a language such as text; this was already raised in the previous review.

adapters/codex/README.md (1)

13-18: Duplicate: introduce the install command with a complete sentence.

Add a sentence such as “Build the local wheels and install the Codex adapter:” before the shell block; this was already raised in the previous review.

.agents/skills/review-doc-style/SKILL.md (1)

36-36: LGTM!

README.md (1)

147-148: LGTM!

Also applies to: 182-182

examples/harbor/README.md (1)

63-63: LGTM!

Also applies to: 194-194

examples/harbor/demo/README.md (1)

143-149: LGTM!

Also applies to: 169-171

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

310-310: LGTM!

docs/getting-started/install.mdx (1)

64-75: LGTM!

docs/getting-started/overview.mdx (1)

13-13: LGTM!

Also applies to: 54-54

docs/index.yml (1)

17-18: LGTM!

docs/integrations/codex.mdx (2)

53-65: LGTM!


29-51: 🎯 Functional Correctness

The Codex CLI prerequisite is already covered. The page scopes codex login to cached-credential setup, and adapters/codex already depends on openai-codex-cli-bin, so this does not introduce a missing user-installed CLI requirement.

			> Likely an incorrect or invalid review comment.
docs/integrations/harbor.mdx (1)

12-12: LGTM!

Also applies to: 73-73

docs/sdk/python.mdx (1)

195-195: LGTM!

Also applies to: 410-410

examples/code_review_agent/README.md (1)

62-62: LGTM!

tests/adapters/test_codex_adapter.py (4)

76-134: Replace the hand-written SDK test doubles with repository-standard mocks.

This remains covered by the existing review comment; it also applies to the derived blocking test doubles.

Also applies to: 259-269, 470-487


140-142: Use os.environ instead of monkeypatch.setenv.

This is already covered by the existing review comment.

Also applies to: 305-305, 553-554


378-408: Mark the side-effect-only fixture with pytest.mark.usefixtures.

This is already covered by the existing review comment.


1-75: LGTM!

Also applies to: 135-139, 143-258, 270-304, 306-377, 409-469, 488-552, 555-559

adapters/codex/LICENSE (1)

1-1: LGTM!

adapters/codex/pyproject.toml (2)

11-13: LGTM!

Also applies to: 39-45


29-29: 📐 Maintainability & Code Quality

No change needed uv.lock already pins openai-codex==0.1.0b3 and openai-codex-cli-bin==0.137.0a4.

			> Likely an incorrect or invalid review comment.
tests/e2e/test_codex.py (1)

1-5: LGTM!

Also applies to: 7-120

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (10)

259-287: Telemetry env still dropped from the SDK child process.

This is the same gap flagged on the prior revision: values = {name: "" for name in os.environ} blanks everything, and runtime_context.telemetry.env is still never merged back in before the SDK subprocess starts. Native OTel env vars provided via runtime_context.telemetry won't reach Codex.


1-88: LGTM!


90-158: LGTM! resolve_cwd correctly treats environment.workspace as config-root-relative and avoids expanduser()/harness.settings.cwd, consistent with the adapter path-resolution convention used elsewhere.

Also applies to: 176-184


160-257: LGTM!


290-397: LGTM! Hashing runtime_id for the state filename avoids path-injection concerns, and save_thread_id uses an invocation-scoped temp file + os.replace for atomic writes.


398-530: LGTM! thread_config applies config_overrides before the Relay merge, so Relay's openai_base_url/hooks/bypass_hook_trust can't be overridden by user config — sound security ordering.


533-600: LGTM!


798-871: LGTM! run_codex's finally-block gateway teardown and run()'s exception-to-failure-envelope boundary correctly keep CodexAdapterError distinct from the catch-all path.

Also applies to: 873-902


717-796: 🎯 Functional Correctness

turn() already uses the SDK’s effort= keyword.

thread.turn() accepts effort in openai-codex==0.1.0b3, so this call matches the public signature.

			> Likely an incorrect or invalid review comment.

603-620: 🩺 Stability & Availability

started_at/completed_at/duration_ms are already JSON-safe. TurnResult exposes these as int | None, so leaving them unwrapped won’t cause json.dumps to raise here.

			> Likely an incorrect or invalid review comment.
adapters/codex/src/nemo_fabric_adapters/codex/__init__.py (1)

1-5: LGTM!

adapters/codex/fabric-adapter.json (1)

3-8: LGTM!

adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (1)

10-15: LGTM!

Also applies to: 31-42, 64-69

tests/adapters/test_adapters_common_relay_hooks.py (1)

12-13: LGTM!

Also applies to: 28-54, 68-77

Comment thread tests/e2e/test_codex.py Outdated
Signed-off-by: Ajay Thorve <athorve@nvidia.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 1

Caution

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

⚠️ Outside diff range comments (2)
adapters/codex/README.md (2)

136-136: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Format the path placeholder with angle brackets.

Use <path/to/nemo-relay> instead of /path/to/nemo-relay; the latter looks like a literal absolute path.

🤖 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 `@adapters/codex/README.md` at line 136, Update the
FABRIC_TEST_NEMO_RELAY_COMMAND example in the README to wrap the path
placeholder in angle brackets, using <path/to/nemo-relay> instead of the
literal-looking /path/to/nemo-relay value.

Source: Coding guidelines


140-143: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Expand ATOF and ATIF on first use.

These niche acronyms are not widely understood. Spell out the repository’s full terms first, then use the abbreviations.

🤖 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 `@adapters/codex/README.md` around lines 140 - 143, Update the README passage
describing the Relay test to spell out the repository’s full terms for ATOF and
ATIF on their first occurrence, followed by each abbreviation in parentheses;
keep subsequent references concise and preserve the existing test coverage
description.

Source: Coding guidelines

🤖 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 `@tests/adapters/test_codex_adapter.py`:
- Around line 579-596: Extend
test_environment_rejects_non_string_runtime_telemetry_env or add a focused
parameterized test covering non-mapping runtime_context.telemetry values, such
as null, a string, or a list. Set codex_payload["runtime_context"]["telemetry"]
to each invalid value and assert adapter.child_environment raises
AdapterInputError with the expected telemetry validation message, covering the
new rejection branch.

---

Outside diff comments:
In `@adapters/codex/README.md`:
- Line 136: Update the FABRIC_TEST_NEMO_RELAY_COMMAND example in the README to
wrap the path placeholder in angle brackets, using <path/to/nemo-relay> instead
of the literal-looking /path/to/nemo-relay value.
- Around line 140-143: Update the README passage describing the Relay test to
spell out the repository’s full terms for ATOF and ATIF on their first
occurrence, followed by each abbreviation in parentheses; keep subsequent
references concise and preserve the existing test coverage description.
🪄 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: ASSERTIVE

Plan: Enterprise

Run ID: 874e4efd-a115-489e-a71a-c1add969f1b8

📥 Commits

Reviewing files that changed from the base of the PR and between 495a0aa and 41da96b.

📒 Files selected for processing (4)
  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
  • tests/adapters/test_codex_adapter.py
  • tests/e2e/test_codex.py
📜 Review details
🧰 Additional context used
📓 Path-based instructions (17)
**/*.{md,mdx,html}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Changes affecting public behavior, adapters, examples, or workspace structure must update the corresponding documentation; public API changes require updated SDK or API reference documentation.

Files:

  • adapters/codex/README.md
**/README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Update an adapter or example README.md when that adapter or example surface changes.

Files:

  • adapters/codex/README.md
**/*.{md,mdx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

For docs site changes, run just docs to regenerate Python and Rust API references and validate Fern configuration.

**/*.{md,mdx}: Verify that commands, package names, file paths, APIs, bindings, support claims, examples, and procedures match current NeMo Fabric behavior and repository layout.
Capitalize NVIDIA correctly and use terminology consistent with the current repository.
Format commands, code elements, expressions, file names, paths, and filenames as inline code where appropriate.
Use title case for technical-documentation headings.
Introduce code blocks, tables, and lists with complete lead-in sentences; use descriptive link text instead of raw URLs or generic labels such as here.
Write procedures as short, imperative, parallel steps, splitting long sequences into smaller tasks.
Prefer active voice, present tense, short sentences, plain English, consistent terminology, and after instead of once; use can for possibility rather than permission.

Files:

  • adapters/codex/README.md
**/*

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*: All source files must include the specified SPDX copyright and Apache-2.0 license header using the comment syntax appropriate to the file type.
Release tags must use raw Rust-compatible SemVer without a leading v, such as 0.1.0 or 0.1.0-rc.1.

**/*: Before implementing, explicitly state assumptions, surface ambiguity and tradeoffs, present multiple interpretations when relevant, and ask for clarification rather than silently deciding or proceeding when requirements are unclear.
Prefer the minimum code needed to solve the requested problem: avoid speculative features, unnecessary abstractions, unrequested flexibility, and handling of impossible scenarios; simplify overcomplicated solutions.
When editing existing code, make surgical changes only: do not modify unrelated code, comments, formatting, or pre-existing dead code; match the existing style, and remove only unused imports, variables, or functions introduced by your changes.
Define verifiable success criteria for each task, such as writing regression tests for bugs and invalid-input tests for validation, then verify the implementation against those criteria. For multi-step work, state a brief plan with a verification check for each step.

**/*: Keep pull request branch scope coherent and reviewable.
Run relevant tests under validate-change before opening or updating a pull request.
Format changed files with the language-native formatter.
Update documentation and examples for public behavior changes.
Update dependent maintainer or consumer guidance when code changes affect APIs, bindings, commands, paths, packaging guidance, or best practices.
Use Conventional Commit style for pull request titles: <type>: <concise imperative summary>, choosing the type from the actual change surface. Use fix only for user-facing or runtime product-code bug fixes.
A pull request body must include #### Overview, #### Details, #### Validation, #### Where should the reviewer start?, and `#### Related ...

Files:

  • adapters/codex/README.md
  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{html,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

HTML and Markdown files must use the specified SPDX header in an HTML comment.

Files:

  • adapters/codex/README.md
**/*.{md,rst}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Update documentation and examples in the same branch as the public API change.

Verify README and documentation entry points, package names, paths, examples, and public commands remain current after changes.

Files:

  • adapters/codex/README.md
**/*.{md,mdx,rst}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-guide.md)

**/*.{md,mdx,rst}: For NeMo Fabric documentation, verify technical claims against the current repository, public API, or documented command before reviewing style.
Always spell NVIDIA in all caps; do not use Nvidia, nvidia, or NV.
Format commands, code elements, expressions, package names, file names, and paths as inline code.
Use descriptive link text; avoid raw URLs and weak anchors such as here or read more.
Use title case consistently for technical documentation headings.
Introduce code blocks, lists, tables, and images with complete sentences.
Write procedures as imperative, parallel steps; split long procedures into smaller tasks.
Prefer active voice, present tense, short sentences, contractions, and plain English while preserving necessary technical precision.
Use can for possibility and reserve may for permission.
Use after for temporal relationships instead of once, and prefer refer to over see when directing readers to another resource.
Avoid culture-specific idioms, unnecessary Latinisms, jokes, and marketing exaggeration in technical documentation.
Spell out months in body text, avoid ordinal dates, and use clear time zones.
Spell out whole numbers from zero through nine unless they are technical values, parameters, versions, or UI values; use numerals for 10 or greater and commas in thousands.
Do not add trademark symbols to learning-oriented documentation unless the source, platform, or legal guidance explicitly requires them.
Do not replace precise technical terms with simpler words when doing so would lose precision.
Do not flag passive voice when the actor is unknown or the action is the important part.
Do not rewrite API names, package names, command flags, or code literals for style.

**/*.{md,mdx,rst}: Use consistent title case for technical-document headings and table headers; avoid quotation marks, ampersands, and exclamation marks in headings, while preserving official product, event, research, and whitepaper title ...

Files:

  • adapters/codex/README.md
**/*.{md,rst,txt,adoc}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-language-mechanics.md)

**/*.{md,rst,txt,adoc}: For technical documentation, use professional, active, conversational, engaging, precise, and plain-English prose. Prefer active voice, present tense, short sentences, and scannable paragraphs. Avoid casual or imprecise language, swearing, threats, insults, jokes, puns, culture-specific idioms, marketing exaggeration, and unsupported third-party comparisons.
Use can for possibility and reserve may for permission; use after for temporal order; use refer to for cross-references; prefer short direct sentences and specific verbs; avoid unnecessary please in technical documentation.
Prefer active voice when the actor matters. Passive voice is acceptable when the actor is unknown or irrelevant, when the action or result is the focus, or in programmer documentation.
Use natural contractions in conversational technical prose, but do not force them in formal legal copy, API references, or generated text.
Prefer simpler English over Latinisms: use for example or such as instead of e.g., and so on instead of etc., that is instead of i.e., compared to instead of vs., and by, through, or using instead of via. Use industry-standard terms such as in silico, in vitro, and in vivo when appropriate, and italicize them in running text.
Use that without commas for essential clauses, and which with commas for nonessential clauses.
Format dates and times clearly: spell out months in body text; use forms such as June 12, 2025; avoid numeric or ordinal dates; capitalize days; use 12-hour time when appropriate; include a space before a.m. or p.m.; use ET and PT for needed time zones; avoid 24/7; and prefer from 12:30 to 1:00 p.m. for prose ranges.
Format numbers consistently: spell out zero through nine in body text, use numerals for 10 or greater and for technical values, use commas in thousands, do not begin a sentence with a numeral, spell out ordinals, and use numerals consistently within a category wh...

Files:

  • adapters/codex/README.md
{adapters/**,examples/**}

⚙️ CodeRabbit configuration file

{adapters/**,examples/**}: Review adapter and example changes for command correctness, config/schema consistency, artifact handling, and compatibility with the public Fabric contracts.

Files:

  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.py

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.py: Python public APIs must use type annotations, and native Python binding declarations must remain synchronized with their Rust implementations.
Python files must begin with the specified # SPDX copyright and Apache-2.0 license header.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,py}: Use snake_case for Rust and Python functions and variables; use PascalCase for Rust types and Python classes.
Run tests for every language surface affected by a change. Changes touching the Rust core or public schemas require both Rust and Python test suites.
Public contract changes must keep native Python binding declarations synchronized with their Rust implementations.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py,pyi,json,yaml,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Determine and update every affected public surface, including the CLI, PyO3 bindings, Python SDK, type stubs, schemas, and adapter contract, so they remain in parity.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
tests/**/*.py

📄 CodeRabbit inference engine (.agents/skills/python-tests/SKILL.md)

tests/**/*.py: Use Pytest to run Python tests.
Do not add @pytest.mark.asyncio to tests; async tests are automatically detected by the async runner.
Do not add -> None return annotations to test functions.
When mocking a class, use unittest.mock.MagicMock or AsyncMock, supplying spec when necessary; do not define a new mock class.
Prefix mocked class names with mock, not fake.
Prefer pytest fixtures over helper methods.
Define shared fixtures in conftest.py rather than repeating them across test files.
Define fixtures using @pytest.fixture(name="<fixture_name>"[, scope="<scope>"]) and a <fixture_name>_fixture function; specify scope only when it is not function.
Prefer pytest.mark.parametrize over separate tests for different input types.
Use @pytest.mark.usefixtures when a fixture is needed but its return value is unused.
Use os.environ to modify environment variables in tests; do not use monkeypatch.setenv, because the autouse restore_environ_fixture in tests/conftest.py restores the environment after each test.
Avoid defensive programming in tests; access expected data directly so missing data raises a clear error instead of being silently tolerated.
Run focused tests with uv run pytest -k "<pattern>" and all tests with uv run pytest.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
**/*.{py,pyi}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When Python code or a Python-facing adapter changes, run just test-python.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py,pyi,toml}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When the PyO3 bridge or package metadata changes, run just build-python and cargo check -p fabric-python --locked.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{tests/**,python/tests/**}

⚙️ CodeRabbit configuration file

{tests/**,python/tests/**}: Tests should cover the behavior promised by the changed API surface, including error paths, lifecycle cleanup, and SDK/native parity where relevant.

Files:

  • tests/e2e/test_codex.py
  • tests/adapters/test_codex_adapter.py
tests/adapters/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When an adapter or integration changes, run its focused tests under tests/adapters, followed by just test-python.

Files:

  • tests/adapters/test_codex_adapter.py
🧠 Learnings (2)
📓 Common learnings
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-15T21:12:27.500Z
Learning: Update relevant entry-point documentation when public behavior changes, including README.md, docs/index.yml, package or crate READMEs, and adapter or integration READMEs.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-15T21:12:27.500Z
Learning: During documentation reviews, lead with actionable findings categorized as Must fix, Should fix, or Nice to have, and include the file path, line reference, current problem, rationale, and concrete rewrite or direction. If no issues are found, state that explicitly and mention residual validation risk.
📚 Learning: 2026-07-09T22:28:51.689Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 43
File: adapters/claude-sdk/src/nemo_fabric_adapters/claude_sdk/adapter.py:164-168
Timestamp: 2026-07-09T22:28:51.689Z
Learning: In the NeMo-Fabric adapters, treat path values used in Fabric adapter configuration (including logic like `_resolve_path` in adapter.py) as config-root-relative. Do not apply `Path.expanduser()` (or otherwise apply `~`/home or shell-style expansion), because it will make the resolved paths normalize inconsistently across adapters. Also, do not rely on or add any resolution behavior that uses `harness.settings.cwd` as an override point for these adapter paths—`harness.settings.cwd` is explicitly unsupported in this adapter context.

Applied to files:

  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
🧬 Code graph analysis (1)
tests/adapters/test_codex_adapter.py (1)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (4)
  • AdapterInputError (115-116)
  • save_thread_id (347-367)
  • run (893-903)
  • runtime_state_path (322-324)
🪛 ast-grep (0.44.1)
tests/adapters/test_codex_adapter.py

[info] 562-562: Do not hardcode temporary file or directory names
Context: "/tmp/relay.json"
Note: [CWE-377] Insecure Temporary File.

(hardcoded-tmp-file)


[info] 569-569: Do not hardcode temporary file or directory names
Context: "/tmp/parent-relay.json"
Note: [CWE-377] Insecure Temporary File.

(hardcoded-tmp-file)


[info] 574-574: Do not hardcode temporary file or directory names
Context: "/tmp/relay.json"
Note: [CWE-377] Insecure Temporary File.

(hardcoded-tmp-file)

🪛 Ruff (0.15.21)
tests/adapters/test_codex_adapter.py

[warning] 87-87: Missing return type annotation for private function mark_interrupted

Add return type annotation: None

(ANN202)


[warning] 111-111: Missing return type annotation for private function build_client

(ANN202)


[warning] 117-117: Missing return type annotation for private function close

Add return type annotation: None

(ANN202)


[warning] 120-120: Missing return type annotation for private function thread_start

(ANN202)


[warning] 120-120: Missing type annotation for **_kwargs

(ANN003)


[warning] 128-128: Missing return type annotation for private function thread_resume

(ANN202)


[warning] 128-128: Missing type annotation for **_kwargs

(ANN003)


[error] 151-151: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)


[warning] 480-480: Missing return type annotation for private function block

Add return type annotation: None

(ANN202)


[error] 551-551: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)


[error] 556-556: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)


[error] 563-563: Probable insecure usage of temporary file or directory: "/tmp/relay.json"

(S108)


[error] 570-570: Probable insecure usage of temporary file or directory: "/tmp/parent-relay.json"

(S108)


[error] 575-575: Probable insecure usage of temporary file or directory: "/tmp/relay.json"

(S108)


[warning] 594-594: Pattern passed to match= contains metacharacters but is neither escaped nor raw

(RUF043)

🔇 Additional comments (5)
tests/e2e/test_codex.py (1)

6-6: Use the Required Focused-Test Form.

The command still omits -k "<pattern>".

Source: Coding guidelines

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)

262-284: LGTM!

tests/adapters/test_codex_adapter.py (1)

4-14: LGTM!

Also applies to: 78-143, 146-206, 228-277, 280-313, 382-384, 415-493, 550-577

adapters/codex/README.md (2)

6-20: LGTM!

Also applies to: 47-61, 92-126


24-45: 🎯 Functional Correctness

API-key auth flow is already clear. The README says API-key login provisions the Codex credential store, requires the same CODEX_HOME for login and execution, and only forwards OPENAI_API_KEY into the SDK runtime.

			> Likely an incorrect or invalid review comment.

Comment thread tests/adapters/test_codex_adapter.py
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
…sdk-relay-cutover

Signed-off-by: Ajay Thorve <athorve@nvidia.com>

# Conflicts:
#	docs/index.yml
#	examples/code_review_agent/README.md
#	examples/code_review_agent/__init__.py
#	examples/code_review_agent/__main__.py
#	tests/python/test_code_review_example.py
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
Signed-off-by: Ajay Thorve <athorve@nvidia.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 6

Caution

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

⚠️ Outside diff range comments (3)
adapters/codex/README.md (1)

125-130: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Pin the Relay CLI installation to a tested 0.6.x release.

The documentation requires >=0.6.0,<0.7.0, but cargo install nemo-relay-cli selects an unbounded release. A future incompatible release—or one without the required zstd fix—can make the documented Relay setup fail. Pin the exact tested 0.6.x release containing the required fix, or document the corresponding source-install command.

As per coding guidelines, documentation examples must use current, reproducible package and build commands.

🤖 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 `@adapters/codex/README.md` around lines 125 - 130, Update the Relay CLI
installation example near the version requirement to use the exact tested 0.6.x
nemo-relay-cli release containing the zstd fix, or replace it with the
corresponding reproducible source-install command. Keep the documented
Fabric-compatible version range consistent with the pinned installation method.

Source: Coding guidelines

tests/adapters/test_codex_adapter.py (1)

358-397: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Test name promises "reuses one resolved executable" but never asserts it.

The test patches resolve_relay_command but never checks that it was called exactly once; it only asserts contract/write call args. As written, the test would still pass even if resolve_relay_command were invoked multiple times, so it doesn't actually verify the "one resolved executable" behavior the name and cohort summary claim.

♻️ Add the missing call-count assertion
     relay = adapter.prepare_codex_relay(codex_payload)

     assert relay is not None
     assert relay.gateway.executable == executable
     assert relay.gateway.url == "http://127.0.0.1:43210"
+    resolve.assert_called_once()
     contract.assert_called_once_with(executable)
🤖 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 `@tests/adapters/test_codex_adapter.py` around lines 358 - 397, Add an exact
call-count assertion for the mocked resolve_relay_command in
test_prepare_relay_reuses_one_resolved_executable, verifying it is called once
with the expected relay context or arguments used by prepare_codex_relay. Keep
the existing contract and write assertions unchanged.
adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

363-445: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Add tests for the missing subagents validation paths. tests/adapters/test_deepagents.py already covers graph_id/runnable; add cases for non-list subagents and non-mapping entries so the new AdapterConfigError branches stay covered.

🤖 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 `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py` around
lines 363 - 445, Add tests in the existing deepagents adapter test suite
covering _gated_subagents with a non-list subagents value and with a list
containing a non-mapping entry. Assert each case raises AdapterConfigError and
preserves the corresponding validation behavior and message.

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.

Inline comments:
In `@adapters/claude/src/nemo_fabric_adapters/claude/adapter.py`:
- Around line 745-751: Update the exception guard in the stream-close handler to
use the same failure predicate as normalize_result(), treating result.is_error
and result.subtype values beginning with "error_" as failed terminal results.
Preserve re-raising when no failed result is available, but log the swallowed
exception before calling normalize_result() so discarded diagnostics are
retained.

In `@adapters/codex/README.md`:
- Around line 163-168: Update the README test requirements description to say
that the LLM request content must be decoded, then list the model, token usage,
and expected agent response as additional ATIF prerequisites. Preserve the
surrounding SDK and Relay test behavior details.

In `@adapters/codex/src/nemo_fabric_adapters/codex/adapter.py`:
- Around line 555-563: Update sdk_config’s codex_bin path handling to remove
expanduser() and preserve config-root-relative resolution for all non-absolute
values. Resolve the raw configured path using the existing config_root(payload)
behavior, while keeping absolute paths unchanged.

In `@adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py`:
- Around line 45-61: Annotate the public RELAY_TOOL_HOOK_EVENTS constant with
dict[RelayHookAgent, frozenset[str]] or an equivalent immutable mapping type,
matching the existing annotation style used by RELAY_HOOK_EVENTS while
preserving its current event values.

In `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py`:
- Around line 210-246: Hoist ToolGateMiddleware out of _tool_gate_middleware and
define it once at module scope, with is_blocked and message supplied through its
constructor. Preserve the existing awrap_tool_call and wrap_tool_call blocking
behavior, then have _tool_gate_middleware instantiate and return the shared
class so exact-type middleware matching remains stable.

In `@tests/_utils/utils.py`:
- Around line 22-60: Add a type annotation to the output parameter of
assert_semantic_relay_artifacts, using the appropriate mapping type for the
relay artifact payload, and include the available trajectory or agent_messages
context as the second argument to the final assertion so failures provide
debugging details.

---

Outside diff comments:
In `@adapters/codex/README.md`:
- Around line 125-130: Update the Relay CLI installation example near the
version requirement to use the exact tested 0.6.x nemo-relay-cli release
containing the zstd fix, or replace it with the corresponding reproducible
source-install command. Keep the documented Fabric-compatible version range
consistent with the pinned installation method.

In `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py`:
- Around line 363-445: Add tests in the existing deepagents adapter test suite
covering _gated_subagents with a non-list subagents value and with a list
containing a non-mapping entry. Assert each case raises AdapterConfigError and
preserves the corresponding validation behavior and message.

In `@tests/adapters/test_codex_adapter.py`:
- Around line 358-397: Add an exact call-count assertion for the mocked
resolve_relay_command in test_prepare_relay_reuses_one_resolved_executable,
verifying it is called once with the expected relay context or arguments used by
prepare_codex_relay. Keep the existing contract and write assertions unchanged.
🪄 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: ASSERTIVE

Plan: Enterprise

Run ID: f4901c6b-a740-478a-a121-094e3cb738ea

📥 Commits

Reviewing files that changed from the base of the PR and between 9454d1d and 3addf38.

⛔ Files ignored due to path filters (2)
  • adapters/claude/uv.lock is excluded by !**/*.lock
  • uv.lock is excluded by !**/*.lock
📒 Files selected for processing (28)
  • ATTRIBUTIONS-Python.md
  • README.md
  • adapters/claude/README.md
  • adapters/claude/pyproject.toml
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • justfile
  • tests/_utils/utils.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_claude_adapter.py
  • tests/adapters/test_codex_adapter.py
  • tests/e2e/test_claude.py
  • tests/e2e/test_codex.py
  • tests/python/test_code_review_example.py
📜 Review details
⏰ Context from checks skipped due to timeout. (4)
  • GitHub Check: Test (Python 3.13, arm64)
  • GitHub Check: Test (Python 3.12, x86_64)
  • GitHub Check: Test (Python 3.13, x86_64)
  • GitHub Check: Test (Python 3.11, x86_64)
🧰 Additional context used
📓 Path-based instructions (36)
**/*

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*: All source files must include the specified SPDX copyright and Apache-2.0 license header using the comment syntax appropriate to the file type.
Release tags must use raw Rust-compatible SemVer without a leading v, such as 0.1.0 or 0.1.0-rc.1.

**/*: Before implementing, explicitly state assumptions, surface ambiguity and tradeoffs, present multiple interpretations when relevant, and ask for clarification rather than silently deciding or proceeding when requirements are unclear.
Prefer the minimum code needed to solve the requested problem: avoid speculative features, unnecessary abstractions, unrequested flexibility, and handling of impossible scenarios; simplify overcomplicated solutions.
When editing existing code, make surgical changes only: do not modify unrelated code, comments, formatting, or pre-existing dead code; match the existing style, and remove only unused imports, variables, or functions introduced by your changes.
Define verifiable success criteria for each task, such as writing regression tests for bugs and invalid-input tests for validation, then verify the implementation against those criteria. For multi-step work, state a brief plan with a verification check for each step.

**/*: Keep pull request branch scope coherent and reviewable.
Run relevant tests under validate-change before opening or updating a pull request.
Format changed files with the language-native formatter.
Update documentation and examples for public behavior changes.
Update dependent maintainer or consumer guidance when code changes affect APIs, bindings, commands, paths, packaging guidance, or best practices.
Use Conventional Commit style for pull request titles: <type>: <concise imperative summary>, choosing the type from the actual change surface. Use fix only for user-facing or runtime product-code bug fixes.
A pull request body must include #### Overview, #### Details, #### Validation, #### Where should the reviewer start?, and `#### Related ...

Files:

  • docs/index.yml
  • justfile
  • adapters/claude/pyproject.toml
  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • adapters/claude/README.md
  • crates/fabric-core/src/config.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • ATTRIBUTIONS-Python.md
  • tests/_utils/utils.py
  • adapters/codex/README.md
  • docs/integrations/codex.mdx
  • tests/python/test_code_review_example.py
  • README.md
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{toml,yaml,yml,sh,bash}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

TOML, YAML, and shell files must use the specified SPDX header with # comments.

Files:

  • docs/index.yml
  • adapters/claude/pyproject.toml
**/*.{rs,py,pyi,json,yaml,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Determine and update every affected public surface, including the CLI, PyO3 bindings, Python SDK, type stubs, schemas, and adapter contract, so they remain in parity.

Files:

  • docs/index.yml
  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/config.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{README.md,docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Keep package names, repository references, and build commands current in documentation and examples.

Files:

  • docs/index.yml
  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
  • README.md
{README.md,docs/index.yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update README.md or docs/index.yml when documentation entry points or example reading paths change.

Files:

  • docs/index.yml
  • README.md
{docs/**/*.{md,mdx,yml},examples/**/*.{md,mdx,yml}}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Update relevant getting-started, reference, adapter, and example documentation when the corresponding examples or adapters change.

Files:

  • docs/index.yml
  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
docs/**/*.{md,mdx,yml}

📄 CodeRabbit inference engine (.agents/skills/contribute-docs/SKILL.md)

Run just docs when the documentation site changes.

Files:

  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Use the current install, import, build, test, clean, and documentation commands consistently in documentation, examples, CI workflows, and just recipes.

Files:

  • docs/index.yml
  • justfile
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
{docs/**/*,.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

Reflect public packaging changes in release-facing documentation and examples.

Files:

  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
docs/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

For documentation or examples changes, run just docs when practical and verify documented commands against the current repository.

Files:

  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
docs/index.yml

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/SKILL.md)

Keep docs/index.yml aligned with current public documentation entry points and repository behavior.

Files:

  • docs/index.yml
{docs/**,README.md,AGENTS.md}

⚙️ CodeRabbit configuration file

{docs/**,README.md,AGENTS.md}: Review documentation for technical accuracy against the current API, command correctness, and consistency with generated schemas.

Files:

  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
  • README.md
{.github/workflows/ci_python.yml,.github/workflows/ci_rust.yml,justfile,pyproject.toml,python/pyproject.toml,Cargo.toml}

📄 CodeRabbit inference engine (.agents/skills/maintain-packaging/SKILL.md)

CI workflows must reference the same package names and commands used by local build and installation workflows.

Files:

  • justfile
justfile

📄 CodeRabbit inference engine (.agents/skills/small-fix/SKILL.md)

Use or update the repository’s justfile when it provides the focused validation path for a small Fabric bug fix.

The set-version recipe must update source metadata and then run just lock-python.

Files:

  • justfile
**/*.{rs,toml}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,toml}: Rust code must be formatted with cargo fmt --all; formatting can be checked with cargo fmt --all -- --check, and Rust workspaces must compile with cargo check --workspace --locked.
Rust files must begin with the specified // SPDX copyright and Apache-2.0 license header.

When Rust code or Rust project configuration changes, run cargo fmt --all -- --check and just test-rust.

Files:

  • adapters/claude/pyproject.toml
  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
**/pyproject.toml

📄 CodeRabbit inference engine (.agents/skills/update-project-version/SKILL.md)

Run just build-python to verify that all Python package metadata resolves.

Files:

  • adapters/claude/pyproject.toml
**/*.{rs,py,pyi,toml}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When the PyO3 bridge or package metadata changes, run just build-python and cargo check -p fabric-python --locked.

Files:

  • adapters/claude/pyproject.toml
  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/config.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
{adapters/**,examples/**}

⚙️ CodeRabbit configuration file

{adapters/**,examples/**}: Review adapter and example changes for command correctness, config/schema consistency, artifact handling, and compatibility with the public Fabric contracts.

Files:

  • adapters/claude/pyproject.toml
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • adapters/claude/README.md
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{md,mdx,html}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Changes affecting public behavior, adapters, examples, or workspace structure must update the corresponding documentation; public API changes require updated SDK or API reference documentation.

Files:

  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • docs/integrations/codex.mdx
  • README.md
**/README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

Update an adapter or example README.md when that adapter or example surface changes.

Files:

  • examples/code_review_agent/README.md
  • adapters/claude/README.md
  • adapters/codex/README.md
  • README.md
**/*.{md,mdx}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

For docs site changes, run just docs to regenerate Python and Rust API references and validate Fern configuration.

**/*.{md,mdx}: Prioritize factual accuracy: commands, package names, APIs, file paths, bindings, support claims, examples, and procedures must match current NeMo Fabric behavior and repository layout.
Update relevant entry-point documentation when public behavior changes, including README.md, docs/index.yml, package or crate READMEs, and adapter or integration READMEs.
Capitalize NVIDIA correctly and use current repository terminology consistently.
Format commands, code elements, expressions, file names, and paths as inline code where appropriate.
Use title case for headings in technical documentation.
Introduce code blocks, tables, and lists with complete lead-in sentences.
Use descriptive link text instead of raw URLs or generic labels such as here.
Prefer active voice, present tense, short sentences, plain English, and precise wording; use can for possibility and may for permission.
Write procedures as imperative, parallel, scannable steps and split overly long sequences into smaller tasks.
Prefer after over once when expressing temporal order, and avoid ambiguous numeric or ordinal dates in body text.
Ensure examples use current APIs and build commands, and introduce code blocks with full sentences.

Files:

  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • docs/integrations/codex.mdx
  • README.md
**/*.{html,md}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

HTML and Markdown files must use the specified SPDX header in an HTML comment.

Files:

  • examples/code_review_agent/README.md
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • README.md
**/*.{md,rst}

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Update documentation and examples in the same branch as the public API change.

Verify README and documentation entry points, package names, paths, examples, and public commands remain current after changes.

Files:

  • examples/code_review_agent/README.md
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • README.md
**/*.{md,mdx,rst}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-guide.md)

**/*.{md,mdx,rst}: For NeMo Fabric documentation, verify technical claims against the current repository, public API, or documented command before reviewing style.
Always spell NVIDIA in all caps; do not use Nvidia, nvidia, or NV.
Format commands, code elements, expressions, package names, file names, and paths as inline code.
Use descriptive link text; avoid raw URLs and weak anchors such as here or read more.
Use title case consistently for technical documentation headings.
Introduce code blocks, lists, tables, and images with complete sentences.
Write procedures as imperative, parallel steps; split long procedures into smaller tasks.
Prefer active voice, present tense, short sentences, contractions, and plain English while preserving necessary technical precision.
Use can for possibility and reserve may for permission.
Use after for temporal relationships instead of once, and prefer refer to over see when directing readers to another resource.
Avoid culture-specific idioms, unnecessary Latinisms, jokes, and marketing exaggeration in technical documentation.
Spell out months in body text, avoid ordinal dates, and use clear time zones.
Spell out whole numbers from zero through nine unless they are technical values, parameters, versions, or UI values; use numerals for 10 or greater and commas in thousands.
Do not add trademark symbols to learning-oriented documentation unless the source, platform, or legal guidance explicitly requires them.
Do not replace precise technical terms with simpler words when doing so would lose precision.
Do not flag passive voice when the actor is unknown or the action is the important part.
Do not rewrite API names, package names, command flags, or code literals for style.

**/*.{md,mdx,rst}: Use consistent title case for technical-document headings and table headers; avoid quotation marks, ampersands, and exclamation marks in headings, while preserving official product, event, research, and whitepaper title ...

Files:

  • examples/code_review_agent/README.md
  • docs/integrations/claude.mdx
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • docs/integrations/codex.mdx
  • README.md
**/*.{md,rst,txt,adoc}

📄 CodeRabbit inference engine (.agents/skills/review-doc-style/assets/nvidia-style-language-mechanics.md)

**/*.{md,rst,txt,adoc}: For technical documentation, use professional, active, conversational, engaging, precise, and plain-English prose. Prefer active voice, present tense, short sentences, and scannable paragraphs. Avoid casual or imprecise language, swearing, threats, insults, jokes, puns, culture-specific idioms, marketing exaggeration, and unsupported third-party comparisons.
Use can for possibility and reserve may for permission; use after for temporal order; use refer to for cross-references; prefer short direct sentences and specific verbs; avoid unnecessary please in technical documentation.
Prefer active voice when the actor matters. Passive voice is acceptable when the actor is unknown or irrelevant, when the action or result is the focus, or in programmer documentation.
Use natural contractions in conversational technical prose, but do not force them in formal legal copy, API references, or generated text.
Prefer simpler English over Latinisms: use for example or such as instead of e.g., and so on instead of etc., that is instead of i.e., compared to instead of vs., and by, through, or using instead of via. Use industry-standard terms such as in silico, in vitro, and in vivo when appropriate, and italicize them in running text.
Use that without commas for essential clauses, and which with commas for nonessential clauses.
Format dates and times clearly: spell out months in body text; use forms such as June 12, 2025; avoid numeric or ordinal dates; capitalize days; use 12-hour time when appropriate; include a space before a.m. or p.m.; use ET and PT for needed time zones; avoid 24/7; and prefer from 12:30 to 1:00 p.m. for prose ranges.
Format numbers consistently: spell out zero through nine in body text, use numerals for 10 or greater and for technical values, use commas in thousands, do not begin a sentence with a numeral, spell out ordinals, and use numerals consistently within a category wh...

Files:

  • examples/code_review_agent/README.md
  • adapters/claude/README.md
  • ATTRIBUTIONS-Python.md
  • adapters/codex/README.md
  • README.md
**/*.mdx

📄 CodeRabbit inference engine (CONTRIBUTING.md)

MDX files must use the specified SPDX header in a JSX comment.

In MDX files, use JSX comment delimiters ({/* and */}) for top-of-file comments, including SPDX headers; do not use HTML comments.

Use {/* ... */} delimiters for top-of-file SPDX comments; do not use HTML comment delimiters.

Files:

  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
**/*.py

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.py: Python public APIs must use type annotations, and native Python binding declarations must remain synchronized with their Rust implementations.
Python files must begin with the specified # SPDX copyright and Apache-2.0 license header.

Files:

  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{rs,py}

📄 CodeRabbit inference engine (CONTRIBUTING.md)

**/*.{rs,py}: Use snake_case for Rust and Python functions and variables; use PascalCase for Rust types and Python classes.
Run tests for every language surface affected by a change. Changes touching the Rust core or public schemas require both Rust and Python test suites.
Public contract changes must keep native Python binding declarations synchronized with their Rust implementations.

Files:

  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • crates/fabric-core/src/config.rs
  • tests/adapters/test_adapters_common_relay_hooks.py
  • crates/fabric-core/src/doctor.rs
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
**/*.{py,pyi}

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When Python code or a Python-facing adapter changes, run just test-python.

Files:

  • examples/code_review_agent/__init__.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • examples/code_review_agent/config.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • tests/e2e/test_claude.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • examples/code_review_agent/__main__.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
tests/**/*.py

📄 CodeRabbit inference engine (.agents/skills/python-tests/SKILL.md)

tests/**/*.py: Use Pytest to run Python tests.
Do not add @pytest.mark.asyncio to tests; async tests are automatically detected by the async runner.
Do not add -> None return annotations to test functions.
When mocking a class, use unittest.mock.MagicMock or AsyncMock, supplying spec when necessary; do not define a new mock class.
Prefix mocked class names with mock, not fake.
Prefer pytest fixtures over helper methods.
Define shared fixtures in conftest.py rather than repeating them across test files.
Define fixtures using @pytest.fixture(name="<fixture_name>"[, scope="<scope>"]) and a <fixture_name>_fixture function; specify scope only when it is not function.
Prefer pytest.mark.parametrize over separate tests for different input types.
Use @pytest.mark.usefixtures when a fixture is needed but its return value is unused.
Use os.environ to modify environment variables in tests; do not use monkeypatch.setenv, because the autouse restore_environ_fixture in tests/conftest.py restores the environment after each test.
Avoid defensive programming in tests; access expected data directly so missing data raises a clear error instead of being silently tolerated.
Run focused tests with uv run pytest -k "<pattern>" and all tests with uv run pytest.

Files:

  • tests/adapters/test_adapters_common_relay_gateway.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/e2e/test_claude.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
tests/adapters/**/*

📄 CodeRabbit inference engine (.agents/skills/validate-change/SKILL.md)

When an adapter or integration changes, run its focused tests under tests/adapters, followed by just test-python.

Files:

  • tests/adapters/test_adapters_common_relay_gateway.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_claude_adapter.py
  • tests/adapters/test_codex_adapter.py
{tests/**,python/tests/**}

⚙️ CodeRabbit configuration file

{tests/**,python/tests/**}: Tests should cover the behavior promised by the changed API surface, including error paths, lifecycle cleanup, and SDK/native parity where relevant.

Files:

  • tests/adapters/test_adapters_common_relay_gateway.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/e2e/test_claude.py
  • tests/adapters/test_claude_adapter.py
  • tests/e2e/test_codex.py
  • tests/_utils/utils.py
  • tests/python/test_code_review_example.py
  • tests/adapters/test_codex_adapter.py
**/*.rs

📄 CodeRabbit inference engine (.agents/skills/contribute-api/SKILL.md)

Implement new runtime or binding behavior in the shared Rust core first.

For any Rust change, run just test-rust and cargo fmt --all -- --check.

Run cargo check --workspace --locked after version changes.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
crates/fabric-core/**/*

📄 CodeRabbit inference engine (.agents/skills/prepare-pr/SKILL.md)

For changes under crates/fabric-core, run both the Rust and Python test suites.

When crates/fabric-core changes in a way exposed through Python, run both the Rust and Python test suites.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
crates/fabric-core/src/**/*.rs

⚙️ CodeRabbit configuration file

crates/fabric-core/src/**/*.rs: Review the Rust core for runtime lifecycle correctness, handle validation, capability routing accuracy, schema stability, and error semantics.
Public API changes should match committed schemas, tests, and documentation.

Files:

  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
README.md

📄 CodeRabbit inference engine (CONTRIBUTING.md)

The root README.md must reflect the current workspace, supported adapters, and top-level documentation.

Update README.md when a small Fabric bug fix changes public behavior.

Files:

  • README.md
🧠 Learnings (2)
📓 Common learnings
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-16T08:17:37.873Z
Learning: During documentation reviews, report findings in severity order under `Must fix`, `Should fix`, and `Nice to have`; include the file path, line reference, current problem, rationale, and a concrete rewrite or direction.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-16T08:17:37.873Z
Learning: When no issues are found, state that explicitly and mention residual risks, such as commands or examples that were not executed.
Learnt from: CR
Repo: NVIDIA/NeMo-Fabric

Timestamp: 2026-07-16T08:17:37.873Z
Learning: Use `karpathy-guidelines` alongside this guidance for implementation or review work; keep changes scoped, surface assumptions, and define focused validation before editing.
📚 Learning: 2026-07-09T22:28:51.689Z
Learnt from: AjayThorve
Repo: NVIDIA/NeMo-Fabric PR: 43
File: adapters/claude-sdk/src/nemo_fabric_adapters/claude_sdk/adapter.py:164-168
Timestamp: 2026-07-09T22:28:51.689Z
Learning: In the NeMo-Fabric adapters, treat path values used in Fabric adapter configuration (including logic like `_resolve_path` in adapter.py) as config-root-relative. Do not apply `Path.expanduser()` (or otherwise apply `~`/home or shell-style expansion), because it will make the resolved paths normalize inconsistently across adapters. Also, do not rely on or add any resolution behavior that uses `harness.settings.cwd` as an override point for these adapter paths—`harness.settings.cwd` is explicitly unsupported in this adapter context.

Applied to files:

  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
🧬 Code graph analysis (10)
tests/adapters/test_adapters_common_relay_gateway.py (1)
adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (1)
  • RelayGatewayError (28-29)
adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)
adapters/common/src/nemo_fabric_adapters/common/utils.py (1)
  • blocked_tools (173-175)
examples/code_review_agent/config.py (1)
python/src/nemo_fabric/models.py (2)
  • remove_skill_path (473-480)
  • remove_mcp_server (456-463)
crates/fabric-core/src/config.rs (1)
adapters/common/src/nemo_fabric_adapters/common/utils.py (1)
  • blocked_tools (173-175)
crates/fabric-core/src/doctor.rs (1)
crates/fabric-core/src/config.rs (5)
  • RunPlan (1838-1870)
  • CapabilityTarget (1997-2004)
  • CapabilityRoute (1971-1980)
  • resolve_run_plan (1183-1186)
  • CapabilityKind (1985-1992)
adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (2)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)
  • render_relay_hooks (544-544)
adapters/claude/src/nemo_fabric_adapters/claude/adapter.py (1)
  • render_relay_hooks (361-361)
tests/e2e/test_codex.py (1)
examples/code_review_agent/config.py (2)
  • codex_config (103-128)
  • with_relay (227-249)
adapters/claude/src/nemo_fabric_adapters/claude/adapter.py (1)
adapters/common/src/nemo_fabric_adapters/common/utils.py (4)
  • load_relay_plugin_config (210-234)
  • load_payload (74-80)
  • write_relay_configs (501-538)
  • blocked_tools (173-175)
tests/adapters/test_codex_adapter.py (1)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)
  • run (901-911)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)
adapters/common/src/nemo_fabric_adapters/common/utils.py (3)
  • load_relay_plugin_config (210-234)
  • write_relay_configs (501-538)
  • config_root (66-67)
🪛 ast-grep (0.44.1)
tests/adapters/test_claude_adapter.py

[info] 753-753: use jsonify instead of json.dumps for JSON output
Context: json.dumps(output)
Note: [CWE-116] Improper Encoding or Escaping of Output.

(use-jsonify)

🪛 LanguageTool
adapters/codex/README.md

[style] ~167-~167: The double modal “requires decoded” is nonstandard (only accepted in certain dialects). Consider “to be decoded”.
Context: .... The semantic regression also requires decoded LLM request content, a model, token usa...

(NEEDS_FIXED)

🪛 Ruff (0.15.21)
tests/adapters/test_adapters_common_relay_gateway.py

[warning] 82-82: Pattern passed to match= contains metacharacters but is neither escaped nor raw

(RUF043)

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py

[warning] 72-72: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in is_blocked

(ANN401)


[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in message

(ANN401)


[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in _tool_gate_middleware

(ANN401)


[warning] 218-218: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 218-218: Dynamically typed expressions (typing.Any) are disallowed in _blocked

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in handler

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in awrap_tool_call

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in handler

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in wrap_tool_call

(ANN401)


[warning] 240-240: Dynamically typed expressions (typing.Any) are disallowed in blocked_tools_middleware

(ANN401)


[warning] 286-286: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 363-363: Dynamically typed expressions (typing.Any) are disallowed in model

(ANN401)


[warning] 420-420: Dynamically typed expressions (typing.Any) are disallowed in subagents

(ANN401)


[warning] 426-428: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 433-433: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 436-436: Avoid specifying long messages outside the exception class

(TRY003)


[warning] 438-438: Avoid specifying long messages outside the exception class

(TRY003)

adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py

[warning] 94-98: Avoid specifying long messages outside the exception class

(TRY003)

tests/adapters/test_claude_adapter.py

[warning] 731-731: Missing return type annotation for private function query_error_result

(ANN202)


[warning] 731-731: Missing type annotation for **_

(ANN003)


[warning] 741-741: Avoid specifying long messages outside the exception class

(TRY003)


[error] 839-839: Possible hardcoded password assigned to: "FABRIC_UNRELATED_SECRET"

(S105)

tests/e2e/test_codex.py

[warning] 20-20: Missing return type annotation for private function _select_codex_runtime

(ANN202)

adapters/claude/src/nemo_fabric_adapters/claude/adapter.py

[warning] 829-829: Do not catch blind exception: Exception

(BLE001)

🔇 Additional comments (31)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)

482-490: LGTM!

Also applies to: 532-551

adapters/codex/README.md (1)

51-56: LGTM!

Also applies to: 86-90, 102-123, 132-146, 150-162

tests/adapters/test_adapters_common_relay_hooks.py (1)

49-73: LGTM!

tests/python/test_code_review_example.py (1)

15-16: LGTM!

Also applies to: 29-53, 86-100

crates/fabric-core/src/config.rs (2)

2066-2110: LGTM!

Also applies to: 2329-2373, 2657-2795


55-101: 🗄️ Data Integrity & Integration

Tool contract surfaces are synchronized. ToolsConfig, ToolsPlan, and tools.blocked are present across the Rust core, schemas, Python SDK, adapter docs, and contract tests.

crates/fabric-core/src/doctor.rs (1)

14-15: LGTM!

Also applies to: 183-203, 477-480, 538-564, 595-613

adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)

42-49: LGTM!

Also applies to: 72-92, 99-99


23-24: 🎯 Functional Correctness

The version pin is for the Python package, not the CLI
nemo-relay~=0.5.0 is the importable package; this check applies to the separate external executable, and the repo already targets a 0.6.x CLI.

			> Likely an incorrect or invalid review comment.
adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (1)

15-44: LGTM!

Also applies to: 75-75, 85-85

justfile (1)

94-129: LGTM!

Also applies to: 196-196, 328-331, 355-373

examples/code_review_agent/config.py (1)

157-193: LGTM!

examples/code_review_agent/__init__.py (1)

9-9: LGTM!

Also applies to: 21-25

examples/code_review_agent/__main__.py (1)

17-17: LGTM!

Also applies to: 24-27

tests/adapters/test_codex_adapter.py (1)

195-397: LGTM!

tests/adapters/test_adapters_common_relay_gateway.py (1)

48-99: LGTM! Renamed tests correctly track the relay_cli_contract rename and match the RelayCliContract version/observability-version contract in relay_gateway.py.

tests/e2e/test_codex.py (1)

1-128: LGTM!

docs/index.yml (1)

17-18: LGTM!

docs/integrations/codex.mdx (3)

1-125: Otherwise, the doc is well-organized, uses inline code formatting for commands/settings, and its Relay version-range claim is consistent with the enforced 0.6.00.7.0 range in relay_gateway.py tests.


97-121: 🎯 Functional Correctness

No issue with these helper names The examples call with_native_otel and with_relay_openinference, and both are defined in examples/code_review_agent/config.py.

			> Likely an incorrect or invalid review comment.

83-96: 🎯 Functional Correctness

Use a resolvable reference for NeMo Relay PR #452.
openai-codex-cli-bin==0.137.0a4 is the pin in adapters/codex/pyproject.toml, but NeMo Relay PR #452`` is not a stable public reference. Link a commit, release tag, or another resolvable target readers can open.

examples/code_review_agent/README.md (1)

62-70: LGTM! Consistent with the Codex SDK adapter rename and the 0.6.x Relay CLI requirement documented elsewhere in this PR.

README.md (1)

160-161: LGTM!

Also applies to: 195-195

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

72-72: LGTM! Formatting-only line changes; no logic change.

Also applies to: 129-129, 286-286, 323-323, 333-333, 397-397

ATTRIBUTIONS-Python.md (1)

1284-1313: LGTM!

adapters/claude/README.md (1)

12-15: LGTM! Version pin, Relay CLI range, tools.blocked mapping, and test documentation all match the corresponding adapter/test code changes.

Also applies to: 47-48, 74-92, 124-181, 211-229

adapters/claude/pyproject.toml (1)

29-29: LGTM!

adapters/claude/src/nemo_fabric_adapters/claude/adapter.py (1)

83-83: LGTM! USER forwarding, the relay_cli_contract-based observability version lookup (consistent with the Codex adapter's identical pattern), and the tools=None/disallowed_tools=common_utils.blocked_tools(payload) mapping are all correct and covered by tests.

Also applies to: 393-398, 495-497

tests/adapters/test_claude_adapter.py (1)

213-221: LGTM! New/updated tests correctly cover the relay_cli_contract migration, tools.blockeddisallowed_tools mapping, the SDK stream-close recovery path, and USER env forwarding.

Also applies to: 288-297, 334-340, 727-756, 853-862

tests/e2e/test_claude.py (1)

14-14: LGTM!

Also applies to: 97-105, 266-269

docs/integrations/claude.mdx (1)

1-100: LGTM! Content is technically accurate (SDK pin, Relay CLI version range) and follows the MDX/SPDX and documentation style guidelines.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Caution

Inline review comments failed to post. This is likely due to GitHub's internal server error or limits when posting large numbers of comments. If you are seeing this consistently it is likely a permissions issue. Please check "Moderation" -> "Code review limits" under your organization settings.

Actionable comments posted: 6

Caution

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

⚠️ Outside diff range comments (3)
adapters/codex/README.md (1)

125-130: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Pin the Relay CLI installation to a tested 0.6.x release.

The documentation requires >=0.6.0,<0.7.0, but cargo install nemo-relay-cli selects an unbounded release. A future incompatible release—or one without the required zstd fix—can make the documented Relay setup fail. Pin the exact tested 0.6.x release containing the required fix, or document the corresponding source-install command.

As per coding guidelines, documentation examples must use current, reproducible package and build commands.

🤖 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 `@adapters/codex/README.md` around lines 125 - 130, Update the Relay CLI
installation example near the version requirement to use the exact tested 0.6.x
nemo-relay-cli release containing the zstd fix, or replace it with the
corresponding reproducible source-install command. Keep the documented
Fabric-compatible version range consistent with the pinned installation method.

Source: Coding guidelines

tests/adapters/test_codex_adapter.py (1)

358-397: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Test name promises "reuses one resolved executable" but never asserts it.

The test patches resolve_relay_command but never checks that it was called exactly once; it only asserts contract/write call args. As written, the test would still pass even if resolve_relay_command were invoked multiple times, so it doesn't actually verify the "one resolved executable" behavior the name and cohort summary claim.

♻️ Add the missing call-count assertion
     relay = adapter.prepare_codex_relay(codex_payload)

     assert relay is not None
     assert relay.gateway.executable == executable
     assert relay.gateway.url == "http://127.0.0.1:43210"
+    resolve.assert_called_once()
     contract.assert_called_once_with(executable)
🤖 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 `@tests/adapters/test_codex_adapter.py` around lines 358 - 397, Add an exact
call-count assertion for the mocked resolve_relay_command in
test_prepare_relay_reuses_one_resolved_executable, verifying it is called once
with the expected relay context or arguments used by prepare_codex_relay. Keep
the existing contract and write assertions unchanged.
adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

363-445: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

Add tests for the missing subagents validation paths. tests/adapters/test_deepagents.py already covers graph_id/runnable; add cases for non-list subagents and non-mapping entries so the new AdapterConfigError branches stay covered.

🤖 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 `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py` around
lines 363 - 445, Add tests in the existing deepagents adapter test suite
covering _gated_subagents with a non-list subagents value and with a list
containing a non-mapping entry. Assert each case raises AdapterConfigError and
preserves the corresponding validation behavior and message.

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.

Inline comments:
In `@adapters/claude/src/nemo_fabric_adapters/claude/adapter.py`:
- Around line 745-751: Update the exception guard in the stream-close handler to
use the same failure predicate as normalize_result(), treating result.is_error
and result.subtype values beginning with "error_" as failed terminal results.
Preserve re-raising when no failed result is available, but log the swallowed
exception before calling normalize_result() so discarded diagnostics are
retained.

In `@adapters/codex/README.md`:
- Around line 163-168: Update the README test requirements description to say
that the LLM request content must be decoded, then list the model, token usage,
and expected agent response as additional ATIF prerequisites. Preserve the
surrounding SDK and Relay test behavior details.

In `@adapters/codex/src/nemo_fabric_adapters/codex/adapter.py`:
- Around line 555-563: Update sdk_config’s codex_bin path handling to remove
expanduser() and preserve config-root-relative resolution for all non-absolute
values. Resolve the raw configured path using the existing config_root(payload)
behavior, while keeping absolute paths unchanged.

In `@adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py`:
- Around line 45-61: Annotate the public RELAY_TOOL_HOOK_EVENTS constant with
dict[RelayHookAgent, frozenset[str]] or an equivalent immutable mapping type,
matching the existing annotation style used by RELAY_HOOK_EVENTS while
preserving its current event values.

In `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py`:
- Around line 210-246: Hoist ToolGateMiddleware out of _tool_gate_middleware and
define it once at module scope, with is_blocked and message supplied through its
constructor. Preserve the existing awrap_tool_call and wrap_tool_call blocking
behavior, then have _tool_gate_middleware instantiate and return the shared
class so exact-type middleware matching remains stable.

In `@tests/_utils/utils.py`:
- Around line 22-60: Add a type annotation to the output parameter of
assert_semantic_relay_artifacts, using the appropriate mapping type for the
relay artifact payload, and include the available trajectory or agent_messages
context as the second argument to the final assertion so failures provide
debugging details.

---

Outside diff comments:
In `@adapters/codex/README.md`:
- Around line 125-130: Update the Relay CLI installation example near the
version requirement to use the exact tested 0.6.x nemo-relay-cli release
containing the zstd fix, or replace it with the corresponding reproducible
source-install command. Keep the documented Fabric-compatible version range
consistent with the pinned installation method.

In `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py`:
- Around line 363-445: Add tests in the existing deepagents adapter test suite
covering _gated_subagents with a non-list subagents value and with a list
containing a non-mapping entry. Assert each case raises AdapterConfigError and
preserves the corresponding validation behavior and message.

In `@tests/adapters/test_codex_adapter.py`:
- Around line 358-397: Add an exact call-count assertion for the mocked
resolve_relay_command in test_prepare_relay_reuses_one_resolved_executable,
verifying it is called once with the expected relay context or arguments used by
prepare_codex_relay. Keep the existing contract and write assertions unchanged.
🪄 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: ASSERTIVE

Plan: Enterprise

Run ID: f4901c6b-a740-478a-a121-094e3cb738ea

📥 Commits

Reviewing files that changed from the base of the PR and between 9454d1d and 3addf38.

⛔ Files ignored due to path filters (2)
  • adapters/claude/uv.lock is excluded by !**/*.lock
  • uv.lock is excluded by !**/*.lock
📒 Files selected for processing (28)
  • ATTRIBUTIONS-Python.md
  • README.md
  • adapters/claude/README.md
  • adapters/claude/pyproject.toml
  • adapters/claude/src/nemo_fabric_adapters/claude/adapter.py
  • adapters/codex/README.md
  • adapters/codex/src/nemo_fabric_adapters/codex/adapter.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py
  • adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py
  • adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py
  • crates/fabric-core/src/config.rs
  • crates/fabric-core/src/doctor.rs
  • docs/index.yml
  • docs/integrations/claude.mdx
  • docs/integrations/codex.mdx
  • examples/code_review_agent/README.md
  • examples/code_review_agent/__init__.py
  • examples/code_review_agent/__main__.py
  • examples/code_review_agent/config.py
  • justfile
  • tests/_utils/utils.py
  • tests/adapters/test_adapters_common_relay_gateway.py
  • tests/adapters/test_adapters_common_relay_hooks.py
  • tests/adapters/test_claude_adapter.py
  • tests/adapters/test_codex_adapter.py
  • tests/e2e/test_claude.py
  • tests/e2e/test_codex.py
  • tests/python/test_code_review_example.py
📜 Review details
🔇 Additional comments (31)
adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)

482-490: LGTM!

Also applies to: 532-551

adapters/codex/README.md (1)

51-56: LGTM!

Also applies to: 86-90, 102-123, 132-146, 150-162

tests/adapters/test_adapters_common_relay_hooks.py (1)

49-73: LGTM!

tests/python/test_code_review_example.py (1)

15-16: LGTM!

Also applies to: 29-53, 86-100

crates/fabric-core/src/config.rs (2)

2066-2110: LGTM!

Also applies to: 2329-2373, 2657-2795


55-101: 🗄️ Data Integrity & Integration

Tool contract surfaces are synchronized. ToolsConfig, ToolsPlan, and tools.blocked are present across the Rust core, schemas, Python SDK, adapter docs, and contract tests.

crates/fabric-core/src/doctor.rs (1)

14-15: LGTM!

Also applies to: 183-203, 477-480, 538-564, 595-613

adapters/common/src/nemo_fabric_adapters/common/relay_gateway.py (2)

42-49: LGTM!

Also applies to: 72-92, 99-99


23-24: 🎯 Functional Correctness

The version pin is for the Python package, not the CLI
nemo-relay~=0.5.0 is the importable package; this check applies to the separate external executable, and the repo already targets a 0.6.x CLI.

			> Likely an incorrect or invalid review comment.
adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (1)

15-44: LGTM!

Also applies to: 75-75, 85-85

justfile (1)

94-129: LGTM!

Also applies to: 196-196, 328-331, 355-373

examples/code_review_agent/config.py (1)

157-193: LGTM!

examples/code_review_agent/__init__.py (1)

9-9: LGTM!

Also applies to: 21-25

examples/code_review_agent/__main__.py (1)

17-17: LGTM!

Also applies to: 24-27

tests/adapters/test_codex_adapter.py (1)

195-397: LGTM!

tests/adapters/test_adapters_common_relay_gateway.py (1)

48-99: LGTM! Renamed tests correctly track the relay_cli_contract rename and match the RelayCliContract version/observability-version contract in relay_gateway.py.

tests/e2e/test_codex.py (1)

1-128: LGTM!

docs/index.yml (1)

17-18: LGTM!

docs/integrations/codex.mdx (3)

1-125: Otherwise, the doc is well-organized, uses inline code formatting for commands/settings, and its Relay version-range claim is consistent with the enforced 0.6.00.7.0 range in relay_gateway.py tests.


97-121: 🎯 Functional Correctness

No issue with these helper names The examples call with_native_otel and with_relay_openinference, and both are defined in examples/code_review_agent/config.py.

			> Likely an incorrect or invalid review comment.

83-96: 🎯 Functional Correctness

Use a resolvable reference for NeMo Relay PR #452.
openai-codex-cli-bin==0.137.0a4 is the pin in adapters/codex/pyproject.toml, but NeMo Relay PR #452`` is not a stable public reference. Link a commit, release tag, or another resolvable target readers can open.

examples/code_review_agent/README.md (1)

62-70: LGTM! Consistent with the Codex SDK adapter rename and the 0.6.x Relay CLI requirement documented elsewhere in this PR.

README.md (1)

160-161: LGTM!

Also applies to: 195-195

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

72-72: LGTM! Formatting-only line changes; no logic change.

Also applies to: 129-129, 286-286, 323-323, 333-333, 397-397

ATTRIBUTIONS-Python.md (1)

1284-1313: LGTM!

adapters/claude/README.md (1)

12-15: LGTM! Version pin, Relay CLI range, tools.blocked mapping, and test documentation all match the corresponding adapter/test code changes.

Also applies to: 47-48, 74-92, 124-181, 211-229

adapters/claude/pyproject.toml (1)

29-29: LGTM!

adapters/claude/src/nemo_fabric_adapters/claude/adapter.py (1)

83-83: LGTM! USER forwarding, the relay_cli_contract-based observability version lookup (consistent with the Codex adapter's identical pattern), and the tools=None/disallowed_tools=common_utils.blocked_tools(payload) mapping are all correct and covered by tests.

Also applies to: 393-398, 495-497

tests/adapters/test_claude_adapter.py (1)

213-221: LGTM! New/updated tests correctly cover the relay_cli_contract migration, tools.blockeddisallowed_tools mapping, the SDK stream-close recovery path, and USER env forwarding.

Also applies to: 288-297, 334-340, 727-756, 853-862

tests/e2e/test_claude.py (1)

14-14: LGTM!

Also applies to: 97-105, 266-269

docs/integrations/claude.mdx (1)

1-100: LGTM! Content is technically accurate (SDK pin, Relay CLI version range) and follows the MDX/SPDX and documentation style guidelines.

🛑 Comments failed to post (6)
adapters/claude/src/nemo_fabric_adapters/claude/adapter.py (1)

745-751: 🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

python3 - <<'PY'
from pathlib import Path
path = Path('adapters/claude/src/nemo_fabric_adapters/claude/adapter.py')
lines = path.read_text().splitlines()
for start,end in [(560,640),(720,770)]:
    print(f"\n--- {start}-{end} ---")
    for i in range(start, min(end, len(lines))+1):
        print(f"{i:4d}: {lines[i-1]}")
PY

Repository: NVIDIA/NeMo-Fabric

Length of output: 6122


Align the stream-close recovery guard with normalize_result() and log swallowed exceptions.
normalize_result() treats subtype.startswith("error_") as failed too, but this except only checks result.is_error, so an error_* terminal result can be re-raised instead of recovered. The branch also suppresses any other exception that happens after a failed ResultMessage with no diagnostics. Use the same failure predicate here and log the discarded exception before normalizing the result.

🤖 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 `@adapters/claude/src/nemo_fabric_adapters/claude/adapter.py` around lines 745
- 751, Update the exception guard in the stream-close handler to use the same
failure predicate as normalize_result(), treating result.is_error and
result.subtype values beginning with "error_" as failed terminal results.
Preserve re-raising when no failed result is available, but log the swallowed
exception before calling normalize_result() so discarded diagnostics are
retained.
adapters/codex/README.md (1)

163-168: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Clarify the ATIF regression prerequisite.

Rewrite “requires decoded LLM request content” as “requires the LLM request content to be decoded,” followed by the model, token usage, and expected response requirements.

🧰 Tools
🪛 LanguageTool

[style] ~167-~167: The double modal “requires decoded” is nonstandard (only accepted in certain dialects). Consider “to be decoded”.
Context: .... The semantic regression also requires decoded LLM request content, a model, token usa...

(NEEDS_FIXED)

🤖 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 `@adapters/codex/README.md` around lines 163 - 168, Update the README test
requirements description to say that the LLM request content must be decoded,
then list the model, token usage, and expected agent response as additional ATIF
prerequisites. Preserve the surrounding SDK and Relay test behavior details.

Source: Linters/SAST tools

adapters/codex/src/nemo_fabric_adapters/codex/adapter.py (1)

555-563: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Keep codex_bin config-root-relative.

Line [560] applies home-directory expansion before joining relative paths to the Fabric config root. This makes ~-prefixed configuration resolve against the adapter process’s home instead of the configured root and can select the wrong app-server binary. Remove expanduser() and resolve the raw path using the existing config-root behavior.

Based on learnings, Fabric adapter path values must remain config-root-relative and must not use home or shell-style expansion.

🤖 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 `@adapters/codex/src/nemo_fabric_adapters/codex/adapter.py` around lines 555 -
563, Update sdk_config’s codex_bin path handling to remove expanduser() and
preserve config-root-relative resolution for all non-absolute values. Resolve
the raw configured path using the existing config_root(payload) behavior, while
keeping absolute paths unchanged.

Source: Learnings

adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py (1)

45-61: 📐 Maintainability & Code Quality | 🟡 Minor | ⚡ Quick win

Annotate the public tool-event mapping.

RELAY_TOOL_HOOK_EVENTS is a new module-level public constant but has no type annotation, unlike RELAY_HOOK_EVENTS. Add dict[RelayHookAgent, frozenset[str]] or an equivalent immutable mapping type.

🤖 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 `@adapters/common/src/nemo_fabric_adapters/common/relay_hooks.py` around lines
45 - 61, Annotate the public RELAY_TOOL_HOOK_EVENTS constant with
dict[RelayHookAgent, frozenset[str]] or an equivalent immutable mapping type,
matching the existing annotation style used by RELAY_HOOK_EVENTS while
preserving its current event values.

Source: Coding guidelines

adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py (1)

210-246: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Recreates ToolGateMiddleware class on every call instead of defining it once.

_tool_gate_middleware defines a new class object each invocation (called once per main-agent config and once per gated subagent). Functionally harmless today, but if anything ever needs to reference this middleware by exact type (deepagents' excluded_middleware matches by exact class), the per-call class identity would break that. Defining the class once at module scope and parameterizing via constructor args would be more robust.

♻️ Sketch: hoist the class to module scope
-def _tool_gate_middleware(is_blocked: Any, message: Any) -> Any:
-    from langchain.agents.middleware import AgentMiddleware
-    from langchain_core.messages import ToolMessage
-
-    def _blocked(request: Any) -> Any:
-        name = request.tool_call.get("name")
-        return ToolMessage(
-            content=message(name),
-            tool_call_id=request.tool_call.get("id", ""),
-            status="error",
-        )
-
-    class ToolGateMiddleware(AgentMiddleware):  # type: ignore[misc]
-        async def awrap_tool_call(self, request: Any, handler: Any) -> Any:
-            if is_blocked(request.tool_call.get("name")):
-                return _blocked(request)
-            return await handler(request)
-
-        def wrap_tool_call(self, request: Any, handler: Any) -> Any:
-            if is_blocked(request.tool_call.get("name")):
-                return _blocked(request)
-            return handler(request)
-
-    return ToolGateMiddleware()
+def _tool_gate_middleware(is_blocked: Any, message: Any) -> Any:
+    return _ToolGateMiddleware(is_blocked, message)
+
+
+class _ToolGateMiddleware:  # defined once at module scope, parameterized per instance
+    def __init__(self, is_blocked: Any, message: Any) -> None:
+        self._is_blocked = is_blocked
+        self._message = message
+    ...
🧰 Tools
🪛 Ruff (0.15.21)

[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in is_blocked

(ANN401)


[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in message

(ANN401)


[warning] 214-214: Dynamically typed expressions (typing.Any) are disallowed in _tool_gate_middleware

(ANN401)


[warning] 218-218: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 218-218: Dynamically typed expressions (typing.Any) are disallowed in _blocked

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in handler

(ANN401)


[warning] 227-227: Dynamically typed expressions (typing.Any) are disallowed in awrap_tool_call

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in request

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in handler

(ANN401)


[warning] 232-232: Dynamically typed expressions (typing.Any) are disallowed in wrap_tool_call

(ANN401)


[warning] 240-240: Dynamically typed expressions (typing.Any) are disallowed in blocked_tools_middleware

(ANN401)

🤖 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 `@adapters/deepagents/src/nemo_fabric_adapters/deepagents/adapter.py` around
lines 210 - 246, Hoist ToolGateMiddleware out of _tool_gate_middleware and
define it once at module scope, with is_blocked and message supplied through its
constructor. Preserve the existing awrap_tool_call and wrap_tool_call blocking
behavior, then have _tool_gate_middleware instantiate and return the shared
class so exact-type middleware matching remains stable.
tests/_utils/utils.py (1)

22-60: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Add a type hint for output and debug context to the final assertion.

output has no type annotation (unlike expected_response), and the final assert any(...) at line 60 lacks the debug-context argument used by the two preceding asserts (assert llm_starts, events / assert llm_ends, events), making a live-test failure here harder to diagnose.

🧹 Suggested tweaks
-def assert_semantic_relay_artifacts(output, expected_response: str) -> None:
+def assert_semantic_relay_artifacts(output: dict, expected_response: str) -> None:
     """Assert Relay artifacts contain model, usage, and agent-response semantics."""
...
-    assert any(expected_response.lower() in message.lower() for message in agent_messages)
+    assert any(
+        expected_response.lower() in message.lower() for message in agent_messages
+    ), agent_messages

As per coding guidelines: "Python public APIs must use type annotations".

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

def assert_semantic_relay_artifacts(output: dict, expected_response: str) -> None:
    """Assert Relay artifacts contain model, usage, and agent-response semantics."""

    artifacts = {
        item["kind"]: Path(item["path"]) for item in output["relay_artifacts"]
    }
    events = [
        json.loads(line)
        for line in artifacts["atof"].read_text(encoding="utf-8").splitlines()
    ]
    llm_starts = [
        event
        for event in events
        if event.get("category") == "llm" and event.get("scope_category") == "start"
    ]
    assert llm_starts, events
    assert all(
        isinstance(event.get("data", {}).get("content"), dict)
        for event in llm_starts
    )
    assert all(event["data"]["content"].get("model") for event in llm_starts)

    llm_ends = [
        event
        for event in events
        if event.get("category") == "llm" and event.get("scope_category") == "end"
    ]
    assert llm_ends, events
    assert any(_relay_event_total_tokens(event) > 0 for event in llm_ends)

    trajectory = json.loads(artifacts["atif"].read_text(encoding="utf-8"))
    agent_messages = [
        message
        for step in trajectory.get("steps", [])
        if isinstance(step, dict)
        if step.get("source") == "agent"
        if isinstance(message := step.get("message"), str)
    ]
    assert any(
        expected_response.lower() in message.lower() for message in agent_messages
    ), agent_messages
🤖 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 `@tests/_utils/utils.py` around lines 22 - 60, Add a type annotation to the
output parameter of assert_semantic_relay_artifacts, using the appropriate
mapping type for the relay artifact payload, and include the available
trajectory or agent_messages context as the second argument to the final
assertion so failures provide debugging details.

Source: Coding guidelines

@AjayThorve
AjayThorve marked this pull request as ready for review July 16, 2026 14:39
@AjayThorve
AjayThorve requested review from a team as code owners July 16, 2026 14:39
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
rapids-bot Bot pushed a commit to NVIDIA/NeMo-Relay that referenced this pull request Jul 16, 2026
#### Overview

Decode supported `Content-Encoding` values before building the gateway's managed LLM request. This restores semantic request attributes for clients such as the Codex app server, which sends Responses API payloads with `Content-Encoding: zstd`.

- [x] I confirm this contribution is my own work, or I have the right to submit it under this project's license.
- [x] I searched existing issues and open pull requests, and this does not duplicate existing work.

#### Details

- Decode `zstd` and `identity` encodings in reverse application order for Relay's managed request representation without allocating for unencoded or identity-only bodies.
- Bound decoded output and the zstd decoder window to `max_passthrough_body_bytes` to avoid decompression amplification and oversized decoder allocations.
- Preserve the original bytes and headers when decoding fails or an encoding is unsupported, so raw passthrough behavior is unchanged.
- Remove `Content-Encoding` only when the managed pipeline reserializes the decoded JSON body as identity bytes.
- Add gateway regressions for semantic zstd decoding, chained encodings, output and window bounds, unsupported and malformed encodings, header cleanup, and passthrough invariants.

Without this, the request reached the provider successfully but Relay recorded `content: null`; OpenInference then emitted opaque `body_bytes` and omitted model and token semantics. The fix was also validated through the published `openai-codex` SDK app-server path and a NeMo Fabric Codex SDK + Relay end-to-end run, where Phoenix received populated chain, LLM, and tool spans.

Validation:

- `cargo test -p nemo-relay-cli gateway::tests -- --nocapture` (54 passed)
- `cargo clippy -p nemo-relay-cli --all-targets -- -D warnings`
- `cargo deny check bans licenses sources`
- `uvx pre-commit run attributions-rust --all-files`
- NeMo Fabric opt-in Codex SDK + patched Relay E2E (one-shot semantic artifacts and two-turn session continuity)

No public API or configuration changes.

#### Where should the reviewer start?

Start with `crates/cli/src/gateway/request.rs`. The key invariant is that decoding creates a bounded managed representation while `PreparedGatewayRequest` retains the original transport body. Then review `effective_dispatch_request` in `crates/cli/src/gateway/mod.rs`, which removes the stale encoding header only after JSON reserialization succeeds.

#### Related Issues: (use one of the action keywords Closes / Fixes / Resolves / Relates to)

- Relates to NVIDIA/NeMo-Fabric#66



## Summary by CodeRabbit

* **New Features**
  * Added observability support for `zstd`-compressed request bodies containing valid JSON, with decoding that’s encoding-aware, bounded, and preserves `Content-Encoding` when applicable.
* **Bug Fixes**
  * Prevented stale `Content-Encoding` headers from being sent after gateway request bodies are rewritten/re-encoded.
  * Improved handling of unsupported, malformed, or oversized compressed observability payloads by falling back to passthrough behavior and preserving original headers.
* **Tests**
  * Expanded gateway test coverage for `zstd` decoding and `Content-Encoding`/payload edge cases.
* **Chores**
  * Updated third-party attribution metadata, including added `zstd` license details.

Authors:
  - Ajay Thorve (https://github.com/AjayThorve)

Approvers:
  - Will Killian (https://github.com/willkill07)
  - https://github.com/Salonijain27

URL: #452
Comment thread adapters/codex/README.md
Comment thread adapters/codex/README.md
Comment thread adapters/codex/README.md
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
Signed-off-by: Ajay Thorve <athorve@nvidia.com>
@AjayThorve

Copy link
Copy Markdown
Collaborator Author

/merge

@rapids-bot
rapids-bot Bot merged commit df958f3 into NVIDIA:main Jul 16, 2026
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants