Skip to content

About

Keep DSH plugins working across host upgrades: reads official upgrade guides directly, scans plugin code for breaking changes, smoke-tests in memory, scaffolds five plugin forms. Agent-native skill, zero dependencies

Topics

Resources

Stars

15 stars

Watchers

0 watching

Forks

Repository files navigation

plugin-fast-adapt

English | 简体中文 | 日本語

CI License: MIT Node Dependencies Self-test

Every time DSH ships a new release, existing plugins can stop working. This skill reads the vendor's official upgrade guide directly, scans your plugin code, and reports which breaking changes you hit together with the vendor's own fix instructions; it also scaffolds a runnable plugin from zero in one command and verifies it. Adapted through 0.2.2-rc.1, field-verified on 0.2.2-rc.2: rc.1 has no vendor guide entry yet, so its official Release Note is folded in as a virtual guide and coverage still reads complete; the rc.2 host — newer than every official npm channel at the time of testing — was verified live, where version resolution returned an honest ahead-of-upstream verdict and the export-surface diff across 391 core packages found zero removals. If a future version has neither a guide nor release notes, the ledger says outright that the scan cannot be called clean instead of pretending otherwise. Also features local environment anchoring, Release Note targeted extraction, and fleet multi-dimensional governance.

At a glance

Upstream ships a new release Works immediately, zero changes (reads vendor sources and release notes, no hand-curated cards)
DSH Host Compatibility Covers v0.1.7-rc.2 through 0.2.2-rc.1 (that version's official Release Note is converted into a virtual guide); host 0.2.2-rc.2 field-verified live while ahead of every official channel (391-package export-surface diff: zero removals). A newer version with no vendor source at all makes the coverage ledger say the scan cannot be called clean
Fleet Governance Board One-click sweep across Web/APP installed plugins & workspace code with life-cycle matrix
Version Authority Strictly anchors to the local installed host version by default (Plan B: 0 network requests)
Scan false positives 12 → 0 (four noise-reduction layers + word boundary regex + virtual guide deduplication)
Verifying one change 3,600 s real host cold start → millisecond-scale in-memory smoke test (with unbuilt check & host module fallback)
Ghost host Warns when the disk has new code but the running process still executes the old one (compares process start time, not version strings)
Fake-green check Warns when tsconfig paths point at a missing checkout, where TypeScript silently falls back to published types
Self-test 270 assertions, runs offline
External dependencies 0 (Node built-ins + the git/npm commands only)
Cross-platform Native support for macOS, Linux standard paths, Termux Android, and containers (XDG-compliant)
Scaffolding One command emits a runnable plugin in five forms, verified on creation, then a write gate issues the birth certificate

What problem it solves

DSH (DeepSeek Harness) is an AI runtime framework where everything is a plugin, and the trouble is that every new release can break existing plugins. The common workaround is hand-written upgrade cards: dozens of cards per version range, each recording what broke and how to fix it. That path has three problems it cannot get around:

  1. Cards go stale the moment they are written. A single upstream jump can touch thousands of files, and there are "corridor gaps" the cards never cover.
  2. A large knowledge base crowds out reasoning. In the paper's evaluation a weaker model (qwen3.8-27b) scored -3.07 pp worse with the full card library loaded (equal-weight difference over 56 tasks: 7 improved, 18 regressed, 31 flat).
  3. Verification is expensive. Every change needs a real host cold start (a 3,600-second timeout is on record), and stale packages left in the profiles overlay after a host upgrade break plugin loading.

This project takes a different approach: maintain the method of obtaining knowledge, not the knowledge itself. The authoritative description of breaking changes lives in the vendor harness repository at docs/upgrade-guide/<version>/<topic>/guide.md, updated with each release in a fixed format (## Change for what changed, ## Migration for how to fix it); version information lives in the npm registry's dist-tags. Both are vendor sources, so the skill catches up the moment upstream ships.

Advantages

  • Adapted through 0.2.2-rc.1, field-verified on 0.2.2-rc.2: reads the official docs/upgrade-guide/ and Release Notes directly. The guide stops at 0.2.2-alpha.3, so 0.2.2-rc.1 is covered by converting its official Release Note (27k+ characters, with a full breaking-changes section) into a virtual guide; that is why coverage still reads complete. The 0.2.2-rc.2 host — ahead of every official npm channel — was verified live on 2026-11-12: honest ahead-of-upstream resolution plus a zero-removal export-surface diff across 391 core packages. Also generates virtual guides and speeds up scans with a 3-tuple compatibility ledger
  • Local environment authority anchoring (zero network reliance): defaults to the locally installed DSH host version (Plan B, 0 external network requests), eliminating upstream network jitters and GitHub rate limits; uses --check-upstream for explicit check
  • Fleet multi-dimensional governance board: introduces fleet-sweep.mjs to inspect workspace code, installed Web plugins, APP desktop plugins, and active processes in a multi-stage life-cycle matrix, with --apply-compat batch safe patching
  • Hard guards against false positives & unbuilt traps:
    • Four noise-reduction layers + regex word boundaries (preventing ABORTED matching FS_ABORTED)
    • Virtual release note & official guide deduplication
    • Unbuilt TypeScript plugin hard gate (blocks and guides pnpm run build when missing lib/index.js)
    • Bundle Resolution Shadow detection for host-bundled packages
    • Exit code 143 (SIGTERM) acknowledged as graceful shutdown, eliminating false crash alarms
    • Auto Schemastery Config({}) parsing and temporary host node_modules fallback symlinking during smoke tests
  • Cross-platform & container ready: eliminates hardcoded directory assumptions, supporting Linux standard paths (/usr/lib/node_modules), Termux on Android ($PREFIX/lib/node_modules), npm_config_prefix, DSH_HOST_PATH / DSH_LOCATION env overrides, and XDG cache specs
  • Cheap verification: in-memory Cordis smoke test returns in milliseconds to seconds without a real host cold start; --real-smoke provides real-host isolated profile boot verification
  • Zero external dependencies: Node built-ins plus git/npm commands only
  • Reproducible: 270 assertions, runs offline; CI runs on ubuntu, macOS, and Windows
  • More than adaptation: scaffold.mjs emits a runnable plugin in five forms in one command, and write-gate.mjs issues a birth certificate
  • Silent failures have hard evidence: ghostHost compares process start time against disk change time; falseGreen catches TypeScript silent fallbacks
  • Honest about its limits: passing smoke test ≠ host compatibility, and the tool states this clearly in its output

Four lanes

The main entry only routes. Each lane owns one job, and the agent reads the matching document instead of loading all four:

SKILL.md                      main skill: pick a lane + one-shot pipeline + cross-lane discipline
sub-skills/adapt/SKILL.md     upgrade adaptation: resolve version → fetch guide → scan hits → seams → smoke → audit
sub-skills/build/SKILL.md     plugin authoring: scaffold five forms + write-gate birth certificate
sub-skills/diagnose/SKILL.md  environment and boot failures: env-doctor + log-doctor + env-heal
sub-skills/review/SKILL.md    code review and architecture audit: P0/P1/P2/P3 grading + sub-agent dispatch
scripts/                      shared toolbox for all lanes, not split per lane
references/                   noise rules, migration SOP, CI template

build, diagnose and review also ship optional top-level aliases so they can trigger on their own (they are not required — the main skill reads the lane document by intent):

ln -s <repo>/sub-skills/build    ~/.agents/skills/dsh-plugin-build
ln -s <repo>/sub-skills/diagnose ~/.agents/skills/dsh-plugin-diagnose
ln -s <repo>/sub-skills/review   ~/.agents/skills/dsh-plugin-review

The aliases exist so "author a plugin", "installed but not working" and "review this code" each get their own trigger surface instead of competing inside one description. Host loaders cap description at 1024 characters and drop the whole skill when it overflows (they do not truncate); the self-test now guards that limit.

Install

With the skills CLI (recommended — one command installs to every supported agent):

npx skills add taxueseek/plugin-fast-adapt

Claude Code marketplace:

/plugin marketplace add taxueseek/plugin-fast-adapt
/plugin install plugin-fast-adapt

npm (ships a plugin-fast-adapt command that forwards to the one-command pipeline):

npx plugin-fast-adapt <plugin-dir>

Manual install:

git clone https://github.com/taxueseek/plugin-fast-adapt.git
# Point your agent at the repository root (where SKILL.md lives) as a skill directory
# Cursor users: cp -r plugin-fast-adapt/* .cursor/skills/plugin-fast-adapt/

Pipeline

1. Single Plugin Pipeline (run.mjs)

Run the whole chain with one command (recommended); every run writes a local log and updates the compatibility ledger:

node scripts/run.mjs <plugin-dir>        # env → version → guide → scan → build-check → audit → smoke → typecheck
node scripts/run.mjs <plugin-dir> --check-upstream # explicitly check upstream npm registry and release tags
node scripts/run.mjs <plugin-dir> --real-smoke   # plus one more tier: install & boot in a clean profile (bridges upstream verify-runtime)
node scripts/run.mjs <plugin-dir> --offline      # skip fetching vendor sources (no npm read, no clone); local all-step pipeline
node scripts/run.mjs <plugin-dir> --no-clone     # resolve the version but do not fetch the guide (use an existing local clone)
node scripts/run.mjs <plugin-dir> --strict       # exit 2 when the scan did not run or the guide does not cover the target version (CI)
node scripts/run-log.mjs list           # review past runs (tool version@commit included)
node scripts/run-log.mjs doctor         # cross-check run logs × host startup logs (first stop for "plugin erroring")
node scripts/run-log.mjs sanitize --latest --out share.json   # sanitise before sharing
npm run release-check                   # release preflight: version sync, tag, npm publish state, pack contents, self-test

2. Fleet Governance Board (fleet-sweep.mjs)

When upgrading DSH hosts or managing monorepos, sweep and categorize all plugins:

node scripts/fleet-sweep.mjs                   # full matrix board: running, workspace, web, app, disabled
node scripts/fleet-sweep.mjs --running         # active plugins currently loaded in running host
node scripts/fleet-sweep.mjs --workspace       # workspace source plugins only
node scripts/fleet-sweep.mjs --web             # Web profile plugins only
node scripts/fleet-sweep.mjs --app             # Desktop (APP) profile plugins only
node scripts/fleet-sweep.mjs --disabled        # disabled/inactive plugins and reasons
node scripts/fleet-sweep.mjs --target 0.2.2-rc.1 --apply-compat # batch adapt zero-hit plugins

Detailed SOP and multi-platform practices are in references/user-guide.md.

You can also run each step on its own (the six-step spine remains; run.mjs just chains the steps below, and the optional ones are added as needed):

# 1. Inspect the local environment: installed version, stale overlay packages,
#    installed plugins, activation readiness. Also two silent-failure judges:
#    ghostHost (process still running old code) and falseGreen (tsconfig paths fake green)
node scripts/env-doctor.mjs <plugin-dir> --brief   # omit raw patch lines, 80.5KB -> 4.5KB

# 2. Resolve the target version: what is upstream's latest, should this machine follow it
node scripts/guide-sync.mjs <local-version>

# 2b. Upstream watch (cron/agent friendly): exit 1 = new version out (guides prefetched),
#     0 = nothing to do, 2 = could not determine
node scripts/guide-sync.mjs --check

# 3. Fetch the guide for the scan window target (managed branch snapshot first;
#    never leave --target empty and follow upstream's newest)
node scripts/guide-sync.mjs <local-version> --target <scan-target> --clone

# 4. Find which changes the plugin hits
node scripts/code-scan.mjs <plugin-dir> <upgrade-guide-dir> <local-version> <target-version>

# 4b. Seam query: dual-source verdict for a package/API symbol across the official
#     guide anchors and the local host install ("removed" is only concluded when both agree)
node scripts/seams.mjs dsh-settings

Heal stale overlay packages first when any are reported (dry-run by default):

node scripts/env-heal.mjs           # report only
node scripts/env-heal.mjs --apply   # move to ~/.dsh/.trash/<date>/, never delete

Two optional steps complete the "verify as you build, audit as you upgrade" loop:

# 5. Post-fix smoke verification: in-memory Cordis mock checks module loading,
#    the apply contract and tool registration. Undeclared-inject host-service
#    access is rejected with the same contract error the real host throws.
node scripts/quick-smoke.mjs <plugin-dir>

# 6. Four-dimension audit while you are at it: performance, resilience,
#    context budget, lifecycle
node scripts/plugin-audit.mjs <plugin-dir>
node scripts/plugin-audit.mjs <plugin-dir> --guide <guide-root> <local-version> <target-version>
node scripts/plugin-audit.mjs <plugin-dir> --guide <guide-root> <local-version> <target-version> --peer-patch  # print verified peer patches

# 7. One-command host-log diagnosis: StartupError / port-in-use /
#    undeclared inject / dead client entry
node scripts/log-doctor.mjs --pattern '^startup-' --limit 5

# 8. Sync the skill surface to a downstream skill directory (--check = drift only)
node scripts/sync-skill.mjs --dest <downstream-skill-dir> --check

Scan accuracy: from 12 false positives to 0

A naive first version reported 12 findings on a real plugin; on inspection all 12 were false positives. The current version applies four layers of noise reduction, and the same plugin reports 0:

  • The scanner uses a state machine to skip comments and strings, so a name mentioned in a comment is not a hit
  • Full member chains win; overly generic parent chains like ctx.tools are dropped
  • Generic words (register, resolve, readFile) and short names never become anchors; "old → new" replacement pairs are recognized, so a plugin already using the new symbol is not reported
  • Constant anchors come only from the Change section; matching requires the object parts to be mutual suffixes, so engines.dsh never collides with result.dsh
  • Package semantic gate: a package name becomes an anchor only when mentioned in a sentence with a removal/renaming verb — contextual mentions ("The mode fields of X accept only …", about field values) do not count. All 3 criticals reported on dsh-files were of this kind; the gate zeroed them

Each finding carries a severity (package=critical, member=high, code=medium — fix the front of the list first), an evidence line (the source line itself, so checking for false positives needs no file opening) and provenance anchors (guideFile/guideLine, pointing straight at the official guide's original location). The rules and the measurements behind them are in references/heuristics.md. Scan roots are the union of source roots (src plus sibling client/web/ui); build outputs (lib/dist) are not scanned twice. The smoke test discloses its mock fallbacks: the mockFallbacks list in the output names every property the plugin touched but the mock does not provide — the longer that list, the less the result can be trusted. A passing smoke test is not host compatibility, and the tool says so in its output, not just in the docs. The smoke test also rejects undeclared-inject host-service access at the inject_contract stage, matching the real Cordis contract, instead of letting load-time crashes pass silently. When you need real-host evidence, run.mjs --real-smoke bridges upstream plugin-upgrade's verify-runtime.mjs: install → boot → four-class attribution in a clean profile (honestly skipped with install guidance when the script is absent).

Scaffold a plugin from zero

node scripts/scaffold.mjs <namespace>/<name> --form tool|hook|service|config|llm-adapter [--out <dir>] [--harness <version>]

One command emits a runnable plugin in five forms: package.json (build-free pure-ESM invariants), a complete entry implementation per form, a cordis.patch.yml mounting row, and a dsh-plugin.naming.json with collision-resistant naming projections derived in full (the output passes upstream validate-names in --strict mode). Non-empty target directories and invalid coordinates are rejected before anything is written.

The entry ships a working starting capability (echo tool, observing hook, example service method, config with defaults, OpenAI-compatible adapter) — swap in your own; the full contract still follows the five form references of plugin-write.

Verification runs in two layers, and each layer reports when it is skipped: tool and hook use the dependency-free in-memory smoke test; all five forms run a real-base-class load check — when the host is installed, the entry is imported against the real @deepseek-ai/* base classes to prove the API is used correctly (Service inheritance and super(ctx, name), real Schema validation, LlmAdapter inheritance and route registration). When no host is installed it is honestly skipped, never faked. When the capability is written, gate it in one command:

node scripts/write-gate.mjs <plugin-dir>   # birth certificate: hard gates auto-judged, soft metrics passed through

There are only three hard gates (entry artifact exists, smoke passes, zero critical findings against the official guide); a failing one exits 1. Audit scores, high/medium findings, mockFallbacks and the not-yet-mounted fact all land in the discretion section labelled for human judgment — the tool never says "qualified" on your behalf. Guide discovery reuses the guide-sync cache (zero network); a new plugin is scanned against the full historical corridor; pass --skip-smoke right after scaffolding to skip the duplicate smoke run.

Dependencies

Zero external dependencies. Only Node built-ins (node:fs, node:path, node:os, node:child_process) plus the git and npm commands.

No TypeScript, no AST library, no HTTP client. Runs on Node 22.13+ (import.meta.dirname needs 20.11+, the optional type stripping needs 22.13+; type stripping is off by default).

Self-test:

npm test   # node scripts/self-test.mjs, 270 assertions

Contributors should enable the pre-commit gate (one time): git config core.hooksPath .githooks — every commit runs the self-test, so a forgotten downstream sync is caught at commit time.

Covers scanner false positives (names in comments and strings are not hits), false negatives, version heuristics, replacement-pair recognition, end-to-end findings (with guide file + line provenance anchors), dual-source seam-query verdicts (agree-removed / host-still-present disagreement / honest no-record), run-log × host-log cross-checks, the --real-smoke bridge tier (fail → exit 2 with a next-step pointer), the upstream-watch exit codes, the sync commit-command suggestion (adds only the synced path), SOP reference integrity, dist-tags cache states, smoke verification (including the undeclared-inject contract rejection), the four-dimension audit (including peer patches), activation diagnostics, ghost-host four states (stale/ok/unknown/no-running-host) with disk-time provenance, tsconfig paths fake green (extends chains, JSONC comments, wildcard prefixes, non-host aliases downgraded), the plugin scaffolder (all five forms, naming-projection grammar, smoke closure, patch-layer recognizability, invalid-input and non-empty-target rejection), the write gate (hard-gate interception, soft metrics never overrule, skip semantics, scaffold handoff), log diagnosis, downstream-sync drift checks plus a real-machine zero-drift gate, cache-root injection (the self-test never writes the real user cache), one-time run-log ledger migration (legacy ~/.cache root moves to ~/.local/state), a self-test size gate, a scanner performance gate, full incident-fixture regression (fixtures/ cross-checked against references/incident-ledger.md, with both sides of every tightened criterion pinned), a single-source state-vocabulary check (lib/run-states.mjs), and a doc-layering check (process reports are archived under docs-local/archive/ and never enter the skill surface). The self-test itself is zero-network and zero-dependency, and runs on any machine.

To gate your own plugin's repository at commit time (smoke/typecheck as hard gates, audit as a soft report), see references/ci-snippet.md.

Scripts

Script Responsibility
scripts/cli.mjs npm entry (npx plugin-fast-adapt), forwards to run.mjs
scripts/run.mjs One-command orchestration of the full chain (env → version → guide → scan → audit → smoke → typecheck), unified report plus a local run log; --real-smoke bridges upstream verify-runtime for a real-cold-boot tier
scripts/run-log.mjs Run-log viewing (list/show), cross-checking (doctor: run logs × host startup logs) and sanitised export (sanitize)
scripts/seams.mjs Seam query: dual-source verdict for one package/API symbol across official guide anchors and the local host install
scripts/scaffold.mjs Scaffold a plugin from zero: one command emits a runnable plugin in any of the five forms (package.json invariants + complete form entry + patch layer + naming projections), verified on creation
scripts/write-gate.mjs Gate a finished plugin: orchestrates smoke + activation readiness + four-dimension audit + official-guide scan into a birth certificate; only three hard gates auto-judge, soft metrics pass through untouched
scripts/env-doctor.mjs Probe the local DSH environment (version, overlay, plugins, processes, activation readiness, ghost host, tsconfig fake green)
scripts/env-heal.mjs Heal stale overlay packages (dry-run by default)
scripts/guide-sync.mjs Resolve the target version and fetch the official guide (managed default-branch snapshot, 1-hour TTL; release tags are an offline fallback marked frozen)
scripts/release-check.mjs Release preflight: version sync, tag, npm publish state, npm pack contents, self-test and worktree; read-only, never tags or publishes
scripts/code-scan.mjs Scan plugin code against official change anchors
scripts/quick-smoke.mjs Post-fix smoke verification (in-memory Cordis mock, discloses fallbacks)
scripts/plugin-audit.mjs Four-dimension performance & architecture audit, optional --guide cross-check; --peer-patch prints verified peer patches
scripts/standards-scan.mjs Upstream standing-rule detection (7 mechanically-decidable rules with defensive-patterns provenance); --rules prints the table
scripts/codemod.mjs Deterministic code/package-surface autofix (Loader entry exports, peer deps, top-level await); dry-run by default, --apply writes with a backup
scripts/types-diff.mjs Host .d.ts and export-surface diff; synthesises virtual guides keyed by baseline version
scripts/fix-peer-deps.mjs Batch-move host core packages from dependencies into peerDependencies; dry-run by default, --apply writes with a backup
scripts/fleet-sweep.mjs Fleet-wide governance and inspection with a matrix board and JSON report; --apply-compat backs up before batch-writing ledgers
scripts/log-doctor.mjs One-command diagnosis of ~/.dsh/logs/ (startup header / failed plugins / waiting services / signal summary)
scripts/sync-skill.mjs Sync the skill surface to a downstream skill directory; --check reports drift
scripts/self-test.mjs Self-test
scripts/lib/scanner.mjs Lexical scanner and version comparison (zero-dependency)
scripts/lib/guide-parser.mjs Official guide parsing and anchor extraction
scripts/lib/runlog.mjs Run-log writing, indexing and sanitisation
scripts/lib/host-modules.mjs Resolves the host @deepseek-ai/* base classes and runs the real-base-class load check
scripts/lib/package-json.mjs Single source for reading package.json: strips UTF-8 BOM, lenient/strict modes, missing/corrupt/ok tri-state
scripts/lib/cache-root.mjs Single source for the cache root (DSH_PFA_CACHE_DIR > DSH_CACHE_DIR > XDG_CACHE_HOME > ~/.cache); self-test can isolate it
scripts/lib/backup.mjs Shared backup contract for the three autofix entry points: { backupDir, backupFiles, backupRel }, NO_BACKUP when nothing changed
references/user-guide.md Comprehensive user guide (local anchoring, cross-platform adaptability, Web/APP fleet governance, guardrails)
references/legacy-migration-sop.md Legacy migration SOP (for ranges the official guide does not cover)
references/heuristics.md Scan noise-reduction rules and the measurements behind them
references/incident-ledger.md Incident ledger: one line per real false positive/negative, each pointing at a minimal reproduction under fixtures/
references/ci-snippet.md CI gate template for plugin repositories (smoke/typecheck hard gates + audit soft report)

Safety posture

  • env-doctor, code-scan, plugin-audit, log-doctor, seams are strictly read-only; run-log is read-only except for sanitize --out <file>, which writes the sanitised result to the given path
  • env-heal is dry-run by default and moves rather than deletes when applied (into ~/.dsh/.trash/<date>/)
  • sync-skill writes to a downstream skill directory explicitly, copying only the fixed skill surface (SKILL.md/README*/references/scripts/sub-skills); --check/--dry-run let you inspect first
  • Never modifies DSH itself, nor config or profile declarations under ~/.dsh
  • Automatic plugin-code edits are limited to three mechanically-decidable classes, always with a backup first: codemod (Loader entry exports, top-level await), fix-peer-deps (host core package peer relocation) and fleet-sweep --apply-compat (batch package.json compatibility ledger and peer ranges). All report by default and write only with --apply/--apply-compat, backing up the original to <plugin>/.pfa-backup/<timestamp>/. Everything else reports findings and vendor fixes only; plugin-audit --peer-patch also prints rather than applies
  • .pfa-backup/ is the local snapshot taken before an autofix; it is listed in the release gate's FORBIDDEN_PACK and in the .gitignore that scaffold generates, because npm pack does include it (measured) and the backup holds the pre-edit package.json
  • The cache root is injectable (DSH_PFA_CACHE_DIR > DSH_CACHE_DIR > XDG_CACHE_HOME > ~/.cache); the self-test points it at a temp directory on startup and never writes the real user cache
  • Network is used only for "fetching vendor sources": version resolution reads npm dist-tags, guide fetching clones the official repo. Both have timeouts and report failures explicitly instead of silently skipping; dist-tags is cached for 1 hour and degrades to the stale cache with a stale marker; guides reuse an existing local clone first, and --no-clone skips the fetch

Legacy plugins

The official upgrade guide only goes back to dsh-v0.1.7-rc.2. For older plugins, follow the legacy migration SOP: use the upstream plugin-upgrade skill's hand-curated card corridor (from dsh-v0.1.0-rc.8 on) as the difference source and walk an eight-stage checklist (mode → read-only prep → ghost-host check → corridor assembly → seven touchpoint classes → plan & confirm → implementation → six-layer validation). The SOP references rather than copies the cards, so renamed cards are caught by the self-test's dead-link assertion.

Known limitations

  • The official upgrade guide does not cover every breaking change (package retirement is one class that is not documented there); the env-doctor overlay inspection covers that case
  • Same-named symbols can still collide (a plugin's path.resolve() versus the guide's runtime.resolve()) and require human judgment of the surrounding code
  • Static matching only, no runtime-behaviour verification; the smoke mock covers the common host surface only
  • The ghost-host check covers CLI host processes only: Windows has no ps etime, and desktop Electron renderers are excluded; both cases report unknown with the reason instead of guessing

Provenance and division of work

This project was split out of oh-my-dsh/dsh-plugin-upgrade-skill (a skill collection that teaches AI agents to upgrade DSH plugins, with an arXiv paper) via git subtree and has evolved independently since. As of 2026-10-26, the upstream project carries 198 upgrade cards, 12 skills and a 65-case auto-graded benchmark.

The two projects complement each other:

Aspect Upstream This project
Difference source Hand-maintained upgrade cards Official docs/upgrade-guide/ + npm dist-tags, updates with upstream automatically
New release ships Wait for cards, corridor gaps in between Works immediately, zero changes needed
Verifying one change Real host cold start, measured up to 3,600 s In-memory Cordis smoke test, milliseconds to seconds
Stale overlay packages Manual troubleshooting env-doctor inspection + env-heal healing (dry-run by default)
Weaker models Full card library in context, -3.07 pp Six independent scripts, one small output each
Code-level scanning None Anchor matching + four noise-reduction layers
Fleet-wide sweep plugin-fleet-sweep owns breadth The six-step pipeline owns depth

A fleet-wide sweep after a host upgrade goes to upstream's plugin-fleet-sweep (breadth), and each flagged plugin comes back to this project's six-step pipeline for a deep pass (depth). For historical corridors the official guide does not cover (before v0.1.7-rc.2), this project's SOP references upstream's cards and scripts — segments with a guide use this project's code-scan, segments without use upstream's plan-migration.mjs and cards, and runtime verification uses upstream's verify-runtime.mjs (directly bridgeable via this project's run.mjs --real-smoke).

About

Keep DSH plugins working across host upgrades: reads official upgrade guides directly, scans plugin code for breaking changes, smoke-tests in memory, scaffolds five plugin forms. Agent-native skill, zero dependencies

Topics

Resources

Stars

15 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages