npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

dsh-plugin-open-with

v2.0.0

Published

Capsule split-button in the dsh web conversation header: open the workspace in VS Code, terminal, or file explorer — extensible to more launchers.

Readme

🖼 效果图

胶囊拆分按钮效果图

设置页面效果图

🧩 功能

  • 💊 胶囊拆分按钮:左半边执行当前选择的启动器;右半边下拉菜单列出全部启动器,点击即切换并立即启动。
  • 🪧 默认启动器:VS Code、CMD、PowerShell、文件资源管理器。它们只是预置的自定义项——毫无特权,同样可以被改、隐藏、删除。
  • ⚡ 设置即改即生效:设置页每次保存后,host 归一化后的文档通过进程内广播推给胶囊按钮,菜单即时重渲染。无需等点开下拉;展开菜单时仍会补读一次,仅作为兜底(如直接手改 settings.json)。
  • ⚙️ 设置页面:在 DSH 设置面板中注入「Open With」配置区域,支持:
    • 统一的项目管理:所有启动器都是平等的普通项,支持统一的添加 / 编辑 / 删除 / 拖拽排序 / 可见性控制。预设项不过是最初写入的那批,编辑与删除同样开放,下拉菜单与设置页所见即所得。
    • 当前项选择:点击卡片切换当前启动器,胶囊按钮同步更新。
    • 按钮位置可切换:胶囊按钮可注入会话标题旁(actions)或右侧工具区(utilities),保存后立即迁移槽位。
    • 按钮顺序可调:同一槽位内按 order 值升序排列,数值越小越靠前(官方「在应用中打开」为 -10),保存后立即重排。
    • 传递会话目录:每项可选是否把会话工作区目录作为参数传给启动器(默认传递)。
    • 一键恢复默认:把启动项列表还原为内置四项(两步确认;只动列表,不重置按钮位置与顺序)。
    • 接管内置按钮:通过本插件自己的 bundle 补丁,声明式关闭 DSH 内置的 open-in-app(Host 与 Client 两半同进同退),会话头部不会出现两个打开按钮。补丁层随插件加载、也随插件消失 —— 卸载后内置按钮自动恢复,本插件从不改动 profile 的 cordis.patch.yml。
    • 图标自动更新:图标从本地可执行文件按需提取;编辑路径后,带修订号的 URL 主动破除浏览器缓存,图标随之更换。
    • 持久化存储:设置自动保存到 profile/<mode>/open-with/settings.json,重启后保持。
  • 🌍 中英双语 UI:跟随 DSH 客户端全局 locale 自动切换。

🚀 安装

方式一:从 npm 安装(推荐)

已发布到 npm:dsh-plugin-open-with(当前最新 2.0.0)。在终端执行:

# 安装
dsh --profile web plugin add dsh-plugin-open-with

# 验证安装版本
dsh --profile web plugin list

# 卸载
dsh --profile web plugin remove dsh-plugin-open-with

方式二:从仓库安装(开发 / 调试)

git clone https://github.com/hyrinx/dsh-plugin-open-with.git
cd dsh-plugin-open-with
npm install
npm run build
dsh --profile web plugin add "link:$($PWD.Path)"

重启 dsh web 生效。后续修改源码只需重新 npm run build + 刷新浏览器。


🔒 安全模型

本插件会在 DSH 宿主端启动外部程序,安全措施如下:

  1. WebServer 路由 + 连接信任栅栏:host 端在 ctx.webServer 注册 settings / icon / open / log 四条路由;每条都先经 ctx.connection.requestRejection 校验 Host / Origin,抵御 DNS rebinding 与跨站调用。请求体限 64 KiB 且必须是 JSON。
  2. 开放 item 模型,逐项校验:启动目标为设置文档中的普通项 id,Wire 端校验 id 必须真实存在;路径必须是可执行文件存在的绝对目录路径,杜绝任意可执行文件注入。
  3. 版本化图标寻址:图标路由按 id + 修订号寻址,浏览器无法命中过期字节;取不到图标时返回 404 且前端留空位,不展示误导性兜底图。
  4. 双半一致、可回退的接管:内置 open-in-app 的 Host / Client 是一对,由本插件的 bundle 补丁按 id 一并关闭,避免只留一半的残缺形态;该补丁不属于 profile 配置,卸载即自动恢复。

