fix(claude): project CLAUDE_CODE_AUTO_MODE_SERVER from provider env into settings.json (#7893)

Claude Code 2.1.281 added a server-side auto mode classifier that only
works on official endpoints. Sessions routed through a gateway (or the
built-in proxy) get a blocking notice unless CLAUDE_CODE_AUTO_MODE_SERVER
is set to 0 — the officially documented compatibility option for proxies
and gateways. Providers carry that key in their env row, but the live
projection only writes floor (connection/auth/model) and exclusive
(compat switch) keys, so it never reached settings.json and the notice
kept coming back after every switch.

Classify it as a provider-exclusive env key: it is written on switch-in
and removed on switch-out only when the value is unchanged, so users can
still set it globally on their own. The frontend preset-scan mirror
(tests/config/claudeKeyFields.json) is updated in lockstep; the mirror
test keeps both sides honest.

Fixes #7891
This commit is contained in:
Sailing Loong authored and GitHub committed 2026-10-06 09:06:09 +08:00
1 parent bf2fe0d0be
commit cf567ca648
3 files changed
+34

No files matched your search

+3
View File
@@ -98,6 +98,9 @@ pub const CLAUDE_EXCLUSIVE_ENV: &[&str] = &[
"CLAUDE_CODE_ALWAYS_ENABLE_EFFORT",
"CLAUDE_CODE_EXTRA_BODY",
"CLAUDE_CODE_ENABLE_FINE_GRAINED_TOOL_STREAMING",
// auto mode 的服务端分类器只有官方端点支持;网关场景要设 0,否则会话被
// 阻断式提示卡住(官方文档给代理、网关的兼容选项)。
"CLAUDE_CODE_AUTO_MODE_SERVER",
// 窗口类:取值由上游模型的窗口决定。
"CLAUDE_CODE_MAX_CONTEXT_TOKENS",
"CLAUDE_CODE_AUTO_COMPACT_WINDOW",
+30
View File
@@ -568,6 +568,36 @@ mod tests {
);
}
#[test]
fn gateway_compat_switches_reach_settings_json() {
// 回归:auto mode 的服务端分类器只有官方端点支持,网关场景的供应商行要带
// `CLAUDE_CODE_AUTO_MODE_SERVER=0`(官方文档给代理、网关的兼容选项)。
// 它此前不在独有字段清单里,行里写了也到不了 settings.json。
let gateway = json!({ "env": {
"ANTHROPIC_BASE_URL": "https://gw.example",
"ANTHROPIC_AUTH_TOKEN": "sk-gw",
"CLAUDE_CODE_AUTO_MODE_SERVER": "0"
}});
let live = json!({ "env": {
"ANTHROPIC_BASE_URL": "https://kimi.example",
"ANTHROPIC_AUTH_TOKEN": "sk-kimi"
}});
let out = project(&live, Some(&kimi()), &gateway);
assert_eq!(out["env"]["CLAUDE_CODE_AUTO_MODE_SERVER"], json!("0"));
// 切回不带它的官方端点:值没被改过,跟着上一家走。
let live = json!({ "env": {
"ANTHROPIC_BASE_URL": "https://gw.example",
"ANTHROPIC_AUTH_TOKEN": "sk-gw",
"CLAUDE_CODE_AUTO_MODE_SERVER": "0"
}});
let official = json!({ "env": { "ANTHROPIC_AUTH_TOKEN": "sk-official" } });
assert_eq!(
project(&live, Some(&gateway), &official)["env"].get("CLAUDE_CODE_AUTO_MODE_SERVER"),
None
);
}
#[test]
fn residue_goes_but_the_targets_own_value_stays_in_place() {
// 旧版给 Kimi 注入的 262144,上一家行里没有:残留清理兜住。
+1
View File
@@ -44,6 +44,7 @@
"CLAUDE_CODE_ALWAYS_ENABLE_EFFORT",
"CLAUDE_CODE_EXTRA_BODY",
"CLAUDE_CODE_ENABLE_FINE_GRAINED_TOOL_STREAMING",
"CLAUDE_CODE_AUTO_MODE_SERVER",
"CLAUDE_CODE_MAX_CONTEXT_TOKENS",
"CLAUDE_CODE_AUTO_COMPACT_WINDOW",
"CLAUDE_CODE_MAX_OUTPUT_TOKENS",