NousResearch/hermes-agent · error · RuntimeError

iron-proxy binary not available — run `hermes egress install

Error message

iron-proxy binary not available — run `hermes egress install`.

What it means

start_proxy() resolves the binary via find_iron_proxy(install_if_missing=...); if that returns None — no binary on disk and auto-install not requested (or not possible) — it refuses to start with the command that performs the install. This is a missing-prerequisite error raised before any config/process work happens.

Source

Thrown at agent/proxy_sources/iron_proxy.py:1789

    just returns the live status.

    ``refresh_secrets_from_bitwarden=True`` re-fetches upstream secrets
    via ``bws secret list`` at startup and injects them into the child
    env.  This delivers the rotation promise that distinguishes
    ``credential_source: bitwarden`` from ``credential_source: env``.
    Without this flag (or with ``bitwarden_config=None``) the proxy still
    starts but uses whatever the host process env happens to contain.
    """

    global _proxy_nonce

    existing = _read_pid()
    if existing and _pid_alive(existing):
        return get_status()

    bin_path = binary or find_iron_proxy(install_if_missing=install_if_missing)
    if bin_path is None:
        raise RuntimeError(
            "iron-proxy binary not available — run `hermes egress install`."
        )

    cfg = config_path or (_proxy_state_dir() / "proxy.yaml")
    if not cfg.exists():
        raise RuntimeError(
            f"iron-proxy config not found at {cfg}. "
            "Run `hermes egress setup` first."
        )

    # Build a minimal subprocess env.  os.environ.copy() would ship every
    # secret in the operator's shell to the proxy — /proc/<pid>/environ
    # would then expose OPENAI_API_KEY, AWS keys, etc. to any same-uid
    # local process.  Defeats the threat model the proxy exists to
    # mitigate.
    env = _build_proxy_subprocess_env(
        extra_env=extra_env,
        refresh_from_bitwarden=refresh_secrets_from_bitwarden,

View on GitHub (pinned to c896c09c42)

Solutions

  1. Run `hermes egress install` (equivalently start with auto-install enabled) to fetch and verify the pinned release binary.
  2. Verify afterwards that find_iron_proxy() now returns a path before calling start_proxy().
  3. If install keeps failing, work through its download/checksum errors first — this error is just the downstream symptom.

Example fix

// before
start_proxy()  # RuntimeError: iron-proxy binary not available

// after
from agent.proxy_sources.iron_proxy import find_iron_proxy, start_proxy
bin_path = find_iron_proxy(install_if_missing=True)
if bin_path is None:
    raise SystemExit("iron-proxy install failed; see logs")
start_proxy(binary=bin_path)
Defensive patterns

Strategy: validation

Validate before calling

from agent.proxy_sources.iron_proxy import find_iron_proxy

def binary_ready() -> bool:
    return find_iron_proxy() is not None

Try / catch

try:
    start_proxy()
except RuntimeError as e:
    if "binary not available" in str(e):
        find_iron_proxy(install_if_missing=True)
        start_proxy()

Prevention

When it happens

Trigger: start_proxy() (or `hermes egress start`) with install_if_missing=False on a machine where the iron-proxy binary was never installed, was deleted from the proxy state dir, or auto-install failed silently earlier. Note: if a live pid exists, start_proxy returns early, so this only fires when the daemon isn't running.

Common situations: Fresh machine where setup ran on a different host; the state dir was cleaned; the binary was quarantined by antivirus/removed by a cleanup job.

Related errors


AI-assisted analysis of NousResearch/hermes-agent@c896c09c42 (2026-08-14). Data as JSON: /api/errors/58f116912549ebf9. Report an issue: GitHub.