🚧 已知限制

  • 仅支持 Windows:macOS / Linux 适配需要社区贡献。
  • 必须通过本机浏览器回环访问(localhost / 127.0.0.1)。
  • VS Code 需要先把 code 命令加入 PATH:首次运行时 host 用 PATH 解析预设项为绝对路径并写入配置;若命令不在 PATH,该项会保留裸名,需在设置页改填完整 .exe 路径。
  • 终端使用系统自带 cmd.exe / powershell.exe:自定义启动器支持任意 .exe 绝对路径。
  • 图标从本地可执行文件按需提取:由 host 端用 PowerShell 的 ExtractAssociatedIcon 取图标并缓存;取不到时图标位置留空,不显示占位图。

🏗 构建与扩展

npm install
npm run build       # 先清 lib,再 tsdown 出主/客两端 bundle,tsc 出 lib/types/*.d.ts
npm run clean       # 只删 lib(改过 src 文件结构后 build 会自己调它)
npm run typecheck   # tsc -p tsconfig.json --noEmit
npm pack            # 发布前预览 tarball 内容
npm publish --access public

目录结构(双半包:一个 host 半 + 一个 dsh.client 浏览器半):

dsh-plugin-open-with/
├── src/
│   ├── index.ts          host 半入口:四条 webServer 路由 + connection 信任栅栏
│   ├── shared.ts         两半共享的路由、协议、设置模型与归一化
│   ├── storage.ts        settings.json 原子读写 + profile 路径解析
│   ├── logger.ts         host.log 落盘
│   ├── launch.ts         各启动器的 spawn 配方与可执行文件解析
│   ├── icons.ts          从可执行文件提取图标
│   └── client/           浏览器半
│       ├── index.ts      入口:挂载按钮、注入设置页、注册词典
│       ├── OpenWithButton.tsx    胶囊拆分按钮
│       ├── OpenWithSettings.tsx  设置面板(添加/编辑表单、拖拽排序、可见性)
│       ├── ItemIcon.tsx          两个界面共用的行内图标
│       ├── settings-events.ts    设置变更进程内广播(按钮即时刷新 + 图标破缓存)
│       ├── controller.ts         浏览器 → host 的 RPC 载体
│       └── locales.ts            中英双语词典
├── locale/               插件展示元数据(DSH 插件管理页的标题与描述来源)
├── lib/                  构建产物,勿手改(index.js / client.js / types/)
├── cordis.patch.yml      bundle 补丁:插入本插件,并按 id 关掉内置 open-in-app
├── tsdown.config.ts      双配置:host 出 ESM,client 出 ModuleLoader 闭包工厂
└── tsconfig.json         只出声明(emitDeclarationOnly → lib/types/)

模型核心:所有启动器都是同一个 OpenWithItem(id / name / path / passCwd),没有预设与自定义的区分。默认项(DEFAULT_ITEMS)仅在设置文档不存在时作为种子写入,host 逐项把裸命令解析为绝对路径后落盘;此后每项就是普通项,可改名、改路径、隐藏、删除。要使一项不可被删除,并不存在这种情况——设计上所有项一律平等。

lib/ 与 package.json#exports 的子路径一一对应:. → lib/index.js、./client → lib/client.js、./locale/*.json → locale/*.json。展示名与描述只来自 locale/*.json 的 meta(package.json 的 name / description 仅作 fallback),locale/en.json 是 DSH 的发现基线,缺了整包元数据就不生效。

如何新增一个启动器:

  1. UI 方式(推荐,无需改代码):设置页 → Open With → 「+ Add」,填写名称与可执行文件绝对路径;支持拖拽排序与可见性控制。
  2. 代码方式(想作为默认项内置):修改 src/shared.ts 的 DEFAULT_ITEMS 数组即可——因为所有项本就统一,新增默认项只需补一条 { id, name, path, passCwd },无需改动类型或启动分发。首次写入时 host 会解析并落盘。

🤝 贡献

欢迎以下方向的 PR:

  • 🍎🐧 macOS / Linux 平台适配:实现各平台的 shell、文件管理器启动与图标提取。
  • 🖥 更多 IDE 启动器:JetBrains 全家桶、Sublime Text、Neovide、Cursor、Windsurf……
  • 💻 更多终端候选:Windows Terminal (wt)、PowerShell 7 (pwsh)、Git Bash、Alacritty、WezTerm……
  • ⚙️ 设置页增强:导入/导出配置、批量操作
  • 🎨 UI 反馈:为启动过程加入进行中 / 成功 / 失败的可视状态

提 PR 前请确保:

npm run typecheck   # 通过
npm run build       # 通过
npm pack            # 无 WARN / error

📜 License

MIT © hyrinx。详见 LICENSE。