pi2dsh README

The project's README from github.com/weijiafu14/pi2dsh. As one markdown file: README.md.

pi2dsh

English | 中文

Run the Pi ecosystem's plugins on DeepSeek Harness, unmodified.

dsh plugin add pi2dsh          # once
dsh plugin add <any-pi-plugin> # then any Pi plugin, straight from npm

Why this exists

DeepSeek Harness is built on ideas worth betting on — a durable, reconstructable session log, a clean service composition, an agent loop you can actually reason about. What it does not have yet is a large plugin ecosystem: it is early, and the plugins people want on day one — web search, memory, code navigation, subagents, vision — are mostly not written for it yet.

Pi has that ecosystem already, and it is mature: hundreds of published packages, many with real users.

pi2dsh is one compatibility layer that implements Pi's public extension ABI on top of DSH's native services, so a Pi package runs on DSH as published — no fork, no patch, no per-package adapter. You install a Pi plugin the same way you install anything else in DSH, and it works.

At the same time, pi2dsh is an ongoing, full-surface, real-world test of DSH's architecture. Instead of patching individual plugins, it asks whether the models, tools, sessions, interaction, resources and client capabilities that Pi plugins rely on can preserve their logic and lifecycle using only DSH's public services and extension seams. If they can, that is strong evidence that DSH's architectural goals for building agents and an agent-plugin ecosystem have been achieved, at least along this dimension. Wherever the bridge must bypass, degrade or cannot express a capability, it pinpoints an architectural gap that remains.

Install

One engine, then whatever plugins you want:

dsh plugin --profile web add pi2dsh
dsh plugin --profile web add pi-mcp-adapter

Then restart dsh — plugins mount at startup.

A profile needs a surface bundle. DSH's built-in templates are web and headless. A custom profile is valid when its product installs a surface — for example @deepseek-harness-tui/dsh-tui in the dsh-tui profile. A bare arbitrary profile has no surface and can start with nothing to drive it, so add the intended surface to dsh.profile.bundles first.

That is the whole model. There is no conversion step, no generated bundle, no build. The engine discovers the Pi packages in your profile (every one is something you explicitly added) and mounts them through a single bridge instance: one model directory, one login, one credential store, one upgrade unit.

Day-to-day:

Task Command
Add a plugin dsh plugin add <pkg> (then restart dsh)
Remove a plugin dsh plugin remove <pkg> — remove plugins before removing the engine
Upgrade a plugin dsh plugin add <pkg>@latest — the engine is untouched
Upgrade the engine dsh plugin add pi2dsh@latest — your plugins are untouched
Check a plugin before upgrading npx pi2dsh inspect <pkg>@<version>

Two installer messages worth knowing:

Requires Node.js 22.19+ and DeepSeek Harness.

Engine configuration

The engine reads one config block from its plugin row. Today it takes a single opt-in:

# $DSH_HOME/profiles/<profile>/cordis.patch.yml
- id: pi2dsh
  config:
    serveNativeSubagents: true

serveNativeSubagents (default: off) serves DSH-native subagents with the profile's Pi packages. With it on, a child agent DSH spawns through its own subagent delegation (one whose session carries the subagent origin) receives every discovered Pi package mounted on its own agent scope — the package's tools, commands and prompt sections appear for that child only, and every contribution unwinds when the child ends. With it off, such children run as plain DSH agents, exactly as before.

The mount is guaranteed for the child's first turn: prompt assembly and tool execution wait for it, so even a child that runs a single turn sees the full tool set. Each child is served exactly once, whichever path DSH created it through — children the agent registry reports as runtime roots are served by the engine's root mount path, and the subagent path serves the rest; the two never overlap. Pi subagent-bridge children are unaffected either way: they already receive the creator package's own per-spawn loader mount, and the bridge recognizes them by the pi2dsh-sub- session-id prefix (stable across a persisted resume), so no child is ever mounted twice.

Walkthrough: advanced MCP in your terminal

The clearest example of what the bridge buys you. dsh-TUI ships a native /mcp command for DSH's official MCP client — it works, and it stays untouched. The Pi ecosystem has a much richer MCP power tool: a full-screen server manager, lazy tool discovery, one proxy tool instead of flooding the model context with dozens of tools, JavaScript orchestration of multiple MCP calls, OAuth logins, resources and prompts. With the bridge, that package runs unmodified.

1. Install

