Connect OpenCode, pi, and DeepSeek Harness to the same model and compare the differences between model-agnostic coding agent harnesses

Connect OpenCode, pi, and DeepSeek Harness to the same model and compare the differences between model-agnostic coding agent harnesses

I researched the design philosophies and behavioral differences among three coding agent harnesses that allow model swapping: OpenCode, pi, and DeepSeek Harness. I then connected the same model to each and had them solve the same task, organizing the basis for choosing a harness.
2026.09.14

This page has been translated by machine translation. View original

Introduction

Hello, I'm Shimada from Classmethod's Manufacturing Business Technology Division.

In August 2026, DeepSeek released DeepSeek Harness.
There have been several model-swappable coding agents for a while, and Codex CLI is one made by a model company.
This article covers three tools: OpenCode (the most widely used), pi (which I use daily), and DeepSeek Harness (the newest).
While I use pi regularly, I wanted to properly understand what the other two changed and how, and what distinguishes all three from Claude Code or Codex CLI in the first place.

First, I'll organize the backgrounds and design differences of the three tools.
Next, I'll cover "what happens when you load Claude or OpenAI models onto these harnesses," split into two relevant background stories and one piece of reasoning about model-harness compatibility.
Finally, I'll connect all three to the same model, give them the same task, and observe the differences in behavior.

The information in this article is current as of September 14, 2026.
The confirmed versions are OpenCode 1.18.30, pi 0.85.1, and DeepSeek Harness 0.1.5-rc.1.
DeepSeek Harness is in developer preview, and the README explicitly states that breaking changes may occur.

What Is a Harness

A harness is a collective term for the layer that sits outside the model itself.
It includes tool definitions, system prompts, context management, session storage, permissions, and sandboxing.
The DeepSeek Harness design document describes this as "Agent = Model + Harness."

A configuration in which a harness, receiving requests from a developer, holds a system prompt, tool definitions, sessions, and permissions, while exchanging requests and tool calls with the model and reading and writing to the working directory
The harness sits outside the model and mediates the back-and-forth with the model and the reading and writing to the working directory

Claude Code and Codex CLI are harnesses that model companies built for their own models.
The three tools covered in this article were built without assuming a specific model.
Both share the same structure, and some tools like Codex CLI allow you to point to other companies' models via configuration, but the difference lies in whether the model and harness were designed simultaneously by the same company.
This distinction is the premise for the discussion in the latter half.

The Background and Design of the Three Tools

OpenCode pi DeepSeek Harness (dsh)
Author Anomaly Innovations Mario Zechner DeepSeek
Released 2025 2025 August 13, 2026 (developer preview)
License MIT MIT MIT
Design philosophy Everything included Minimal Everything as plugins
Default tools bash, edit, write, read, grep, glob, lsp, apply_patch, skill, todowrite, webfetch, websearch, question read, write, edit, bash bash, read, write, edit, glob, grep, str_replace_editor, skill, todo, subagent, web, and others
What's omitted Nothing in particular MCP, sub-agents, plan mode, permission popups, TODO, background bash Fixed workflow
How to extend plugins, MCP, agents, skills TypeScript extensions, Skills, prompt templates, themes Plugin replacement on top of Cordis
Sessions client/server. Shared across TUI, desktop, and IDE JSONL tree. Branching and rewinding Append log. resume, fork, search, replay
Non-interactive execution opencode run pi -p dsh --profile headless

OpenCode is a harness developed by Anomaly Innovations, the creator of SST, aiming for the same usability as Claude Code.
It comes with LSP auto-loading, MCP, multiple agents, and plugins from the start.
A single server process drives the TUI, desktop app, and IDE extension in a client/server configuration, so you can run opencode serve as a resident process and connect to it from another client.

OpenCode's TUI with the model selection open, showing providers like Switchyard with options like weak-only
OpenCode's TUI. Adding a provider immediately shows up in the model selection

Some articles describe OpenCode as being written in Go, but this is a confusion of histories.
The original Go implementation moved to Charm and became a separate project called Crush, while the current OpenCode was rewritten in TypeScript.

In terms of billing, there are three paid plans: Zen (pay-as-you-go per model), Black (using Claude via an API-billing gateway), and Go (open-weight models only).
The reason for this structure is explained in the next section.

pi Is a Minimal Harness with Only Four Tools

pi is a harness developed by Mario Zechner, known as the creator of libGDX.
It has just four default tools — read, write, edit, and bash — and its system prompt is kept short as well.

pi intentionally omits MCP, sub-agents, plan mode, permission popups, TODO, and background bash.
The README explains the rationale for each omission: MCP can be replaced with a CLI tool or extension, sub-agents with tmux or an extension, and permissions with containers.
It's designed so that missing features can be added via TypeScript extensions, and indeed, packages like MCP adapters, sub-agents, and permission control extensions have been published around pi.

