Model or dataset
OleksandrChekhovskyi/hax avatar
OleksandrChekhovskyi/hax

hax: a terminal-native coding agent in a single C binary

A minimalist, terminal-native coding agent written in C.

788 stars49 forksCMIT

At a glance

What is it?
hax is a minimalist coding agent written in C and distributed as one native binary, with local llama.cpp models treated as a first-class provider. It is aimed at developers who run agents in the terminal and want to see what those agents actually send.
Who is it for?
Adopt hax if you want a small C binary that talks to llama.cpp or a hosted API and leaves your terminal scrollback alone; skip it if you need MCP marketplaces, a plugin runtime, IDE panels, or per-command permission prompts, which docs/philosophy.md lists as deliberate omissions. Before committing, run scripts/install_deps.sh on your distribution, build with make, and confirm that the provider you intend to use appears under /provider after you set its API key.
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 1 day ago.
What is it written in?
Mainly C, 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

What hax is for, and who it is not for

Most coding agents arrive as a Node or Python application that pulls a runtime, a package tree and a plugin ecosystem along with it. hax takes the opposite route: it is a single native binary written in C, and the README describes it as "lightweight by design" with a small dependency set, instant startup and a memory footprint of a few MB. That matters when the machine is also running a local model, because every megabyte the agent holds is a megabyte the model cannot use.

The stated audience is narrow on purpose. Developers who live in the terminal, run local models, audit what their tools do, package software for distributions, or run agents on constrained hardware. The README is equally direct about who should look elsewhere: if you want MCP marketplaces, a plugin runtime, IDE panels, or per-command permission prompts, other agents build exactly that, and hax "deliberately doesn't". docs/philosophy.md is where each omission and its substitute pattern is explained, which is a more honest arrangement than a feature list that quietly leaves things out.

How the provider layer and the terminal UI fit together

hax separates the model backend from the interface. Providers listed in the README are OpenAI and compatible endpoints, Anthropic and compatible endpoints, Codex through a ChatGPT subscription, OpenRouter, OpenCode Zen and Go, llama.cpp, and custom endpoints. Selection happens at runtime: start hax, use /provider to see what is available and pick a model, and the interactive provider, model and effort choices are remembered.

The local path is the one the README treats as the default case. You start llama-server with a GGUF model, then run hax with the llama.cpp provider, and hax auto-discovers the model and its runtime capabilities. No custom provider configuration block is required for that setup, which is unusual; most agents make you describe your local endpoint by hand.

On the display side, hax reflows streaming Markdown and live tool output for the terminal, and redraws only the current streaming line or the input area. Native scrollback is preserved, and the README states that hax does not take over the terminal. The inspectability story is the same shape: Ctrl+T opens a transcript view showing what was sent to the model and what came back, and a detailed wire protocol trace can be collected optionally. For anyone who has debugged an agent by guessing, that transcript view is the feature that decides the tool.

Installing hax and running a first prompt

On macOS or Linux with Homebrew, installation is one command. On Arch Linux the package is in the AUR as hax. On other Linux distributions you download the prebuilt static binary for x86_64 or aarch64 from the latest release and unpack it into a directory on your PATH. Windows users are directed to WSL, and the BSDs build from source only.

bash
brew install oleksandrchekhovskyi/hax/hax

Building from source links against your system's shared libraries instead of producing a static binary. The dependency script covers Debian and Ubuntu, Fedora, Arch, openSUSE, Alpine, macOS, FreeBSD and OpenBSD, and installs a C compiler, libcurl, jansson, meson, ninja, pkg-config, plus fzf, which hax uses for @file completion when it is present.

bash
git clone https://github.com/OleksandrChekhovskyi/hax.git
cd hax
scripts/install_deps.sh
make

After make, the binary is at ./build/hax. The README notes that make install is optional and may prompt for sudo, and that the examples assume hax is on PATH, so after a plain build you invoke ./build/hax instead. If you are hacking on hax rather than using it, make symlink links the freshly built binary into ~/.local/bin so it stays on PATH across rebuilds.

Getting a first answer depends on the provider. For a hosted API, set the matching environment variable, then start hax and pick a model with /provider. One-shot mode prints the final answer to stdout and puts resume hints on stderr, which keeps it usable in a pipeline.

bash
hax -p "list TODOs"
printf "explain x" | hax -p

For a local model, start llama-server with your GGUF file first and then run hax with the llama.cpp provider; the README says hax discovers the model and its capabilities without a custom config block.

Sessions, resume, and the plain-text contract

hax keeps sessions per directory. hax -c continues the latest session for the current directory, hax --resume lets you pick from past sessions, and hax --resume=ID -p "next" resumes a specific session in one-shot mode. Resumed conversations restore their own provider, model, effort and preset unless a CLI selection flag overrides them, so a session carries its own context rather than inheriting whatever you happen to have configured today.

The README describes config and session files as plain text, and points to docs/sessions.md for the session-file format and the hax --json stream. That is the part worth weighing against heavier tools. A plain-text session file can be read, diffed and edited with tools you already have, and the JSON stream gives a scripted consumer something to parse. The trade-off is that there is no database, no index and no server-side sync; if you want sessions shared across machines or searched as a corpus, that is work you do yourself.

