sanshanya/better-model-provider ↗★ 0
better-model-provider
DeepSeek Harness 的单模型能力声明插件:为兼容 OpenAI 的服务商声明推理努力程度和请求模态(文本/图像),无需手动编辑 YAML 配置文件。
AI 分析
核心用途是免去手动编辑 settings.yaml,直接在界面配置单模型的推理级别和输入模态。适合使用 OpenAI 兼容服务商且需要精细化模型控制的用户。
安装
npx -p @deepseek-ai/dsh dsh plugin --profile web add github:sanshanya/better-model-provider说明文档
阅读完整 README ↗better-model-provider
A DeepSeek Harness settings plugin that declares, per model, your OpenAI-compatible provider's reasoning-effort levels (with wire spellings) and request modalities (text / image) — no hand-editing settings.yaml.
English | 中文

Why you may need it
The official Models page manages providers and model rows, but two per-model capability fields stayed YAML-only: reasoningEfforts (which reasoning levels the model accepts, plus each level's wire spelling) and input (which request modalities the model admits). Until they are declared:
- the composer's model picker shows no reasoning-effort control for your model;
- the host refuses image sessions for it (
Model ... does not accept image input), because a hand-declared model defaults to text-only.
There are a few cousin plugins for the reasoning half (dsh-effort-tweak, dsh-model-thinking, dsh-effort-config) — all separate pages with a hardcoded 7-level list. This one puts capability editing inside each model row, reads the vocabulary from the adapter's own schema, and writes catalog models through modelOverrides so the built-in model list is never touched. For the vision half (input modalities) this is currently the only plugin that exists.
What it does
- Lists every configured
llm-pi-aiprovider (hand-declared or catalog route) and its models. - Per model row:
- Reasoning effort — provider default, non-reasoning (
false), or a custom level list with per-level wire spellings. Checking a level seeds the spelling with the level id; a blankoffspelling storesnull("supported, send nothing"). - Input modalities — provider default or a custom modality list. Checking
imageis literally what makes a vision model usable: image sessions stop refusing to switch to it, and images can be sent.
- Reasoning effort — provider default, non-reasoning (
- Catalog routes write
modelOverrides.— the built-in catalog stays intact, and clearing the capabilities lifts the override whole. - "Add provider" enables a catalog route (empty profile) in one click; removing a provider is a two-step confirm.
- Writes are minimal
settings.mutatepath ops with a compare-and-set revision; an invalid declaration fails on its own row before anything is written.
Install
# From GitHub:
dsh plugin --profile web add github:sanshanya/better-model-provider
# Local checkout:
dsh plugin --profile web add link:
Restart dsh web, hard-refresh the browser, and the settings sidebar gains Model capabilities. Uninstall:
dsh plugin --profile web rm better-model-provider
Use
- Configure the provider on the official Models page first (that's where the API key lives; this page never touches credentials).
- Open Settings → Model capabilities.
- Expand a model row: pick Custom under reasoning effort and check the levels; for vision models check
imageunder input modalities. - Apply. The picker immediately offers exactly the declared levels, and the host's image admission admits the model.
Small note: declaring { high } alone gives the picker only High; also check off (blank wire → null) if you want Off available.
How it is built (and why it stays maintainable)
| Decision | Reason |
|---|---|
| Zero runtime harness deps | The bundle takes React from the shell and inlines everything else. The dsh family isn't fully on npm yet (@deepseek-ai/dsh-type-meta is missing), so a runtime dep would break installs today |
| Vocabulary read from schema | Levels and modalities come from the serialized llm-pi-ai schema — an adapter upgrade changes the page with no plugin release |
| Catalog routes write modelOverrides | The smallest possible declaration for a catalog model; nothing in its catalog gets rewritten |
| Structurally open edits | Hand-written YAML keys the editor doesn't show survive every write |
The stable boundary is the host's wire contract (settings.describe/mutate, llm.providers/models, plus the settings/document-updated / llm/adapters-updated events). The plugin is browser-side only.
Development
pnpm install
pnpm build # lib/index.js + lib/client.js (module-loader bundle)
pnpm test # unit + interaction flows + bundle smoke
pnpm test:coverage # v8, 100% per-file gates
pnpm lint; pnpm typecheck
License
MIT