Built in RustOpen source
nharnessedA new generation of harness.
One tool: a Python REPL. The model writes the rest.
Higher score. Lower bill.
Same model, different harness: with Claude Opus 5.5, Unharnessed passes 47 of the 66 tasks. Each point is one run of Terminal-Bench 4.0: its score against what a task cost.
- Unharnessed
- Claude Code and Codex, top 5 models
- Other runs
The more capable the model, the less harness it needs.
Every hardcoded tool is a decision made in advance, on the model’s behalf: what a read returns, how an edit is shaped, how much output survives. That was a fair trade when models needed rails. Each generation needs fewer.
Unharnessed is built for where that curve ends: one tool, and nothing left to take away.
Use the subscription you already pay for.
Unharnessed is free. Sign in with your browser, from the panel, and requests draw on your plan’s limits: no API key to create, no second bill.
- ClaudePro / Max
- ChatGPTPlus / Pro
- GitHub CopilotYour Copilot plan
- Google AIPro / Ultra
- GrokxAI account
Or bring a key
API keys and cloud accounts
- Anthropic
- OpenAI
- Google Gemini
- Google Vertex AI
- Amazon Bedrock
- Azure OpenAI
- Mistral
- xAI
- DeepSeek
- Groq
- Cerebras
- Fireworks
- Hugging Face
- OpenRouter
- Vercel AI Gateway
- Cloudflare AI Gateway
- Cloudflare Workers AI
- Moonshot AI
- Kimi For Coding
- MiniMax
- ZAI
- Xiaomi MiMo
- OpenCode Zen
- OpenCode Go
- Prime Inference
Or run it yourself
Model servers on your machine
- Ollama
- LM Studio
- llama.cpp
- vLLM
- Any OpenAI-compatible server
One tool: a Python session that stays open.
- 1
One call does the work of many.
Frontier models reach for Python anyway. With a tool list, each call does one thing and costs a round trip: the model waits for the result, reads it, then makes the next. Here one call is a script: read a file, search the repository, change forty places, check the result. Fewer round trips, fewer turns.
With a tool list4 round tripsModelYour machineReadSearchEditCheckDoneUnharnessed1 round tripModelYour machineRead, search, edit, checkDone - 2
What it reads stays in Python, not in its context.
With tool calls, every result is poured into the context and stays there: read a long log, and the model carries it for the rest of the task. Here the log lands in the session, under a name. The model looks at the ten lines it needs and the rest stays within reach. The session is a kernel, like Jupyter’s: it stays alive between calls, and so do its variables. A server the model starts keeps running there too.
Your repositoryPython sessionModel’s contextWith a tool list40,000 lines in contextNothing keptServer log40,000 linesall 40,000 linesUnharnessed10 lines in contextServer log40,000 linesServer logkept, under a namethe 10 lines it needed - 3
It writes the functions it needs.
Not new tools: plain Python functions, kept as variables in the session. The model calls one again whenever it needs it, rewrites it or deletes it, like any other variable. Run across 200 files, that is one loop in one call. A fixed tool list takes 200 calls, and puts 200 results in the context.
Your repositoryPython sessionModel’s contextWith a tool list200 callsNothing kept200 files200 resultsUnharnessed1 call200 filesFind flaky testsa variable in the session3 flaky tests - 4
The context gets compacted. The session carries on.
A long task outgrows the context, and the harness has to summarise it. What lived only in the conversation is gone. What lives in the session is still there: the data, the running server, the functions it wrote. Resume the session another day and the data and the functions come back.
Python variablesModel’s contextWith a tool listOnly a summary leftNothing kept outside the contextCompactedeverything it reada summary; the rest is goneUnharnessedEverything still thereServer logTest resultsDev serverFind flaky testsstill thereCompactedwhat it looked ata summary
Code mode calls the tools it was given. Here the model writes its own.
Droid, Pi, Codex and Reason now let the model write a script. But that script only calls the tools the harness already built: the same fixed list, called from code.
Here there is no list to call. The model writes the code that does the work, and keeps what it wrote as functions for the next time.
What we didn’t build.
-
No sub-agents
To hand work to a sub-agent, the main model has to write it a brief, and a brief is never the whole task. The sub-agent starts from zero, spends tokens finding out what the first model already knew, then sends back a summary of what it found. Something is lost at each hand-off.
Here, the model that holds your task makes every call itself. What it needs to know, it reads first-hand.
-
No memory
A memory is the agent keeping notes about you from one session to the next. The notes pile up and are loaded every time, so they take context whether they matter or not. And they don’t expire when you change your mind: the old preference is still in there, arguing with what you ask today.
Here, a new session starts from your repository and your request. What should always hold, you write yourself in
AGENTS.md, where you can read it and delete it. -
No permission prompts
Most harnesses stop before a command and wait for you to approve it. Nothing moves until you are back at the screen.
Unharnessed never blocks a call, so a goal can run on its own. It is a bet, taken early: models keep getting better at judging what is safe to run, and a harness built around asking would have to be taken apart later. Today it is the riskier choice; until the bet is won, run it in a container.
A minimal system prompt
Every rule in a system prompt is a decision made for the model, and it sits in the context on every turn.
Ours says what the one tool is and how to use it, once. The rest of the room is the model’s.
Async by default
In most harnesses, a command holds the model until it ends: a ten-minute build is ten minutes of waiting.
Here every command starts in the background and hands back a handle. The model keeps working, and is told when the command is done.
Just the harness
A harness that comes as an app of its own, or as a new IDE, has to rebuild what your editor already does: Git, diffs, a terminal. And to use it, you leave your setup for its own.
Unharnessed is a VS Code extension: one panel on the side, with your conversations. Your Git, your extensions and your workflows stay as they are, and all our work goes into the harness.
Why not a CLI?
A terminal only shows text: tool calls drown in it, Markdown renders poorly, and you work hard for very little.
An extension has a real interface: you see each tool call clearly, Markdown renders properly, and you can drop an image straight into the message. It is simpler, and it looks better.
Take the harness off.
Give the model a Python kernel and get out of its way.