> This page is for version 0.10.
> For other versions, use one of these documentation indexes:
> - Latest (default): https://docs.nvidia.com/nemo-helix/latest/llms.txt
> - 0.10: https://docs.nvidia.com/nemo-helix/v0.10/llms.txt
> - 0.9: https://docs.nvidia.com/nemo-helix/v0.9/llms.txt
> - 0.8: https://docs.nvidia.com/nemo-helix/v0.8/llms.txt
> - 0.7: https://docs.nvidia.com/nemo-helix/v0.7/llms.txt
> - 0.6: https://docs.nvidia.com/nemo-helix/v0.6/llms.txt
> - 0.5: https://docs.nvidia.com/nemo-helix/v0.5/llms.txt

> For clean Markdown of any page, append .md to the page URL.
> For a complete documentation index, see https://docs.nvidia.com/nemo-helix/llms.txt.
> For AI client integration (Claude Code, Cursor, etc.), connect to the MCP server at https://docs.nvidia.com/nemo-helix/_mcp/server.

# Register Agents

> Register an agent on NeMo Helix from code, a container image, a remote endpoint, or its traces.

> **Warning**
>
> **Upgrading to 0.9:** `nemo agents create` was renamed to `nemo agents register`.
> There is no compatibility alias; the legacy command fails with
> `No such command 'create'`. Update scripts and CI to use `register` with the same
> arguments, and Python callers from `AgentsResource.create` to
> `AgentsResource.register`. See [Fabric 0.6 Upgrade and Adapter Support](/nemo-helix/v0.10/documentation/agents/fabric-upgrade)
> for the version, preflight and telemetry migration checklist.

Registering an agent creates an `agent` entity in a workspace. Choose the method that matches what you have:

