AI工具配置 24

DeepSeek Harness 模型配置:提供方、图片输入与请求兼容

DeepSeek Harness 的模型都在 Web UI 的设置 → 模型里配。本文默认你已经把 Web UI 跑起来了。改完不必重启服务器,下一次请求就会用新配置。

页面上有三件事:给 DeepSeek 填密钥、从已安装目录加提供方、以及自己接公司网关或自建服务。自定义提供方如果还要传图,或网关自称兼容 OpenAI 实际却拒请求,就要改 $DSH_HOME/settings.yaml——表单里没有这些字段。

配置 DeepSeek

打开设置 → 模型,DeepSeek 卡片上有一个 API 密钥字段。填进去,保存即可。

密钥是只写的。保存之后,页面只会拿到脱敏描述符,永远看不到明文。明文落在 $DSH_HOME/.credentials.yaml 里,settings 只保留凭据引用。

添加目录提供方

添加提供方,挑 Anthropic 或 OpenAI 这类已在目录里的服务,填它的 API 密钥再保存。端点、协议和模型列表由已安装目录给出,不用自己填。

Bedrock、Vertex、Azure、Codex 走各自的原生认证,只填 API 密钥字段配不完:

  • Bedrock:AWS 凭据与区域
  • Vertex:ADC 项目
  • Azure:api-version
  • Codex:OAuth

目录提供方的模型列表来自本地已安装目录,获取可用模型不会对它们发网络请求。

添加自定义提供方

公司网关、自建服务器,或目录里根本没有的服务,走添加自定义提供方。表单要你提供:

  • 小写 Provider ID
  • 基础 URL
  • API 协议
  • 凭据
  • 至少一个模型

Provider ID 不能事后改名

Provider ID 是永久的。请求、已保存会话、模型默认值、凭据引用都拿它当键。显示名称、基础 URL、协议、凭据和模型以后还能改;ID 本身不行。真要换名字,只能再加一个提供方,把旧的删掉。

获取可用模型只改草稿

表单里的模型目录获取可用模型。它用的是你此刻填在表单上的基础 URL 和凭据,去打 OpenAI 兼容的 GET /models。点选候选项只会改当前草稿,点保存之前,这个提供方还不会被存下来。

对方不提供 GET /models 时,请手动输入模型。返回 401 时先核密钥。

给自定义模型声明图片输入

手填的模型在自己声明之前,一律按纯文本对待——没有环节会去问端点到底收哪些模态。给这类模型附加图片,请求发出去之前就会被拒绝,报错会点名那个模型。

视觉模型要在 $DSH_HOME/settings.yaml 里给它加 input。表单没有这个字段。

单模型 input

input 只认 textimage,而且只作用于写了它的那一个模型。同一条路由可以一边挂纯文本、一边挂视觉:

yaml
llm-pi-ai:
  providers:
    my-gateway:
      apiKeyEnv: GATEWAY_API_KEY
      api: openai-completions
      baseURL: https://gateway.example/v1
      models:
        - id: legacy-chat
        - id: vision-preview
          input: [text, image]

省略 input,或者写成空列表,意思一样:沿用已安装目录给该模型记的模态;目录没描述过的,回退到这条路由的 defaultInput

路由级 defaultInput

手填的模型如果全都收图,不必每个都写一遍,在路由上设一次回退即可:

yaml
llm-pi-ai:
  providers:
    vision-gateway:
      apiKeyEnv: GATEWAY_API_KEY
      api: openai-completions
      baseURL: https://vision.example/v1
      defaultInput: [text, image]
      models:
        - id: first-model
        - id: second-model

defaultInput 是回退,不是覆盖,默认值是 [text]。在目录提供方上,它只给目录没描述过的模型补答案,不会把目录里本来就能看图的模型的图片能力去掉。真要收窄某个目录模型,用它自己的 input

除了模型自己的那份列表,每个列表至少要写一项模态。模型自己的空列表等于省略。未知模态写在任何位置都会被拒。

inputdefaultInput 都是你对端点的断言,不是探测。模型声明了图片、端点其实不收,这里拦不住,会由提供方在请求时拒绝。

目录提供方用 modelOverrides

目录提供方没有可填的 models 列表,收窄或改写写在 modelOverrides 下,键是模型 id:

yaml
llm-pi-ai:
  providers:
    anthropic:
      modelOverrides:
        claude-sonnet-4-5:
          input: [text]

DeepSeek 自己的 chat-completions 路由是纯文本,不能靠配置打开图片。

