nxstate
nxstate runs show commands on Cisco Nexus switches and returns clean, structured JSON. It is built for two audiences: network engineers who want scriptable, filterable device state without writing glue code, and coding agents that need a safe, self-describing interface to inspect a Nexus fleet without any risk of changing a device.
Read-only by design
Section titled “Read-only by design”nxstate cannot configure a switch. This is a product boundary, not a runtime flag.
Any input that is not a show command — conf t, write, reload, clear, and dozens of other mutating leaders — is rejected before a connection is opened, with a structured WRITE_REFUSED error and exit code 11. There is no --allow-mutations flag. “No conf t” is the entire point.
$ nxstate show "configure terminal"error: refused non-read command: 'configure terminal' ('configure' is not a read command) code: WRITE_REFUSED fix: nxstate is read-only; only 'show ...' commands are permitted (no conf t / mutations)This makes nxstate safe to hand to an autonomous agent pointed at a production fleet.
Key capabilities
Section titled “Key capabilities”Structured output everywhere. NX-OS returns {"TABLE_intf": {"ROW_intf": [...]}} wrappers; nxstate normalizes them to plain arrays. Choose your format: --format json|plain|tsv, project specific fields with --select, and bound large tables with --limit.
Curated command surface. Common state is a single sub-command away: interface list, vlan list, bgp summary, route list, neighbor list, arp list, mac list, system version, and more. All return parsed, stable JSON — not screen-scraped text.
Generic read passthrough. Any show command the curated surface doesn’t cover is available via nxstate show "<cmd>". nxstate runs the command, tries every parser it knows (Genie → ntc-templates → raw text), and returns structured output wherever possible.
Self-describing for agents. nxstate schema emits the full command tree, exit-code table, and live safety state as machine-readable JSON — no docs required. nxstate agent prints the embedded usage guide that tells an LLM exactly how to drive the tool.
Inventory-driven fleet fan-out. Define hosts and groups once in ~/.config/nxstate/inventory.yaml. Target one device, a glob, a group, or the whole fleet with --device, --group, or --all. Multi-device runs execute concurrently (default 10 workers), stream NDJSON as results arrive, isolate per-device failures, and exit 15 (partial) if any device fails — one bad switch does not abort the run.
Prompt-injection fencing. Device free-text — interface descriptions, neighbor names, log messages, banners — is attacker-influenceable. nxstate wraps all such content in BEGIN/END UNTRUSTED DEVICE OUTPUT markers and sets "untrusted": true in the JSON envelope so an LLM agent won’t follow instructions embedded in the output.
Credential safety. Passwords are never accepted on the command line. Resolution order: --password-stdin → NXSTATE_PASSWORD env var → OS keyring (nxstate auth login) → interactive prompt (TTY only). Env vars cover the rest: NXSTATE_HOST, NXSTATE_USERNAME, NXSTATE_TRANSPORT, NXSTATE_PORT.
Dual transport. Default --transport auto probes NX-API first (fast HTTP POST to /ins), then falls back to SSH via scrapli. Force one with --transport ssh|nxapi. NX-API with a self-signed cert needs --insecure on trusted networks.
A quick taste
Section titled “A quick taste”# Set credentials once; nxstate resolves flag → inventory → env → defaultexport NXSTATE_HOST=leaf1export NXSTATE_USERNAME=netopsexport NXSTATE_PASSWORD=... # never on argv
# Verify connectivity and credentials before doing anything elsenxstate doctor
# Structured JSON for the version string onlynxstate system version --select nxos_ver_str --json
# Interface list as TSV — paste into a spreadsheetnxstate interface list --format tsv
# BGP summary for a specific VRFnxstate bgp summary --vrf prod --json
# Any 'show' command you need; Genie parses it if a parser existsnxstate show "show ip ospf neighbors detail"
# Fan-out: all devices in the 'datacenter' group, concurrentlynxstate interface list --group datacenterExample single-device output:
[ { "interface": "Ethernet1/1", "state": "up", "ip_address": "10.0.0.1/30", "speed": "1000" }]Example fan-out NDJSON (one line per device as it completes):
{"device": "leaf1", "host": "10.1.1.11", "ok": true, "data": [...]}{"device": "leaf2", "host": "10.1.1.12", "ok": true, "data": [...]}Install
Section titled “Install”nxstate is a Python package on PyPI. Pick whichever fits your workflow — uvx is the fastest way to start.
# uv (recommended) — run with zero install, or install persistentlyuvx nxstate --help # zero-install: runs straight from PyPI, nothing left behinduv tool install nxstate # persistent: puts the `nxstate` binary on your PATH
# pipx — isolated permanent installpipx install nxstate
# pip — into the current environment / virtualenvpip install nxstate
# Maximum parser coverage — adds Genie's ~293 NX-OS parsers (works with any method above)uvx "nxstate[genie]" --helpuv tool install "nxstate[genie]"pipx install "nxstate[genie]"Prefer to grab the artifacts directly? Every tagged version ships a wheel and sdist on the GitHub Releases page.
Requires Python 3.10 or later. Licensed under the MIT License.
Where to go next
Section titled “Where to go next”- Installation — system requirements, install methods, verifying your setup
- Quickstart — connect to your first switch in under five minutes
- Read-only safety — how
WRITE_REFUSEDworks and why there is no override - Transports and parsing — SSH vs NX-API, the Genie → ntc-templates → raw pipeline
- Authentication — keyring, env vars,
--password-stdin, RBAC - Inventory and fan-out — defining hosts and groups, concurrent fleet runs
- Output and filtering —
--format,--select,--limit, NDJSON - Gathering state — a command-by-command reference with example outputs
- Troubleshooting —
doctor, common errors, exit codes - Command reference — every sub-command and its flags
- Global flags — flags available on every command
- Exit codes — the full table with names and meanings
- Inventory schema —
hosts,groups,defaultsformat - Environment variables — all recognized env vars