跳到主要内容

请求 Header 覆盖

request_header_overrides 是 AIDY 网关层的 request header 覆盖 DSL。

它和 compat 的职责不同:

  • compat
    • 只给协议层使用
    • 用来控制协议特有行为,例如 Claude 的 anthropic_version / anthropic_beta
  • request_header_overrides
    • 只给网关层使用
    • 用来决定最终发往 upstream 的 request headers 如何透传、覆盖或删除

当前该字段同时存在于:

  • provider.request_header_overrides
  • upstream.request_header_overrides

运行时合并顺序:

  1. provider.request_header_overrides
  2. upstream.request_header_overrides 覆盖 provider 同名 key

header 名按大小写不敏感处理;运行时合并时会归一化为小写,"*" 保持原样。

1. 应用顺序

chat 主链路里,最终 outbound request header 的构造顺序是:

  1. 协议层生成的 request headers
  2. upstream/provider 静态 headers
  3. request_header_overrides
  4. 传输层最终修正

这意味着:

  • request_header_overrides 可以覆盖协议层和静态 headers
  • 但部分传输层字段最终仍会被 AIDY 自己重写,例如 HostContent-LengthAccept-Encoding

2. DSL 形态

request_header_overrides 是一个扁平 JSON object。

支持的 key 只有两类:

  • "*"
  • 普通 header 名

当前不支持:

  • regex
  • 嵌套 DSL
  • operation list

3. "*" 的语义

"*": true 表示透传所有允许透传的 inbound headers。

示例:

request_header_overrides:
"*": true

当前 * 只接受 bool,并且通常只有 true 有意义。

示例:

  • {"*": true}
    • 合法,启用全量安全透传
  • {"*": false}
    • 合法,但等同于不开启 wildcard 透传
  • {"*": "yes"}
    • 非法

"*": true 透传时会跳过这些 header:

  • Host
  • Content-Length
  • Accept-Encoding
  • Connection
  • Keep-Alive
  • Proxy-Authenticate
  • Proxy-Authorization
  • TE
  • Trailer
  • Transfer-Encoding
  • Upgrade
  • Cookie
  • Authorization
  • x-api-key
  • x-goog-api-key
  • sec-websocket-key
  • sec-websocket-version
  • sec-websocket-extensions

也就是说:

  • wildcard 不会透传认证头
  • wildcard 不会透传 hop-by-hop / transport 头

4. 普通 Header Key 的语义

普通 header 名的 value 只允许三种形式:

  • true
  • false
  • string

4.1 true

表示显式透传该 inbound header。

示例:

request_header_overrides:
x-trace-id: true

语义:

  • 如果客户端带了 X-Trace-Id,则把它透传到 upstream
  • 如果客户端没带,则删除当前已有的同名 header

注意:

  • 这里不是“保留原值”,而是“只使用客户端值”
  • 对于重复 header 值,true 透传会保留全部值

4.2 false

表示显式删除该 header。

示例:

request_header_overrides:
x-static: false

语义:

  • 无论该 header 来自协议层、静态 headers 还是 wildcard 透传,都会在这一层被删除

4.3 string

表示显式设置或覆盖该 header。

示例:

request_header_overrides:
authorization: "Bearer override-token"

语义:

  • 该字符串会直接作为最终 header 值写入

5. 占位符

当 value 是 string 时,支持两种占位符:

  • {api_key}
  • {client_header:<name>}

占位符必须占满整个 value,不支持字符串拼接。

5.1 {api_key}

表示当前被选中的 upstream API key 明文值。

示例:

request_header_overrides:
x-api-key: "{api_key}"

语义:

  • 如果当前 upstream 有可用 API key,则把该值写入目标 header
  • 如果当前 upstream 没有 API key,则跳过该 override,不写入 header

5.2 {client_header:<name>}

表示从 inbound request 中读取指定 header 的值。

示例:

request_header_overrides:
x-upstream-client: "{client_header:x-client-header}"

语义:

  • 如果客户端带了对应 header,则使用该值
  • 如果客户端没带,则跳过该 override
  • 这里使用的是第一个 header 值,不做多值展开

非法示例:

  • "Bearer {api_key}"
  • "prefix-{client_header:x-trace-id}"

因为占位符必须占满整个 value。

6. 显式规则与 Wildcard 的优先级

执行顺序固定为:

  1. 先应用 *
  2. 再应用普通 header key

因此普通 header key 的优先级更高。

示例:

request_header_overrides:
"*": true
authorization: "Bearer override-token"
x-static: false

语义:

  • 先透传所有允许的 inbound headers
  • 然后把 Authorization 强制改成固定值
  • 再删除 X-Static

7. Host 相关限制

当前 request_header_overrides 不支持:

  • 覆盖 Host
  • 删除 Host
  • 透传 Host

也就是说,以下写法当前都非法:

request_header_overrides:
host: true
request_header_overrides:
host: false
request_header_overrides:
host: "{client_header:host}"

最终 Host 始终由实际选中的 upstream URL 决定。

8. 完整示例

providers:
- name: openai-compatible
protocol: chat-completions
base_url: https://api.openai.com/v1
request_header_overrides:
"*": true
authorization: "Bearer override-token"
x-static: false
x-upstream-client: "{client_header:x-client-header}"

upstreams:
- name: primary
provider_id: gp_xxx
request_header_overrides:
x-trace-id: true
x-api-key: "{api_key}"

上面的最终效果是:

  • provider 默认开启 wildcard 透传
  • provider 把 Authorization 固定覆盖为指定值
  • provider 删除 X-Static
  • provider 把客户端的 X-Client-Header 改名写到 X-Upstream-Client
  • upstream 再额外声明 X-Trace-Id 只使用客户端值
  • upstream 还会把当前选中的 API key 写到 X-Api-Key

9. 什么时候该用 compat

如果你想控制的是协议特有 header,不要优先写到 request_header_overrides,而应先看该协议是否已经通过 compat 提供正式入口。

当前最典型的例子是:

  • claude-messages
    • anthropic_version
    • anthropic_beta

这类 header 应优先通过 compat 配置,而不是把协议逻辑硬塞到通用 override DSL 里。