网关通了但仍被拒绝:请求兼容性

密钥有效、地址也打得通,网关仍可能拒绝每一个请求。pi-ai 看端点 URL 来决定请求长什么样:系统提示词放哪个角色、输出上限写哪个字段、思考级别怎么传。它认不出的地址,一律按 OpenAI 本身来发。多数「OpenAI 兼容」网关至少会拒绝 OpenAI 接受的某一样东西。

占绝大多数的是这两样:

  • 声明了推理能力的模型,系统提示词会以 role: "developer" 发出,很多网关直接拒。
  • 输出上限写成 max_completion_tokens,只认 max_tokens 的服务端会拒。

表单里没有这两个开关,要在 $DSH_HOME/settings.yaml 的路由上改 compat

yaml
llm-pi-ai:
  providers:
    my-gateway:
      apiKeyEnv: GATEWAY_API_KEY
      api: openai-completions
      baseURL: https://gateway.example/v1
      compat:
        supportsDeveloperRole: false
        maxTokensField: max_tokens
      models:
        - id: my-model

路由上的 compat 是这条路由上所有模型的默认值。某个模型自己写了同名字段,以模型为准,所以只修一个模型不用把整条路由重写一遍:

yaml
      models:
        - id: my-model
        - id: my-reasoner
          compat:
            thinkingFormat: deepseek

路由和模型都没写的字段,沿用已安装目录给该模型记的值;目录也没描述,才落到 pi-ai 自己的检测。

写下来的开关必须带值。supportsDeveloperRole: 这种冒号后面空着的键会被拒绝,不会被忽略——空值会把目录里已知的信息抹掉,却给不出替代。任何协议都不认的名字同样会被拒,报错会列出当前能用的那些。

每个开关只属于声明了它的协议。某个 api 上合法的开关,换一个协议可能直接报错,报错会点名该协议实际提供哪些。和 input 一样,compat 也是断言:你打开一个网关其实不需要的开关,结果只是发出另一种形状的请求。

全部开关、各自能填的值、以及哪些协议接受它们,写在生成的 dsh-llm-pi-ai 配置参考的 PiAiCompatProfile 里。那份参考从源码生成,跟适配器实际接受的内容对齐。

选择模型

配好的提供方会出现在模型选择器里。选一个模型,同时会把它设成新会话的默认值。已经发过请求的会话,继续用自己日志里记下的那个模型,不会跟着默认值跑。

如果已保存的默认值指向一个已经删掉的提供方,输入框会显示选择模型,在你选别的模型之前,输入会被拦住。

排错

  • MISSING_CREDENTIAL:到模型页把提供方密钥存进去,或提供被引用的环境变量。
  • UNKNOWN_MODEL:选一个已经配好的模型,或给自定义提供方补上缺失的模型。
  • 获取可用模型返回 401:先查密钥。模型发现走的是 OpenAI 兼容的 GET /models;对方没有这个端点,就手动输入模型。
  • 密钥和地址都对,网关却拒绝每一个请求:请求形状和 OpenAI 不一样。先在路由上设 compat.supportsDeveloperRole: falsecompat.maxTokensField: max_tokens
  • 只有推理模型失败:pi-ai 把它们的系统提示词以 developer 角色发出,网关拒这个角色。设 compat.supportsDeveloperRole: false
  • 某个 compat 开关因没有值而被拒绝:冒号后面是空的。给它一个值,或删掉这个键,让它沿用已安装目录的值。
  • 图片在发送前被拒绝:该模型没声明图片模态。给自定义提供方的模型加上 input: [text, image]。DeepSeek 自己的 chat-completions 路由是纯文本,配置改不了。
  • 提供方拒绝了带图片的请求:模型声明了端点其实没有的图片能力。从授予它图片能力的那个列表里去掉 image——可能是模型的 input,也可能是路由的 defaultInput——然后开一个新会话。已经附上的图片会留在会话日志里,旧会话不离开它,同一个请求会反复带图。

需要直接改 YAML 时看哪里

自动生成的插件配置目录会列出每个插件支持的字段和默认值。这里配的提供方段落对应 dsh-llm-pi-ai。直接改 settings.yaml、目录解析、推理控制、凭据和适配器错误,分别看 dsh-llm-pi-aidsh-llm-deepseek 的参考文档。

感谢阅读,如果这篇文章对你有帮助,欢迎继续浏览同栏目内容。

返回 AI工具配置