Agent Reach Environment Variables for Server vs. Local Detection

Agent Reach inspects SSH_CONNECTION, SSH_CLIENT, DISPLAY, and WAYLAND_DISPLAY inside _detect_environment() in agent_reach/cli.py to determine whether the current runtime is a headless server or a local workstation.

Agent Reach automatically adapts its installation flow and diagnostic output by detecting whether it is running on a remote server or a local machine. The core logic resides in agent_reach/cli.py, where the private function _detect_environment() reads specific environment variables and filesystem markers to classify the environment without manual configuration. The detection result propagates to docs/install.md to influence proxy suggestions and to agent_reach/doctor.py to tailor diagnostic messages for server versus local setups.

SSH Session Environment Variables

Remote SSH sessions are one of the strongest signals that Agent Reach is running on a server. The codebase looks for two specific OpenSSH environment variables to make this determination.

SSH_CONNECTION and SSH_CLIENT

According to the Panniantong/Agent-Reach source code, _detect_environment() checks for the presence of either SSH_CONNECTION or SSH_CLIENT:

  • SSH_CONNECTION – Set by OpenSSH when a remote session is active. It typically contains the client IP, client port, server IP, and server port.
  • SSH_CLIENT – Also set by OpenSSH and serves as an alternative indicator.

If either variable is present, the function increments the indicators score by 2:


# https://github.com/Panniantong/Agent-Reach/blob/main/agent_reach/cli.py#L75-L115

def _detect_environment():
    import os
    # 1️⃣ SSH session

    if os.environ.get("SSH_CONNECTION") or os.environ.get("SSH_CLIENT"):
        indicators += 2
    # …additional checks…

    return "server" if indicators >= 2 else "local"

Presence of these variables means the process is being run over an SSH session, which strongly suggests a remote server environment.

Headless Display Environment Variables

Graphical display variables indicate a local desktop environment. When both are absent, Agent Reach treats the system as headless and increments the server score.

DISPLAY and WAYLAND_DISPLAY

The function checks for X11 and Wayland display identifiers using os.environ.get:

  • DISPLAY – The X-Window display identifier (e.g., :0).
  • WAYLAND_DISPLAY – The Wayland display identifier (e.g., wayland-0).

If neither variable is set, the environment is considered headless, and the indicators score increases by 1:

    # 3️⃣ Headless (no X/Wayland display)

    if not os.environ.get("DISPLAY") and not os.environ.get("WAYLAND_DISPLAY"):
        indicators += 1

Headless environments are typical of servers that have no graphical display attached.

Container and Virtualization Checks

While Docker detection does not rely on environment variables, it contributes heavily to the server classification score alongside the env-var checks.

Docker Filesystem Markers

Inside _detect_environment(), Agent Reach checks for the existence of two container marker files:

  • /.dockerenv
  • /run/.containerenv

If either file exists, the function adds 2 to the indicators score. These are filesystem checks, not environment variable inspections.

Cloud VM and Virtualization Markers

Beyond SSH and display variables, the function reads system files to identify cloud instances:

  • /sys/hypervisor/uuid and /sys/class/dmi/id/product_name are scanned for known cloud provider strings such as "amazon", "google", or "microsoft".
  • The command systemd-detect-virt is executed; any non-"none" result adds to the indicator score.

These checks help tag virtual machines as server-side even when no SSH or Docker indicator is present.

The Scoring Threshold

Agent Reach does not rely on a single boolean check. Instead, _detect_environment() aggregates indicators into a cumulative score.

How the Score Determines the Environment

The function tallies points across all checks:

  • SSH session (SSH_CONNECTION or SSH_CLIENT): +2 indicators
  • Docker or container filesystem markers: +2 indicators
  • Headless (no DISPLAY or WAYLAND_DISPLAY): +1 indicator
  • Cloud VM or virtualization detected: Additional increments

If the total indicators value is greater than or equal to 2, _detect_environment() returns "server". Otherwise, it returns "local".

Practical Detection Examples

The following examples demonstrate how to invoke the detection logic directly from the repository source.

Local Workstation Example

On a local laptop with an active X display and no SSH session:


# Example 1 – on a local laptop (no SSH, X display present)

$ echo $DISPLAY
:0
$ echo $SSH_CONNECTION   # empty

$ python - <<'PY'
import os, subprocess, importlib.util
spec = importlib.util.spec_from_file_location("cli", "agent_reach/cli.py")
cli = importlib.util.module_from_spec(spec)
spec.loader.exec_module(cli)
print(cli._detect_environment())
PY

# → local

Remote SSH Server Example

Inside an SSH session on a remote VM with no GUI:


# Example 2 – inside an SSH session on a remote VM (no GUI)

$ echo $SSH_CONNECTION
192.168.1.2 54321 10.0.0.5 22
$ echo $DISPLAY   # empty

$ python - <<'PY'
import importlib.util
spec = importlib.util.spec_from_file_location("cli", "agent_reach/cli.py")
cli = importlib.util.module_from_spec(spec)
spec.loader.exec_module(cli)
print(cli._detect_environment())
PY

# → server

Docker Container Example

Inside a headless Docker container:


# Example 3 – inside a Docker container (headless)

$ ls /.dockerenv   # file exists

/.dockerenv
$ python - <<'PY'
import importlib.util
spec = importlib.util.spec_from_file_location("cli", "agent_reach/cli.py")
cli = importlib.util.module_from_spec(spec)
spec.loader.exec_module(cli)
print(cli._detect_environment())
PY

# → server

Summary

  • SSH_CONNECTION and SSH_CLIENT environment variables each trigger a +2 score toward server detection in _detect_environment().
  • Absence of DISPLAY and WAYLAND_DISPLAY flags the environment as headless, adding +1 to the server indicator count.
  • Docker and container runtimes are detected via /.dockerenv and /run/.containerenv filesystem markers, not environment variables.
  • The function returns "server" only when the cumulative indicator score reaches 2 or higher; otherwise it returns "local".
  • Additional checks for cloud VM strings and systemd-detect-virt output ensure accurate classification of virtualized and cloud-hosted infrastructure.

Frequently Asked Questions

Which environment variables does Agent Reach check for server detection?

Agent Reach checks SSH_CONNECTION, SSH_CLIENT, DISPLAY, and WAYLAND_DISPLAY in agent_reach/cli.py. SSH_CONNECTION and SSH_CLIENT indicate a remote SSH session, while missing DISPLAY and WAYLAND_DISPLAY variables signal a headless environment.

How does Agent Reach detect Docker containers?

Agent Reach detects Docker and container environments by checking for the existence of /.dockerenv or /run/.containerenv on the filesystem. These are not environment variables, but filesystem markers that add 2 points to the server indicator score when found.

What score does _detect_environment() require to return "server"?

The _detect_environment() function returns "server" when the cumulative indicators score is greater than or equal to 2. A single check, such as an active SSH session or a Docker filesystem marker, is sufficient to meet this threshold.

Can Agent Reach detect cloud virtual machines?

Yes. Agent Reach reads /sys/hypervisor/uuid and /sys/class/dmi/id/product_name for known cloud provider strings like "amazon", "google", or "microsoft". It also runs systemd-detect-virt to identify generalized virtualization platforms, adding extra weight to the server classification.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →