Introduction

When using DSH, plugins are generally installed in the profile directory and managed by the profile’s package.json. As you install more, a problem arises: the same plugin might be declared twice, for example, once from github: and once from a local file:, with the same package name but different sources. This results in multiple copies of the same package in node_modules. This can take up space lightly, or heavily lead to the runtime loading the wrong version, which takes a lot of time to troubleshoot.

dsh-plugin-dedupe solves this issue: it scans the profile before installation and blocks it directly if duplicate declarations are found. Below is an introduction to its features, installation, and usage.

What is it

dsh-plugin-dedupe (DSH Plugin Deduplication Guardian) is an open-source plugin maintained by Jiaoyc224, MIT licensed, current version 0.1.0. One-sentence positioning: it prevents installing the same plugin multiple times in a DSH profile.

It works in two ways:

  1. When loaded as a DSH plugin, it automatically scans the current profile’s package.json dependencies and the actual installation status of node_modules during the startup phase;
  2. As a pnpm install preinstall hook, it runs a check script before installation and returns a non-zero exit code upon finding errors to block the installation.

It declares peerDependencies: @deepseek-ai/cordis ^4.0.1 in package.json and is marked as optional.

What it checks

The detection logic is divided into two layers: first parsing the dependencies / devDependencies / optionalDependencies / peerDependencies of package.json, and then scanning node_modules to count the actually installed package names. Specific rules are as follows:

Detection Type Behavior Description
Duplicate declaration of same-named dependencies (different sources) Error The same package name appears multiple times in package.json with different sources, e.g., github + file
Duplicate declaration of same-named dependencies (same source, multiple fields) Warning The same package is declared in both dependencies/devDependencies with the same source protocol
Multiple same-named packages in node_modules Warning The same-named package appears multiple times in node_modules (different versions/sources coexist)
dsh-* plugins installed but not declared Warning Likely old remnants or manually copied in

Only “duplicate declarations with different sources” count as errors and will block installation; other cases downgrade to warnings. The actual blocking output looks roughly like this:

[dsh-plugin-dedupe] Scanning profile: C:\Users\<your-user>\.dsh\profiles\web
❌ Duplicate declaration detected: "dsh-agent-teams" has multiple sources in package.json:
   github:NanmiCoder/dsh-agent-teams
   file:E:/fake/dsh-agent-teams
[dsh-plugin-dedupe] Detected 1 duplicate plugin error, installation blocked.

Installation

Install directly in the DSH profile directory:

cd <your-dsh-profile-dir>  # e.g.: C:\Users\<user>\.dsh\profiles\web
pnpm add github:Jiaoyc224/dsh-plugin-dedupe

Or use the dsh plugin command:

dsh plugin --profile web add github:Jiaoyc224/dsh-plugin-dedupe

Enabling the preinstall hook

The preinstall hook needs to be added manually. Edit the profile’s package.json and add to scripts:

{
  "scripts": {
    "preinstall": "node node_modules/dsh-plugin-dedupe/scripts/check-duplicates.mjs"
  }
}

This way, every time before running pnpm install, the deduplication check is performed first. If duplicate plugins are found, it returns a non-zero exit code to block the installation.

There is one note about the first installation: after installing the plugin, you need to run pnpm install once first to generate node_modules/dsh-plugin-dedupe; otherwise, subsequent pnpm install calls won’t trigger the preinstall hook. This step can use pnpm install --prefer-offline to avoid an infinite loop.

Running the check independently

If you don’t want to hook it, the check script can be run independently:

# In the profile root directory
node node_modules/dsh-plugin-dedupe/scripts/check-duplicates.mjs

# Or specify the profile directory
node node_modules/dsh-plugin-dedupe/scripts/check-duplicates.mjs --profile /path/to/profile

The plugin’s bin field also provides the dsh-dedupe command, pointing to the same check script.

Environment Variables

The plugin supports two environment variables:

Environment Variable Description Default Value
DSH_DEDUPE_WARN_ORPHANS When set to true, also warn about undeclared dependencies that are not plugins false
DSH_PROFILE_DIR Manually specify the profile root directory Automatically searches upward

Usage Scenarios and Notes

The suitable scenarios are clear: profiles with many plugins and mixed sources (npm, github, local file, link), or DSH/Agent developers who frequently debug plugins locally and need to switch sources. If you have only one profile and only install plugins from a single source, this plugin’s effect is limited.

A few notes:

  1. The plugin runs with the permissions of the current dsh process. It is recommended to check the source code and license of third-party plugins before installing them.
  2. The preinstall hook only works for pnpm install and needs to be manually configured in the profile’s package.json.
  3. The boundary between errors (blocking installation) and warnings (only prompting) is shown in the rule table above; adjust the intensity of reminders for undeclared dependencies as needed via DSH_DEDUPE_WARN_ORPHANS.

Conclusion

dsh-plugin-dedupe does something small but very practical: turning “duplicate plugin installation” from post-troubleshooting to pre-installation interception. If you have encountered the problem of same-name plugins with multiple sources coexisting in DSH profile management, it is worth trying.

  • Community directory page: https://www.skillhub.cn/plugins/Jiaoyc224/dsh-plugin-dedupe
  • GitHub repository: https://github.com/Jiaoyc224/dsh-plugin-dedupe