dsh plugin --profile dsh-tui add @deepseek-harness-tui/dsh-tui   # skip if the profile exists
dsh plugin --profile dsh-tui add pi2dsh
dsh plugin --profile dsh-tui add pi-mcp-adapter

Or use the same unmodified Pi packages in dsh-pi-tui:

dsh plugin --profile pi-tui add @xmoon76/dsh-pi-tui
dsh plugin --profile pi-tui add pi2dsh pi-mcp-adapter @tintinweb/pi-subagents
dsh --profile pi-tui

That composition keeps dsh-pi-tui's native /login and projects Pi OAuth flows into it, mounts the original MCP manager through the public piTuiExtensions surface, and exposes the original Pi subagent flow at /agents. See examples/pi-tui-ecosystem.

Then restart dsh — plugins mount at startup.

2. Configure your MCP servers

Inside dsh-TUI, run:

/pi-mcp setup

The setup flow can adopt MCP server definitions from host configs you already have into the adapter's own standard mcp.json. No bridge-specific configuration exists — everything you touch is the package's own surface.

3. Use it

/pi-mcp

opens the full-screen interactive server manager — its footer documents the keys for enable/disable, reconnect and OAuth login. The model receives the adapter's mcp and mcpScript tools through DSH's normal tool registry, and each agent (/new included) gets its own fully connected instance.

dsh-TUI's native command remains separate, and both stay available:

/mcp       # native DSH MCP-client status
/pi-mcp    # the installed Pi adapter's manager

What is verified behind this walkthrough: 16 host-influenced capabilities end to end on the stock npm stack — three real transports, discovery, proxy and hot-loaded direct tools, mcpScript, resources, prompts, images becoming real DSH attachments, MCP Apps, tool approval through DSH questions, elicitation, sampling against the real DSH model runtime, cancellation and session restart. The full evidence matrix: docs/mcp-compatibility.md.

Full runnable version: examples/tui-mcp.

What actually works today

Two levels, and they are not the same claim.

Level 1 — verified end to end, with a runnable example

Someone sat down, used the plugin's real feature on a real DSH loop, and saw it work. This is the list to trust.

Plugin What was exercised Where Example
@kassing/pi-vision Image analysis delegated to a vision model; image-admission companion route; analysis injected into a text-only model's turn CLI + web vision-bridge
@crazygit/pi-codex-image-gen ChatGPT/Codex OAuth → gpt-image-2 generation; local reference-image upload through DSH approval; image edit; native attachment storage and inline Web rendering CLI + web codex-image-gen
pi-btw /btw <question> as a real child session in DSH's subagent UI; /btw-inject; /btw --save; main thread stays clean CLI + web side-conversation
pi-powerline-footer A terminal status line — model, thinking level, project, context usage — drawn as a floating status pill in DSH web, colour included web presentation-surfaces
pi-mcp-adapter Original full-screen manager; stdio/Streamable HTTP/SSE; discovery, direct/proxy/scripted calls, resources, prompts, images, structured content, MCP Apps, approval, elicitation, sampling, cancellation and restart through DSH runtimes CLI + web + dsh-TUI + dsh-pi-tui tui-mcp · mcp-at-scale · pi-tui-ecosystem · evidence matrix
@tintinweb/pi-subagents The model delegates to autonomous subagents: spawn (with real host-native tools), background + completion notify, mid-run steer, wait-for-result, resume with memory, stop that stays stopped, interactive manager, and cross-restart reopen by archive identity — every child a native DSH session CLI + dsh-TUI + dsh-pi-tui subagents · pi-tui-ecosystem · acceptance report
pi-provider-alibaba Alibaba Token Plan (CN) with its plan-specific key: live catalog, cold-start dynamic model, complete tool loop and restart. The package also declares Coding/API routes, but each requires its own non-interchangeable credential CLI + web alibaba-token-plan
@ff-labs/pi-fff + pi-lens Code navigation for the model: ffgrep content search finds a marker that exists in exactly one file, and lsp_diagnostics reports a planted TS2322 through a real local typescript-language-server — both asserted from the tools’ own results in the session log CLI + web code-navigation
pi-vision-tool Tool registration through a JSON-Schema shape DSH had to convert (anyOf → oneOf) CLI + web —
pi-approval-guardian Every tool call reviewed by a second model before execution; allow and deny both observed CLI (bare env) —
pi-hermes-memory Cross-session memory end to end: memory_add in one session, recalled in a second, fresh one (the codeword existed nowhere else); five tools, ten /memory-* commands, system-prompt memory injection CLI persistent-memory
pi-background-tasks Background shell job started with bg_run, output read mid-run with bg_logs: the log result carries early ticks of a still-running 60-second job, with the final tick provably absent CLI background-tasks

Examples for the two remaining rows are still to be written; per this project's own rule they get re-verified from scratch before an example lands, so the table says plainly which have one today.

Level 2 — mounts and its surface answers a probe

The Pi catalog's top 50 packages by monthly downloads, each mounted in a real DSH runtime and then called through a black-box probe. Status as of 2026-08-14; per-package machine-readable evidence in community/.

47 of 50 exercised successfully · 1 with no probeable surface · 2 pending a re-run.

What this level does not tell you: that the plugin's actual feature works the way you would use it. A probe calls a registered surface with synthetic arguments; a user runs a workflow. pi-btw is the cautionary example — it graded "working" here for weeks while /btw <question> failed on a real session, because the feature needed two ABI gaps closed (Pi's settable AgentState.messages, and an input descriptor on bridged commands) that no probe exercised. Both are fixed in 0.11.0, and both were general fixes that unlock every plugin doing the same thing.

So read the table below as "the bridge covers what this plugin touches", not as "this plugin is known-good". When you try one, a report either way is useful.

Area Packages
MCP pi-mcp-adapter · pi-mcp-extension
Web search & fetch pi-web-access · pi-deepseek-search · pi-web-search · @ollama/pi-web-search · @juicesharp/rpiv-web-tools
Code navigation & editing pi-lens (ast-grep) · @narumitw/pi-lsp · pi-readseek · @ff-labs/pi-fff · pi-landstrip · pi-hashline-edit-pro¹
Subagents & background work @gotgenes/pi-subagents · @mjasnikovs/pi-task
Memory pi-hermes-memory · pi-goosedump
Planning & goals @narumitw/pi-goal · pi-goal-list-loop-audit · @narumitw/pi-plan-mode · @juicesharp/rpiv-todo
Asking you / approvals @juicesharp/rpiv-ask-user-question · pi-ask-user · @gotgenes/pi-permission-system · @juicesharp/rpiv-advisor
Side conversations pi-btw · @narumitw/pi-btw
Models & providers pi-provider-litellm · pi-llama-cpp · pi-prompt-template-model · @vigolium/piolium
Images @kassing/pi-vision (see above) · @amaster.ai/pi-image-gen
External integrations @llblab/pi-telegram · pi-cursor-sdk² · @howaboua/pi-codex-conversion · pi-agent-browser-native² · pi-harness-runtime
Prompting & workflow pi-simplify · pi-fabric² · mitsupi · pi-cc-extensions · pi-rtk-optimizer · pi-interview¹
Terminal decoration pi-powerline-footer · @narumitw/pi-statusline · pi-zentui
Voice @juicesharp/rpiv-voice
Usage reporting @alexanderfortin/pi-deepseek-usage³

¹ Mounts; the exercise run is pending a re-run (a harness-side failure, not a package or bridge gap). ² Ran its own business logic end to end and rejected the synthetic probe arguments — working, correctly validating. ³ A pure event-hook package: all subscriptions attach, but every handler is gated on a live DeepSeek billing session, so a black-box probe has nothing safely callable to assert.

Packages outside the top 50 are not a separate case — the bridge has no per-package code. If one hits an ABI gap, fixing that gap unlocks every package that shares it.

Level 1 grows by working through Level 2 one plugin at a time. The full verification ladder, with what each rung does and does not prove: support matrix.

How it works

Three layers, and nothing crosses them:

┌─ Pi plugin ─────────────────────────────────────────────────┐
│ unmodified npm package. It sees a complete Pi host: the     │
│ three Pi runtime imports, registerX, ctx.*, 33 lifecycle    │
│ events. It never learns DSH exists.                         │
└──────────────────────────┬──────────────────────────────────┘
                           │  Pi's public ABI
┌──────────────────────────▼──────────────────────────────────┐
│ pi2dsh — the translator, and the only place that knows both │
│ vocabularies. Registry projection, event bridge, session &  │
│ subagent bridge, credentials, vendored Pi logic.            │
└──────────────────────────┬──────────────────────────────────┘
                           │  ordinary DSH plugin + llm adapter
┌──────────────────────────▼──────────────────────────────────┐
│ DeepSeek Harness. Sees a normal plugin. Never learns Pi     │
│ exists.                                                     │
└─────────────────────────────────────────────────────────────┘