Sessions are saved as a JSONL tree, allowing you to branch from any point and try again from there.
Compaction is also done without deleting history, so you can return to the original branch.

pi's /tree screen showing multiple branches from a single session displayed as a tree
pi's /tree. You can reselect a branched path and continue from there

DeepSeek Harness Is a Model-Agnostic Harness Released by the Model Company

DeepSeek Harness is a harness released by DeepSeek on August 13, 2026, under the MIT license, with the command name dsh.
Built on top of a dependency injection framework called Cordis, it treats everything as plugins — model adapters, tool registration, sessions, the agent loop, sandboxing, and the UI.
In the 0.1.5-rc.1 I installed locally, more than 300 packages were bundled under the @deepseek-ai scope.

One surprising discovery was that the multi-provider layer of DeepSeek Harness is a package from pi.
A plugin called dsh-llm-pi-ai depends on @earendil-works/pi-ai from pi's repository, and connections to OpenAI-compatible or Anthropic-compatible endpoints are handled there.
DeepSeek's own models have a separate dedicated adapter alongside it.

Another notable feature is that plugins for loading Claude Code's and Codex's hooks.json respectively are bundled.
This means there is room from the very start to bring in configuration assets written for other harnesses.

The DeepSeek Harness Web UI showing a model selection screen with models from added providers listed
dsh's Web UI. Once you add a provider, you can select models just like with OpenCode or pi

What Happens When You Load Claude or OpenAI Models onto These

You sometimes hear statements like "it's not appropriate to load Claude or OpenAI models onto these harnesses."
On closer inspection, this single statement mixes together discussions of different natures.
One is the background of decisions made separately by Anthropic and OpenAI.
The other is reasoning about model-harness compatibility, which serves as a basis for choosing a harness.
I'll address each in turn.

Anthropic Blocked Subscription Misuse Through Its Terms of Service

On January 9, 2026, Anthropic blocked server-side the route by which OAuth tokens issued for Claude Pro and Max subscriptions could be used from third-party tools.
Users of OpenCode, Cline, and Roo Code were affected.
In February, the Legal and compliance documentation for Claude Code was updated to explicitly state that third-party developers must use API keys issued through Claude Console and must not route requests on behalf of users using credentials from Free, Pro, or Max plans.
On April 4, subscription usage quotas themselves became unavailable for use in third-party harnesses.

The reasons Anthropic cited were that the fixed-cost plan's compute resources were being consumed in autonomous loops without going through pay-as-you-go billing, that clients were sending headers claiming to be the Claude Code client to pass authentication, and the associated technical instability.

An important distinction here is that what was prohibited was use via subscription — not Claude itself.
The pay-as-you-go route using an API key still works.
OpenCode Black is a product that sells Claude access via an API-billing gateway.
In other words, the accurate statement is not that Claude "can't be used" with these harnesses, but that it "can't be used with a flat-rate plan, so it becomes more expensive."

OpenAI Permitted Use from Third-Party Harnesses

OpenAI moved in the opposite direction.
OpenAI executives Tibo Sottiaux and Sam Altman have publicly stated that ChatGPT Plus and higher subscriptions may be used from third-party harnesses such as pi and OpenCode.
Sottiaux also noted that pi and OpenCode each account for 5% of Codex traffic respectively.
While there is no explicit permission written into the terms of service, the direction from the company's leadership is to allow it.

Therefore, writing that Claude and OpenAI should both not be used with third-party harnesses is inconsistent with the facts.
The terms-of-service issue is specific to Anthropic.

Model-Harness Compatibility Shows Up as Benchmark Differences

Separate from the background stories, there is reasoning that serves as a basis for choosing a harness.
It's the idea that a model's performance is determined not by the model alone, but by the combination of model and harness.

You sometimes see explanations that each company's model has been post-trained on top of its own harness, with the tool vocabulary baked into the weights.
The clearest example is the file editing tool.
Codex CLI edits using a patch format called apply_patch, while Claude Code edits by passing old_string and new_string to the Edit tool in a string replacement approach.
Even the names of the context files they recognize differ — CLAUDE.md versus AGENTS.md.
The explanation here is that when a model is given a tool format it's unfamiliar with, it uses more tokens for inference and makes more mistakes.

There is published data comparing the same model and the same benchmark with only the harness changed.
Terminal-Bench is a benchmark that tests multi-step tasks in a terminal environment, and up through version 2.1, the operators also published scores for their reference agent implementation Terminus 2.

Condition Terminal-Bench 2.1
Claude Opus 4.6 + Claude Code 70.1%
Claude Opus 4.6 + Terminus 2 63.8%