Configuration is optional, and the resolution order matters: interactive selections are remembered separately from the config file, CLI flags apply only to the current run, and environment variables are aimed at shells and scripts. docs/configuration.md covers the file format, resolution order, presets and the setting reference.

Where hax is the wrong tool

The absences are the product. No plugin runtime, no MCP marketplace, no IDE panels, no per-command permission prompts. If your workflow depends on approving each shell command before it runs, hax does not offer that gate, and the README does not pretend otherwise. The substitute pattern for extension is composition through subprocesses, which means your integration work happens outside the agent, in shell scripts and pipelines you maintain.

There are practical limits too. Windows is supported only under WSL, and the BSDs are source-only, so a team standardized on native Windows cannot adopt hax as-is. The build dependency list is short but real: libcurl, jansson, meson, ninja and pkg-config, plus a C compiler, and on platforms outside the script's coverage you install those by hand. The README also notes that fzf is needed for @file completion, so that convenience is conditional on an external program being present.

Finally, the README does not document rollback or downgrade steps, and it does not describe an upgrade path between releases. If you need a supported migration story between versions, hax does not provide one.

How hax differs from a Python or Node agent framework

The obvious comparison is a general agent framework such as Aider or a Node-based CLI agent, and the difference is not the feature list but the delivery model. Those tools typically install through a language package manager, bring a runtime and a dependency tree, and extend through plugins or a protocol such as MCP. hax installs as a binary, extends through subprocesses, and treats the terminal as the whole interface.

That choice buys startup time and memory, which the README frames as leaving more RAM for local models, and it buys auditability: a C binary with a small dependency set is easier to inspect and package than a tree of interpreted dependencies. It costs you the ecosystem. There is no marketplace to browse, no plugin to drop in, and no IDE integration, so anything beyond what hax ships is a script you write. The README's own framing is that other agents build exactly those things, and hax deliberately does not.

For distribution packagers the difference is sharper still. A static binary for x86_64 or aarch64, an AUR package, and a Homebrew formula are three packaging stories that do not involve vendoring a language runtime.

Maintenance, licence, and what upgrading costs

hax is MIT licensed, which permits use, modification and redistribution with the licence text preserved. Nothing in the repository suggests a copyleft obligation, but packaging a binary for a distribution still involves that distribution's own policy, and this is not legal advice.

The repository is not archived, and the last push to master was on 2026-09-14. Tagged releases are frequent: v0.3.0 on 2026-08-12, v0.4.0 on 2026-08-22, and v0.5.0 on 2026-09-04. That cadence is good for users who want fixes and awkward for anyone pinning versions, because three releases landed inside roughly three weeks.

Upgrade cost depends on how you installed it. Homebrew and the AUR handle version movement for you. A static binary means re-downloading from the releases page. A source build means re-running make after a pull, and the README's make symlink target exists specifically so a rebuild does not leave you invoking a stale binary. What the README does not document is rollback or a downgrade procedure, so if you pin a release for production use, keep the old artifact yourself. The CHANGELOG.md at the repository root is the file to read before moving between versions.

Editorial conclusion

Adopt hax if you want a small C binary that talks to llama.cpp or a hosted API and leaves your terminal scrollback alone; skip it if you need MCP marketplaces, a plugin runtime, IDE panels, or per-command permission prompts, which docs/philosophy.md lists as deliberate omissions. Before committing, run scripts/install_deps.sh on your distribution, build with make, and confirm that the provider you intend to use appears under /provider after you set its API key. The last push to master was on 2026-09-14 and the most recent tagged release is v0.5.0, so the project is moving; pin a release rather than tracking master if you package it.

Frequently asked questions

What is hax and who is it for?

hax is a minimalist, terminal-native coding agent written in C and shipped as a single native binary. The README targets developers who live in the terminal, run local models, audit what their tools do, package software for distributions, or run agents where resources are scarce.

How do I install hax?

On macOS or Linux you can use brew install oleksandrchekhovskyi/hax/hax, and on Arch Linux it is in the AUR as hax. Otherwise download the prebuilt static binary for x86_64 or aarch64 from the latest release, or build from source with scripts/install_deps.sh followed by make, which leaves the binary at ./build/hax.

Does hax work with local models?

Yes. Start llama-server with your GGUF model, then run hax with the llama.cpp provider, and the README states that hax auto-discovers the model and runtime capabilities without a custom provider config block. Ollama is also listed as a provider, started with ollama serve.

Which providers does hax support?

OpenAI and compatible endpoints, Anthropic and compatible endpoints, Codex via a ChatGPT subscription, OpenRouter, OpenCode Zen and Go, llama.cpp, and custom endpoints. You can also run ollama serve. The easiest first run is interactive: start hax and use /provider to choose.

Can I see what hax sent to the model?

Yes. Ctrl+T opens a transcript view showing what was sent to the model and what it replied, and the README says you can optionally collect a detailed wire protocol trace. docs/debugging.md covers trace and transcript logs, a mock provider, and demo scripts.

Does hax run on Windows?

The README says hax runs on Linux, macOS, FreeBSD and OpenBSD, and that on Windows you should use it under WSL. The BSDs build from source only.

Official sources

  1. License: MIT
  2. OleksandrChekhovskyi/hax on GitHub
  3. Project website
  4. README
  5. Releases
Community notes

Community notes