mcp-nixos: An MCP Server That Answers Nix Queries From Upstream APIs
MCP-NixOS - Model Context Protocol Server for NixOS resources
At a glance
- What is it?
- mcp-nixos exposes NixOS packages, options, Home Manager, nix-darwin and several documentation sources to MCP-capable assistants through two tools. It queries remote APIs, so the client machine does not need Nix installed, except for the flake-input and store actions.
- Who is it for?
- Adopt mcp-nixos if an MCP-capable assistant already writes Nix expressions for you and you want its package and option lookups grounded in upstream data rather than recalled from training. Skip it if your work is entirely local flake evaluation, since the flake-inputs and store actions need Nix on the host while everything else is API-backed.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 11 days ago.
- What is it written in?
- Mainly Python, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.
DEEP OPEN-SOURCE ANALYSIS
The problem mcp-nixos addresses: invented package names in Nix configs
Language models write plausible Nix expressions. They also write package attributes that do not exist, option paths that were renamed two releases ago, and Home Manager settings borrowed from a blog post about a different module set. The failure is quiet: the expression looks right until evaluation fails, and the correction loop costs more time than writing the config by hand.
mcp-nixos targets that loop. It is a Model Context Protocol server that answers queries about Nix resources from upstream sources rather than from model memory. The README frames the motivation directly in its title, and the tool list backs it up: NixOS packages, NixOS options, Home Manager options, nix-darwin settings, Nixvim and NVF Neovim options, FlakeHub flakes, Noogle function signatures, the NixOS Wiki, nix.dev, package version history from NixHub, and binary cache status.
The intended user is someone whose assistant already participates in writing Nix code: a NixOS or nix-darwin user configuring a system, a Home Manager user maintaining dotfiles, or a platform engineer who needs to confirm that a package exists and is cached before pinning it. The README notes the server works on Windows, macOS and Linux because it is querying APIs, not evaluating a local Nix store. That detail matters for the audience: you can use it from a laptop that has never had Nix installed.
Two tools, eleven sources: the interface mcp-nixos actually exposes
The design decision the README spends the most words on is tool consolidation. The project previously shipped 17 tools and now ships 2, on the stated grounds that tool definitions consume the assistant's context window. The README claims roughly 1,030 tokens total for the tool surface. That number is the project's own figure, not an independent measurement.
The first tool is `nix`, with the signature `nix(action, query, source, type, channel, limit, version, system)`. The README notes that `version` and `system` are only used when `action="cache"`. Actions are `search`, `info`, `stats`, `browse`, `channels`, `flake-inputs`, `cache` and `store`. The `browse` action carries a legacy alias, `options`, which tells you something about the migration path from earlier versions.
The second dimension is `source`, and it is where the data flow becomes visible. Sources map to distinct upstream providers: `nixos` for packages, options and programs; `home-manager`, `darwin`, `nixvim` and `nvf` for option sets; `flakes` for search.nixos.org; `flakehub` for the FlakeHub registry; `noogle` for function signatures; `wiki` and `nix-dev` for documentation; `nixhub` for package metadata and store paths.
One normalization detail is worth flagging because it affects query construction. NVF results use canonical `vim.*` option paths, and the server accepts the shorthand `programs.nvf.vim.*` or the module path `programs.nvf.settings.vim.*`, normalizing both. If your assistant produces one form and the docs show another, the server is expected to reconcile them. There is no equivalent normalization described for Nixvim queries.
Running mcp-nixos: uvx, Nix, Docker, HTTP or a Pi adapter
The README lists five installation paths. The recommended one is uvx, configured as an MCP server entry with `"command": "uvx"` and `"args": ["mcp-nixos"]`. The Nix path uses `"command": "nix"` with `"args": ["run", "github:utensils/mcp-nixos", "--"]`. The Docker path runs `ghcr.io/utensils/mcp-nixos` with `--rm -i`.
The HTTP transport is configured through environment variables rather than flags. `MCP_NIXOS_TRANSPORT=http` selects it, `MCP_NIXOS_HOST` and `MCP_NIXOS_PORT` set the bind address, and the MCP endpoint defaults to `/mcp`. A custom path is set with `MCP_NIXOS_PATH`, for example `MCP_NIXOS_PATH=/api/mcp`. Setting `MCP_NIXOS_STATELESS_HTTP=1` disables per-client session state, which is the setting you want when the server sits behind a load balancer that does not pin sessions. STDIO is the default and can be forced with `MCP_NIXOS_TRANSPORT=stdio`.
The Pi coding agent path is the one that needs reading carefully. Pi does not speak MCP natively, so the README offers two routes. The recommended route installs `npm:pi-mcp-adapter` and adds an entry to `~/.pi/agent/mcp.json` with a `"lifecycle": "lazy"` key, which defers server startup. The alternative is a project-local extension shipped in the repository at `.pi/extensions/mcp-nixos.ts`, auto-loaded when `pi` runs in the cloned repo, with an optional `cd .pi && npm install` for editor type resolution. The README states that Pi runs it either way.
Python 3.11 or later is required according to the PyPI badge. The README does not describe a configuration file for the server itself; transport and binding are environment variables, and everything else is per-query arguments.
Where mcp-nixos stops: Nix-dependent actions and upstream freshness
The headline claim that no Nix installation is required is accurate for API-backed sources and not accurate for all of them. Two actions depend on a local Nix store: `flake-inputs`, described as exploring local flake inputs from the Nix store, and `store`, described as reading files or listing directories at an explicit `/nix/store` path. The README marks both with a Nix requirement. If your workflow is built around inspecting pinned flake dependencies, you are in the category that needs Nix on the host, and the cross-platform convenience argument does not apply to you.
The second constraint is that every answer is only as current as the upstream service. Package and option data come from remote providers, so a channel that has not been indexed upstream, or an option added in an unreleased branch, will not appear. The README does not describe a caching layer, an offline mode, or a fallback when a provider is unreachable. For a documentation assistant that is usually fine. For a pre-deployment check it means the server's answer and `nix flake check` can disagree, and the local evaluation is the one that counts.
There is also a migration cost embedded in the version history. The jump from 17 tools to 2 is a breaking change to the tool surface. Any prompt, saved configuration or client integration that referenced the old tool names needs updating. The `options` alias on the `browse` action suggests the project is aware of this, but an alias on one action is not a compatibility shim for a reorganized interface. Check the release notes for the version you install before wiring it into an existing setup.
How mcp-nixos differs from running nix search or a documentation MCP
The obvious alternative is the Nix CLI itself. `nix search nixpkgs firefox` answers a package query locally, with no third-party service in the path, and it reflects the exact nixpkgs revision your flake pins. The difference in approach is where the answer comes from. mcp-nixos queries aggregated upstream indexes that span channels and registries, which is why it can answer questions the local store cannot, such as which historical versions of a package exist on NixHub, whether a store path is present in the binary cache, or what a FlakeHub flake contains. The trade is that the CLI is authoritative for your pinned revision and mcp-nixos is authoritative for the upstream index.
A second alternative is a general documentation MCP server pointed at the NixOS Wiki or nix.dev. That covers prose and tutorials. mcp-nixos covers those two sources as well, but its distinguishing surface is structured data: option paths, package attributes, function type signatures, cache status. The two are complementary rather than competing, and a user who only needs conceptual explanations will not get much from the structured queries.
A third comparison is against doing nothing and letting the assistant recall Nix syntax from training. That is the baseline the project is arguing against, and for package and option names the argument is sound. It is less sound for anything the README does not list as a source: module implementation details, overlay composition, and behavior that only appears at evaluation time are outside the server's scope entirely.
Maintenance, licence and what to check before adopting mcp-nixos
The repository is MIT licensed, which permits commercial and private use with the usual attribution requirement. That is a permissive baseline, and nothing in the README suggests dual licensing or a separate terms document. This is not legal advice; if you redistribute the server inside a product, read the licence text yourself.
Upgrade cost is driven by the tool schema rather than by dependencies. The release cadence visible in the material shows v3.1.0, v3.0.2 and v3.0.1 within roughly a month, which is frequent enough that pinning a version is reasonable for a production assistant configuration. Because the interface is two tools with an `action` and `source` argument, most upstream source additions should not break existing callers. The 17-to-2 consolidation was the disruptive change, and it is already behind the current release line.
Running cost is small but not zero. The uvx and Docker paths pull a Python package or image; the HTTP transport adds a process to supervise if you self-host it. The README does not document rate limits on the upstream providers, so if you point a busy assistant at the HTTP transport with many concurrent clients, the behavior under provider throttling is unverified in the supplied material.
Before adopting, check three things. Confirm which `source` values your queries will actually hit, since the Nix-dependent actions change the deployment story. Confirm the tool signature in the version you install matches what your client configuration expects, given the v3 consolidation. And confirm that the upstream index freshness is acceptable for your use, because the server reports what the providers publish, not what your pinned nixpkgs revision contains.
Editorial conclusion
Adopt mcp-nixos if an MCP-capable assistant already writes Nix expressions for you and you want its package and option lookups grounded in upstream data rather than recalled from training. Skip it if your work is entirely local flake evaluation, since the flake-inputs and store actions need Nix on the host while everything else is API-backed. Before trusting it in a workflow, verify which sources answer your queries and whether the version you install matches the tool schema you expect, because v3 consolidated 17 tools into 2 and older client configurations may still reference the previous names.
Community notes