Even with the same model, there's a 6-point difference between the official harness and a general-purpose harness.
As of September 2026, Terminal-Bench 4.0 is the latest version, but from 3.0 onward, only results running each model with a single harness are listed — there are no rows comparing the same model across different harnesses.
Since 2.1 is the last version with Claude Code and Terminus 2 side by side for the same model, I'm using the 2.1 figures here.
The arXiv paper Harness-Bench also ran 5,194 executions across multiple model-harness combinations and concluded that both completion rates and failure patterns vary significantly by model-harness pairing.

However, the causal claim that "the difference arises because of post-training" is, within the scope of what has been publicly shared, an inference.
The existence of the difference has been measured, but I could not find an experiment that isolates the cause.

Two conclusions can be drawn from this.
Loading Claude or GPT onto a harness that isn't from the lab that made them will result in performance that varies by combination, so you need to re-measure.
And open-weight models that don't have a dedicated harness, or have one but don't lock it down (GLM, Kimi, DeepSeek, Qwen), can be combined with model-agnostic harnesses without friction.
I think OpenCode Go emerging as a plan exclusively for open-weight models is a reflection of this situation.

How to Classify Similar Tools

Sorting tools that seem to belong in the same category by their relationship to models looks like this:

  • Built by the model company for their own models: Claude Code, Codex CLI, Gemini CLI, Copilot CLI. These are the ones designed alongside the model. Codex CLI and Gemini CLI have open-source code, and Codex CLI can be configured to point to other companies' endpoints, but the starting point of their design is their own models.
  • Model-swappable OSS for the terminal: OpenCode, pi, Crush, Aider, Goose. The main subject of this article.
  • IDE extensions: Cline, Roo Code, Kilo Code, Cursor. These were affected by the January blockade in the same way as OpenCode.
  • Autonomously running residents: OpenHands, OpenClaw, Hermes. Designed to receive requests from Slack and similar services and act on them.

DeepSeek Harness sits between the first and second categories.
It was released by the model company, but the layer responsible for connecting to other companies' models is a pi package, with the adapter for DeepSeek's own models placed separately alongside it.
The fact that tools and sessions can also be swapped out as plugins is characteristic of the second category.
When you also consider that DeepSeek released the harness for free the same week it raised the prices on its own model's API, the contrast between Anthropic locking down its harness and DeepSeek and OpenAI opening theirs up makes their positioning easier to understand.

Connecting All Three to the Same Model and Giving Them the Same Task

To see how the design differences manifest in behavior, I connected all three to the same model and had them solve the same task in non-interactive mode.

Connection Target

I used the OpenAI-compatible endpoint of NeMo Switchyard running in a local Docker container as the model entry point.
I pointed all three at Switchyard's weak-only route in the same way, and confirmed from the responseModel in the session logs that the actual model was DeepSeek V4 Flash (0731) on Fireworks AI.
Since the model is the same, any differences that emerge are differences on the harness side.

A configuration in which OpenCode, pi, and DeepSeek Harness all connect to NeMo Switchyard's weak-only route via the OpenAI-compatible API, and Switchyard relays to DeepSeek V4 Flash on Fireworks AI
All three connect to the same Switchyard route, with the actual model kept identical

Registering an OpenAI-compatible endpoint is done with a single configuration file for all three.
The format differs for each.

For OpenCode, you write it in opencode.json in the project root.
For a Chat Completions format endpoint, specify @ai-sdk/openai-compatible.

opencode.json
{
  "$schema": "https://opencode.ai/config.json",
  "provider": {
    "switchyard": {
      "npm": "@ai-sdk/openai-compatible",
      "name": "Switchyard",
      "options": {
        "baseURL": "http://127.0.0.1:4100/v1",
        "apiKey": "{env:SWITCHYARD_API_KEY}"
      },
      "models": {
        "weak-only": { "name": "weak-only", "limit": { "context": 262144, "output": 16384 } }
      }
    }
  },
  "model": "switchyard/weak-only"
}

For pi, you write it in ~/.pi/agent/models.json.

~/.pi/agent/models.json
{
  "providers": {
    "switchyard": {
      "baseUrl": "http://127.0.0.1:4100/v1",
      "api": "openai-completions",
      "apiKey": "$SWITCHYARD_API_KEY",
      "models": [
        { "id": "weak-only", "input": ["text"], "contextWindow": 262144, "maxOutputTokens": 16384 }
      ]
    }
  }
}

For DeepSeek Harness, you write in ~/.dsh/settings.yaml (the location can be changed with DSH_HOME), using plugin IDs as keys.
The reason the api: openai-completions specification has the same name as in pi is because, as mentioned earlier, the underlying implementation is a pi package.