DSH is two halves, and so is the bridge. The column above is the server; the browser shell has its own plugin surface, and a Pi capability that is a SHAPE rather than a behaviour lands there:

┌──────────── DSH server (cordis) ────────────┐  ┌──────── DSH browser shell ────────┐
│ services · waterfalls · durable events      │  │ dsh.client + exports "./client"   │
│                                             │  │ slot registry (ui-slots)          │
│ pi2dsh engine                               │  │   shell.overlay  ← panel, pills   │
│   tools · commands · models · sessions      │  │   session.header.utilities ← hdr  │
│   subagent bridge ─────────────┐            │  │   overlay ← widget pills/cards    │
│   browser-state registry       │            │  │   composer.dock ← working/footer  │
│     GET /pi2dsh/browser-state ─┼── own route┼──┼─▶ all four seats, one poller      │
└────────────────────────────────┴────────────┘  └───────────────────────────────────┘

The browser half's data rides this package's own route, not DSH's typed Remote system: that one is a first-party, code-generated contract, and an out-of-tree plugin talking to its own UI should carry its own channel. One payload per session serves every seat — the side-conversation panel, plus the Pi presentation surfaces (status, widget, header, footer, title and the working/thinking chrome), which are drawn in the host's own slot seats rather than re-implemented. Two host rules make the browser half load at all — the package must export ./package.json (the host resolves the manifest by subpath), and the ./client bundle is a closure-factory artifact, not plain ESM.

The rules that keep it honest:

pi2dsh (weijiafu14/pi2dsh)

migration
Searching Database…

218 ·GitHub
What is this?pi2dsh is a compatibility layer that runs Pi ecosystem plugins on DeepSeek Harness (DSH) unmodified — no fork, no patch, no per-package adapter. It implements Pi's public extension ABI on top of DSH's native services, so a Pi package installs and works on DSH exactly as published.
So is pi2dsh itself a DSH plugin, or a separate tool I run?It's itself a DSH plugin — the 'engine'. You add it once; it then discovers every Pi package in your profile and mounts them through a single bridge instance with one login, one credential store and one upgrade unit.
How do I get it running?Install DeepSeek Harness, then add the engine with dsh plugin add and restart dsh — plugins mount at startup. Add any Pi plugin the same way; there is no conversion step, no generated bundle, no build.
What do I need installed before it works?Node.js 22.19+ and DeepSeek Harness. Pi plugins are ordinary npm packages added through dsh plugin add, and your DSH profile needs a surface — the built-in web or headless templates, or a TUI bundle like dsh-tui.
Does every Pi plugin actually work on DSH once bridged?Two levels: about a dozen plugins (MCP adapter, subagents, vision, image generation, memory, code navigation, background tasks) are verified end to end with runnable examples, and 47 of the Pi top-50 packages at least mount and answer a black-box probe. A probe is not a feature guarantee — pi-btw looked fine for weeks while /btw still failed on real sessions.
Are there any install gotchas I should watch for?Two. pnpm blocks dependency build scripts by default (ERRPNPMIGNOREDBUILDS) — run pnpm approve-builds inside $DSHHOME/profiles/web or list the packages under allowBuilds, then re-run the add. And right after a release, pnpm's minimumReleaseAge can silently install an older version, so pin the version when adding.
What's the flagship example of what the bridge enables?The MCP walkthrough: Pi's pi-mcp-adapter — a full-screen server manager, lazy tool discovery, one proxy tool instead of dozens flooding the model context, scripted multi-call orchestration, OAuth logins — runs unmodified inside dsh-TUI next to DSH's native /mcp command. Sixteen host-influenced capabilities are verified end to end for it.
How do updates work — do I reinstall everything each time?No: upgrade a plugin with dsh plugin add @latest (the engine is untouched) and the engine with dsh plugin add pi2dsh@latest (your plugins are untouched). Remove plugins before removing the engine, and you can pre-check a plugin with npx pi2dsh inspect .
Why did the author build this instead of writing native DSH plugins?DSH is architecturally promising but early — it lacks the plugins people want on day one, while Pi already has hundreds of mature packages. The bridge doubles as a full-surface real-world test of DSH's architecture: wherever it must bypass or degrade a capability, that marks an architectural gap still to close.
Creator
weijiafu14
Size
49.1 MB
Stars
218
Age
2mo
Commits · 90 Days