| Method                                                   | You provide                                                          | Use when                                                                |
| -------------------------------------------------------- | -------------------------------------------------------------------- | ----------------------------------------------------------------------- |
| [Code](#register-with-code)                              | An `agent.yaml` and the files beside it                              | NeMo Helix should run the agent.                                        |
| [Container image](#register-with-a-container-image)      | An `agent.yaml` and an image                                         | The agent is already packaged, or the image runs its own server.        |
| [Remote endpoint](#register-a-remote-endpoint)           | An `agent.yaml` that points at a URL                                 | The agent runs elsewhere behind an OpenAI- or Anthropic-compatible API. |
| [Traces](#register-from-traces)                          | A name                                                               | You only want to analyze traces the agent already sends.                |
| [Source and image references](#register-with-references) | A name and an existing fileset, a container image reference, or both | You want to record associated artifacts on the agent.                   |

Agent names must start with a lowercase letter, be 2–63 characters long, and use lowercase letters,
digits, hyphens, and dots, with no consecutive hyphens and no trailing hyphen.

The CLI and Python SDK connect to the deployment in your current CLI context. To connect to a local or remote deployment, see [Connect with CLI Contexts](/nemo-helix/v0.10/documentation/reference/cli-reference/connect-to-deployments).

#### CLI

```bash
# Confirm the deployment and workspace in the current context
nemo config view
```

#### Python SDK

```python
from nemo_helix_plugin.client.client import NemoClient

client = NemoClient.from_config()
```

> **Note**
>
> These examples use the `default` workspace. If your current CLI context uses a different workspace, run `nemo config set --workspace default` first. To check, run `nemo config view`.

## Register with Code

An agent is defined by an `agent.yaml` in the `nemo-agents-spec-v1` format. This calculator agent ships with the source checkout:

```yaml
config_format: nemo-agents-spec-v1
name: calculator-agent
description: Calculator agent executed with DeepAgents

instructions:
  system:
    content: |
      You are a concise calculator agent. Solve arithmetic and numeric
      comparison requests yourself and return only the answer.

default_harness: deepagents
harnesses:
  deepagents:
    kind: deepagents

models:
  default:
    provider: nvidia
    model: ${NEMO_DEFAULT_MODEL}
```

Register it:

#### CLI

```bash
nemo agents register \
  --name calculator-agent \
  --agent-config plugins/nemo-agents/examples/nemo-agent-config/calculator-agent/agent.yaml
```

#### Python SDK

```python
import yaml
from nemo_agents_plugin.sdk import AgentsResource
from nemo_helix_plugin.client.client import NemoClient

agents = AgentsResource(NemoClient.from_config())

with open("plugins/nemo-agents/examples/nemo-agent-config/calculator-agent/agent.yaml") as f:
    config = yaml.safe_load(f)

agents.register(name="calculator-agent", config=config, config_format=config["config_format"])
```

#### Studio

Open **Agents**, select **Register Agent**, and choose one of:

* **Register with code upload**: drop the folder that contains `agent.yaml`.
* **Register from GitHub**: enter `github.com/owner/repo`, optionally with `@branch` and
  `#sub/directory`. Studio reads the files from GitHub on demand. Select an access-token secret
  for a private repository.

The CLI validates the config, replaces `${NEMO_DEFAULT_MODEL}` with the default model from
`nemo setup`, creates the agent, and uploads the text files in the config's directory (skills,
prompts, MCP server scripts) to the `<name>-ethos` fileset, up to 500 files and 900 KB.
Deployments and evaluations stage that fileset beside `agent.yaml`, so relative paths keep
working. The Python SDK registers the config only; use the CLI or Studio when the agent has other
files.

Config files must contain a YAML mapping; `{}` is accepted as an empty config.
API and SDK registration use `config.config_format` when the outer `config_format`
is omitted. If both are supplied, they must match. Nonempty configs without a
format retain the legacy `nat-workflow-v1` default.

### `agent.yaml` Reference

| Field                          | Purpose                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| ------------------------------ | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ |
| `config_format`                | Always `nemo-agents-spec-v1`.                                                                                                                                                                                                                                                                                                                                                                                                              |
| `name`, `description`          | Agent metadata.                                                                                                                                                                                                                                                                                                                                                                                                                            |
| `helix_registration`           | Optional fields of the Agent itself rather than harness config: `reference` (see [Register with References](#register-with-references)), and `context_schema`, `default_input`, and `post_run_actions` (see [Declare How an Agent Runs](/nemo-helix/v0.10/documentation/agents/execute-agents-as-jobs#declare-how-an-agent-runs)). `nemo agents register` sends them as the agent's own fields; they are not stored in its config or passed to the harness. |
| `default_harness`, `harnesses` | The harness that runs the agent. Each entry sets a `kind` (`deepagents`, `claude`, `codex`, `hermes`, `nooa-bench-agent`, `remote-agent`), plus optional `settings` and a harness-specific `model`.                                                                                                                                                                                                                                        |
| `models`                       | Named model bindings. A harness uses `models.default` unless it sets its own `model`.                                                                                                                                                                                                                                                                                                                                                      |
| `instructions.system.content`  | The system prompt, shared by every harness.                                                                                                                                                                                                                                                                                                                                                                                                |
| `skills.paths`                 | Skill directories relative to `agent.yaml`; each must contain a `SKILL.md`.                                                                                                                                                                                                                                                                                                                                                                |
| `mcp.servers`                  | MCP servers that expose tools to the harness.                                                                                                                                                                                                                                                                                                                                                                                              |
| `tools.blocked`                | Tool names the harness must not call.                                                                                                                                                                                                                                                                                                                                                                                                      |
| `runtime`                      | `timeout_seconds` and `max_turns`.                                                                                                                                                                                                                                                                                                                                                                                                         |
| `environment`                  | Workspace and artifacts directories, and environment variables.                                                                                                                                                                                                                                                                                                                                                                            |
| `telemetry`                    | Relay telemetry settings. When unset, deployments and execute jobs export ATIF trajectories to Intake for every harness that supports it (not `remote-agent`); set `enabled: false` to opt out.                                                                                                                                                                                                                                            |

See the [examples directory](https://github.com/NVIDIA-NeMo/nemo-helix/tree/main/plugins/nemo-agents/examples/nemo-agent-config)
for a config per harness.

> **Note**
>
> `nemo agents register` also accepts legacy NeMo Agent Toolkit (NAT) workflow configs
> (`config_format: nat-workflow-v1`, the default for nonempty configs when `config_format` is omitted). Use
> `nemo-agents-spec-v1` for new agents; registered-agent evaluation targets and the optimization
> strategies require it.

For the built-in Mini-SWE-Agent 2.x harness, install `nemo-helix[nemo-agents-plugin-mini-swe-agent]`
or, from a source checkout, `nemo-agents-plugin[mini-swe-agent]`. The public
[Mini-SWE lifecycle guide](/nemo-helix/v0.10/documentation/agents/mini-swe-agent) covers model
credentials, deployment, invocation, sessions, telemetry, timeouts and unsupported
shared capabilities.

### Bring Your Own Harness

The built-in harnesses build the agent from `agent.yaml`. To run agent code you wrote yourself, such
as your own LangGraph or Deep Agents graph, wrap it in a
[Fabric adapter](https://github.com/NVIDIA/NeMo-Fabric/tree/v0.6.0/docs/adapter-contract): a Python
runtime that Fabric starts, plus a descriptor that registers it. NeMo Helix then registers, deploys,
and invokes the agent like any other.

**1. Implement the runtime.** Fabric calls `start` once with the agent's config, `invoke` for each
request, and `stop` on shutdown. Return the reply text as `output["response"]`.

```python
from nemo_fabric_adapter_contract.models import (
    AgentConfig,
    AgentRunRequest,
    AgentRunResult,
    AgentRunStatus,
    RuntimeContext,
)
from nemo_fabric_adapters.common import lifecycle

from acme_agent.graph import build_agent  # your agent code


class AcmeRuntime:
    async def start(self, payload: dict) -> None:
        config: AgentConfig = payload["config"]
        model = config.models["default"]
        system = config.instructions.system if config.instructions else None
        self.agent = build_agent(
            model=model.model,
            base_url=model.base_url,  # the Inference Gateway, filled in by NeMo Helix
            system_prompt=system.content if system else None,
        )

    async def invoke(self, request: AgentRunRequest, context: RuntimeContext) -> AgentRunResult:
        reply = await self.agent.run(request.input)
        return AgentRunResult(status=AgentRunStatus.SUCCEEDED, output={"response": reply})

    async def stop(self) -> None:
        self.agent = None


def main() -> None:
    lifecycle.serve(AcmeRuntime, config_loader=AgentConfig.from_mapping)


if __name__ == "__main__":  # Fabric starts the runner with `python -m`
    main()
```

**2. Describe it** in `acme-agent.fabric-adapter.json`. `config.accepts` lists the `agent.yaml` fields
the runtime applies; Fabric rejects a config that sets anything else. NeMo Helix accepts a harness
`kind` naming a built-in harness or the `adapter_id` of an installed descriptor, and rejects any other
`kind` when you deploy the agent or create a job.

```json
{
  "contract_version": "fabric.adapter/v1alpha2",
  "adapter_id": "nvidia.fabric.acme-agent",
  "adapter_kind": "python",
  "runner": {"module": "acme_agent.fabric_adapter"},
  "config": {
    "accepts": ["models", "models.base_url", "instructions.system"],
    "system_instruction_modes": ["replace"]
  }
}
```

**3. Package the descriptor with your code.** Fabric discovers descriptors installed under
`share/nemo-fabric` in the Python environment, and NeMo Helix accepts a harness `kind` only when its
descriptor is installed there. The `shared-data` table below puts it there when the wheel is
installed. Install the package into the environment itself; an overlay such as `uv run --with` hides
the descriptor. See Fabric's
[registration and discovery guide](https://github.com/NVIDIA/NeMo-Fabric/blob/v0.6.0/docs/adapter-contract/tutorials/registration-and-discovery.md)
for details.

```toml
[project]
name = "acme-agent"
version = "0.1.0"
dependencies = ["nemo-fabric-adapters-common>=0.6.0,<0.7.0"]

[build-system]
requires = ["hatchling"]
build-backend = "hatchling.build"

[tool.hatch.build.targets.wheel]
packages = ["src/acme_agent"]

[tool.hatch.build.targets.wheel.shared-data]
"acme-agent.fabric-adapter.json" = "share/nemo-fabric/adapters/acme-agent/acme-agent.fabric-adapter.json"
```

**4. Select it** in `agent.yaml`:

```yaml
default_harness: acme
harnesses:
  acme:
    kind: nvidia.fabric.acme-agent
```

**5. Install the package everywhere the agent is validated or runs:**

* The environment where you run `nemo agents register` and `nemo agents package`, which validate the
  agent against its adapter.
* The platform's Python environment, for subprocess deployments. If you installed NeMo Helix with
  `uv tool install`, add your package to that tool environment with `--with`.
* The agent image, for Docker and Kubernetes deployments and execute jobs. Package with `--pyproject`
  so the image installs your project, or with a `--template` Dockerfile that installs the adapter; the
  `nemo agents package-agent` platform job can do neither. Without either flag, `nemo agents package`
  rejects an adapter the image doesn't install.

The platform checks each harness `kind` against the adapters installed in its own Python environment
when you deploy the agent or create an execute job. When a Docker or Kubernetes deployment, or an
execute job, names an `image`, the platform can't see which adapters that image installs, so it skips
this check at create time and the agent checks its `kind` inside the image when it starts.

Automatic trace export and streaming depend on what the descriptor declares; see the
[adapter contract](https://github.com/NVIDIA/NeMo-Fabric/tree/v0.6.0/docs/adapter-contract). The
Compass plugin's
[`nvidia.helix.compass.analyst`](https://github.com/NVIDIA-NeMo/nemo-helix/tree/main/plugins/nemo-compass)
adapter is a complete example.

### Model Access

Platform-routed models go through the [Inference Gateway](/nemo-helix/v0.10/documentation/models-and-inference),
which holds the provider credentials:

* Set `provider` to `nvidia`, `openai`, or `openai-compatible`, and leave `base_url` unset. NeMo
  Helix fills in the gateway URL when it runs the agent.
* For an `anthropic` model, set `base_url` to the gateway's route,
  `<platform-url>/apis/inference-gateway/v2/workspaces/<workspace>/openai/-`. Anthropic clients add
  `/v1/messages` themselves. An `anthropic` model without `base_url` calls Anthropic directly.
* Set `model` to a model entity from `nemo models list` (for example,
  `nvidia-nemotron-3-5-lightning-30b-a3b`) or a
  [virtual model](/nemo-helix/v0.10/documentation/models-and-inference/virtual-models) in the same workspace.
* `api_key_env` is optional. The platform supplies a placeholder for gateway-routed models.

To route a model to a provider directly instead, set `base_url` and name the environment variable
that holds its key in `api_key_env`.

### Install Harness Support

The Agents plugin includes Fabric and every harness adapter, but not the third-party harness
packages. Install the extra for the harness you use:

| Harness                 | Package                                     | Source checkout                                           |
| ----------------------- | ------------------------------------------- | --------------------------------------------------------- |
| DeepAgents              | `nemo-helix[nemo-agents-plugin-deepagents]` | `uv sync --package nemo-agents-plugin --extra deepagents` |
| Claude Code             | `nemo-helix[nemo-agents-plugin-claude]`     | `uv sync --package nemo-agents-plugin --extra claude`     |
| Codex                   | `nemo-helix[nemo-agents-plugin-codex]`      | `uv sync --package nemo-agents-plugin --extra codex`      |
| NOOA (Python 3.12–3.13) | `nemo-helix[nemo-agents-plugin-nooa]`       | `uv sync --package nemo-agents-plugin --extra nooa`       |
| Remote agent            | `nemo-helix[nemo-agents-plugin]`            | Included                                                  |

```bash
uv tool install "nemo-helix[nemo-agents-plugin-deepagents]"
```

Hermes conflicts with NeMo Helix's dependencies, so it runs from a separate Python 3.14
environment. From a source checkout, run `script/dev-install-hermes.sh` and export the
`ADAPTER_PYTHON` it prints before starting NeMo Helix. Otherwise, follow the
[Hermes Agent installation guide](https://hermes-agent.nousresearch.com/docs/installation) and
install the matching `nemo-fabric[relay]` and `nemo-fabric-adapters-hermes` versions into that
environment.

## Register with References

Add an optional `reference` block under `helix_registration` in the YAML passed to `nemo agents register`.
The fileset references the agent's source code and supporting files, which may include an `agent.yaml`.
Both fields are optional, and an agent can have either or both:

```yaml
name: support-agent
helix_registration:
  reference:
    fileset: default/support-agent-source
    container_image: nvcr.io/my-org/support-agent:1.0
```

Save this as `agent.yaml`, then register it:

```bash
nemo agents register --name support-agent --agent-config ./agent.yaml
```

`--name` is still required. You can register references without a runtime
configuration, as above, or include both in the same YAML.

| Field                                          | Registration validation                                                                                                                                                                                                                                     |
| ---------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `helix_registration.reference.fileset`         | An existing fileset as `name` or `workspace/name`. A bare name resolves in the agent's workspace and is stored as `workspace/name`. Registration checks that the caller can access the fileset; it does not require an `agent.yaml` inside it.              |
| `helix_registration.reference.container_image` | Image syntax only. Shorthand and untagged names such as `alpine` or `org/agent`, tagged names, and SHA-256 digest references are accepted. The supplied string is preserved; registration does not contact the registry or check image existence or access. |

For Python SDK registration, pass `reference` separately from `config`:

```python
from nemo_agents_plugin.sdk import AgentsResource
from nemo_helix_plugin.client.client import NemoClient

agents = AgentsResource(NemoClient.from_config())
agents.register(
    name="support-agent",
    reference={
        "fileset": "default/support-agent-source",
        "container_image": "nvcr.io/my-org/support-agent:1.0",
    },
)
```

## Register with a Container Image

The image is chosen when you deploy, so register the agent's `agent.yaml` as in
[Register with Code](#register-with-code), then deploy it with `--image`:

```bash
nemo agents deploy --agent calculator-agent --mode docker --image calculator-agent:local
```

`nemo agents package` builds an image from an `agent.yaml`; see
[Build and Publish Agent Images](/nemo-helix/v0.10/documentation/agents/deploy-agents#build-and-publish-agent-images).

For an image that already runs its own server, add `--use-image-entrypoint` so the deployment keeps
the image's `ENTRYPOINT` and `CMD`. The server must:

* Listen on `0.0.0.0:$PORT`.
* Serve `GET /health`.
* Serve `POST /v1/chat/completions` to work with `nemo agents invoke` and `nemo agents chat`.

The deployment writes the stored config into the container and sets `AGENT_CONFIG_PATH` to its path
(`NAT_CONFIG_PATH` for legacy NAT workflow configs).

## Register a Remote Endpoint

The `remote-agent` harness forwards each request to an agent that runs elsewhere. The endpoint
must stream Server-Sent Events (SSE) and speak OpenAI Responses (`openai-responses`, the default),
OpenAI Chat Completions (`openai-completions`), or Anthropic Messages (`anthropic-messages`).

```yaml
config_format: nemo-agents-spec-v1
name: support-agent
default_harness: remote-agent
harnesses:
  remote-agent:
    kind: remote-agent
    settings:
      base_url: https://agent.example.com/v1   # API root, including /v1
      api_type: openai-responses
models:
  default:
    provider: remote
    model: support-agent                      # model name the endpoint expects
    api_key_env: REMOTE_AGENT_API_KEY          # omit for an unauthenticated endpoint
telemetry:
  enabled: false
```

Register and deploy it like any other agent. Skills, MCP servers, tool policy, and tracing stay
configured on the remote agent; tag its traces with the agent's name so they match. For live streaming and sessions, see the
[Remote Agent example](https://github.com/NVIDIA-NeMo/nemo-helix/tree/main/plugins/nemo-agents/examples/nemo-agent-config#remote-agent).

## Register from Traces

To analyze an agent that already sends traces to Intake, register it with only a name. The platform stores an empty Fabric config.
The name must match the agent name on its traces (`agent.name` in ATIF, `gen_ai.agent.name` in
OTLP); see [Collect Agent Traces](/nemo-helix/v0.10/documentation/agents/traces-and-insights/collect-agent-traces).

#### CLI

```bash
nemo agents register --name support-agent
```

#### Python SDK

```python
from nemo_agents_plugin.sdk import AgentsResource
from nemo_helix_plugin.client.client import NemoClient

agents = AgentsResource(NemoClient.from_config())
agents.register(name="support-agent")
```

#### Studio

Open **Agents**, select **Register Agent** > **Register from traces**, and choose an unregistered
agent name found in ingested traces.

A trace-only agent works with [Insights](/nemo-helix/v0.10/documentation/agents/traces-and-insights/insights-from-traces),
but has no runnable config. Deployment, execute jobs, registered-agent evaluations, and the built-in
optimization strategies reject it at submission. To run it on NeMo Helix, delete it and register it
again under the same name with a config.

## Manage Registered Agents

```bash
nemo agents list
nemo agents get calculator-agent
nemo agents delete calculator-agent
```

An agent's config and references cannot be edited in place. To change them, register a new agent, or use
`nemo agents redeploy` to replace a deployed agent; see
[Update a Deployed Agent](/nemo-helix/v0.10/documentation/agents/deploy-agents#update-a-deployed-agent).

## Label Agents

Labels are key/value pairs you attach to an agent when you register it, then filter on
when you list agents.

#### CLI

```bash
nemo agents register --name support-analyst --agent-config ./agent.yaml --label team=support

nemo agents list --label team=support
```

#### Python SDK

```python
agents.register(name="support-analyst", config=config, labels={"team": "support"})
agents.list(labels={"team": "support"})
```

A key is `<name>` or `<prefix>/<name>`. Each part is 1–63 letters, digits, `-`, or `_`, and
starts and ends with a letter or digit. Unlike Kubernetes labels, keys cannot contain dots.
A value is empty or up to 253 letters, digits, `-`, `_`, `.`, or `/`.

NeMo Helix plugins may apply labels when registering agents for you, using the prefix `helix-<plugin>/`,
for example `helix-agents/managed-by` or `helix-compass/target-agent`. Avoid that prefix for your own
keys. The API does not enforce this convention.

Labels are for filtering and display only. Never rely on them for authorization.