~/.dsh/settings.yaml
llm-pi-ai:
  providers:
    switchyard:
      apiKeyEnv: SWITCHYARD_API_KEY
      api: openai-completions
      baseURL: http://127.0.0.1:4100/v1
      models:
        - id: weak-only
          contextWindow: 262144
          maxTokens: 16384
          input: [text]
agent-default-model:
  provider: switchyard
  model: weak-only
session-telemetry-otel:
  mode: DISABLED

The Task

The task was a small Python CLI fix.
I introduced two bugs into a script that counts word frequencies in a text file: punctuation attaching to words, and uppercase and lowercase letters being counted separately.

TASK.md
wordfreq.py has 2 problems. Punctuation attached to the beginning and end of words is being counted as part of the word, and uppercase and lowercase letters are being counted as separate words.
Please do the following:
1. Fix count_words so that it strips punctuation and counts words case-insensitively
2. Add a `--top N` option to display only the top N results
3. Add pytest tests to tests/test_wordfreq.py (at least 3 cases covering the 2 fixed issues and --top)
4. Run pytest and confirm all tests pass
When finished, briefly report the files changed and the confirmation results.

I prepared three identical directories and passed this text to each in non-interactive mode.

opencode run --pure --format json -m switchyard/weak-only "$(cat TASK.md)"
pi -p --mode json --no-extensions --no-skills "$(cat TASK.md)"
dsh --profile headless "$(cat TASK.md)"

OpenCode's --pure and pi's --no-extensions are specified to disable external plugins and compare the bare harnesses.
DeepSeek Harness's headless profile runs with the default workspace-write mode (only writes within the working directory are permitted).

Results

All three completed the task from start to finish, reported the changed files and confirmation results, and terminated.

OpenCode pi DeepSeek Harness
Time taken 68 seconds 45 seconds 71 seconds
Number of requests to model 19 6 13
Tool calls 19 (bash 7, edit 7, read 2, write 2, glob 1) 7 (read 3, bash 2, write 2) 14 (bash 5, read 4, edit 3, write 2)
Input tokens for first request 8,084 1,744 7,626
Total input tokens (including cache reads) 238,856 19,899 148,638
Total output tokens 4,617 2,007 4,277
Tests added 8 6 8
Reported pytest result 8 passed 6 passed 8 passed

The output from all three works correctly.
The reports matched the actual results as well.
However, there are differences in the numbers.

The size of the first request directly reflects the size of the system prompt and tool definitions.
Since the task text is identical for all three, the difference between OpenCode's 8,084 tokens and pi's 1,744 tokens is the difference in the preamble that each harness passes to the model.
DeepSeek Harness had an amount close to OpenCode.
This difference accumulates with every request, so in total input tokens, OpenCode ends up at roughly 12 times pi's count.
If prompt caching is available on your route, the impact on cost will be smaller, but with a local model, it directly adds to the prefill time for each request.

Guidelines for Choosing Between Them

These are rough guidelines based on my hands-on experience with all three.

  • OpenCode: When you want to keep the same feel as Claude Code but swap out the model. LSP, MCP, and IDE integration are available from the start. The tradeoff is a larger preamble per request, and that weight becomes visible with local models.
  • pi: When you want to keep the preamble small, or when you want to understand exactly what the harness is doing. Since it's designed with the expectation that you'll add missing features via extensions, there's upfront effort in making your own choices. Because you start from a minimal setup and add things yourself, this is the one I use most.
  • DeepSeek Harness: When you want to experiment by swapping out tools, sessions, and sandboxing at the unit level. Even though it's a developer preview, I found the Web UI polished enough to be practical.

As I mentioned earlier, none of these allow you to use Claude with a flat-rate plan, so if you want to use Anthropic's models, it's best to use Claude Code or Claude Code on the web.
If you're using these harnesses, the options as of September 2026 are: Claude via pay-as-you-go with an API key, OpenAI models via a ChatGPT subscription, and everything else via open-weight models through an API or locally.

Closing

OpenCode, pi, and DeepSeek Harness are all model-swappable harnesses, but their design philosophies differ: everything included, minimal, and everything as plugins.
On investigation, I found that even with a closed model like Opus, benchmark scores change depending on which harness you run it with.
When I actually connected all three to the same model and ran them, differences appeared in time taken and token consumption as well.
I also didn't know until I looked into it that DeepSeek Harness's provider layer is a pi package.

Beyond the three covered in this article, coding agent harnesses continue to appear one after another.
If something catches your attention, try it out yourself and find what suits your workflow.

References


Claudeならクラスメソッドにお任せください

クラスメソッドは、Anthropic社とリセラー契約を締結しています。各種製品ガイドから、業種別の活用法、フェーズごとのお悩み解決などサービス支援ページにまとめております。まずはご覧いただき、お気軽にご相談ください。

サービス詳細を見る

Share this article

AI白書