fix(core,manager): 按模型粒度配置上下文窗口(model_catalog_json + 后缀语法)#1197
Open
jarvislee90s-dot wants to merge 23 commits into
Open
fix(core,manager): 按模型粒度配置上下文窗口(model_catalog_json + 后缀语法)#1197jarvislee90s-dot wants to merge 23 commits into
jarvislee90s-dot wants to merge 23 commits into
Conversation
- AGENTS.md: fork 工作规范(安全/编码/测试/上游同步) - docs/research/01-调研结果.md: cc-switch 机制、CodexPlusPlus 源码根因、BigPizzaV3#931 验证结论 - docs/specs/2026-06-23-model-catalog-prototype-design.md: 阶段一原型设计(后缀语法+catalog 生成) - docs/plans/三阶段计划.md: 原型验证→后端完整→前端全栈 PR 对应 issue BigPizzaV3#1171 / BigPizzaV3#931
Mac 上是 /usr/local/bin/codex(codex-cli 0.128.0),非 .exe。 BigPizzaV3#931 的 exe 表述是 Windows 用户语境,统一改为 codex 客户端。
6 个任务:后缀解析器→条目收集与JSON构建→apply接入3入口→兼容回归测试→ example工具→A预检+B对拍实跑验证。带结果验证与测试方案,自检通过。
实现 parse_model_suffix、collect_catalog_entries、build_model_catalog_json, 解析 deepseek-v4-pro[1M] 这类后缀语法并生成 codex 原生 catalog 格式。 当前 model 在 model_list 中存在同名后缀条目时采纳其窗口值,避免 catalog 中当前模型窗口丢失。
新增 apply_model_catalog_to_config,接入 3 个 apply 入口(limits 之后、落盘之前)。 有后缀条目才生成 catalog + 写相对路径指针;无后缀 no-op;用户手写指针不覆盖。
无后缀 no-op、用户手写指针不覆盖;确认现有 does_not_write / preserves 用例未破坏。
codex 0.128.0 对 model_catalog_json 字段要求严格,最小字段集报 missing field supported_reasoning_levels/base_instructions 等。 改为 compile-time 引入 assets/codex-models.json 作为 template, 生成每条 entry 时 clone 模板再覆盖关键字段,并显式写 effective_context_window_percent=100 以显示真实窗口。 B 对拍已通过:deepseek-v4-pro=1000000、claude-sonnet-4=200000。
原 or_insert 只记录首次出现的后缀,若同名条目先无后缀后有后缀, current_model 无法拿到正确窗口。改为 insert 让靠后声明的后缀生效, 并补充覆盖该场景的测试。
问题:用户在「配置模型」或「模型列表」中使用 deepseek-v4-flash[1M] 等后缀语法时, 后缀会原样写入 config.toml 的 model = 。codex 按原串匹配 model_catalog_json 里的 slug, 导致匹配失败并回退到内置 272K 窗口,从而在 ~245K 就触发自动压缩。 修复: - 后端:complete_relay_profile_config 写入 model 前剥离后缀,保证 catalog slug 与 model 一致 - 后端:新增回归测试覆盖 profile.model / config_contents 带后缀的场景 - 前端:保存与预览 config.toml 时也剥离 model 后缀,界面输入框仍保留后缀便于用户识别 - .gitignore:忽略 pnpm-lock.yaml / pnpm-workspace.yaml
|
👋 感谢贡献!此 PR 当前存在 合并冲突,无法直接合并。 |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
背景
Closes #1171,基于 #931 已确认的运行时根因做 CodexPlusPlus 侧的自动化实现。
目前 CodexPlusPlus 的上下文窗口是按 relay profile 单值配置的:一个 profile 只有一个
model_context_window。当模型列表里同时存在deepseek-v4-pro(1M)、claude-sonnet-4(200K)等不同窗口的模型时,用户只能二选一:要么统一写成 1M 导致小窗口模型配额浪费,要么统一写成 200K 导致大模型被提前压缩。本 PR 引入 模型级后缀语法 + 自动 model_catalog_json 生成,让每个模型可以独立声明上下文窗口,切换模型即生效。
用法
在「供应商配置 → 配置模型」或「模型列表」里,给模型名加后缀即可:
支持的后缀格式:
[1M]/[1m][200K]/[200k][1000000]不写后缀的模型继续使用 Codex 默认长度(272K)。
实现原理
采用 codex 原生
model_catalog_json机制(与 cc-switch 思路一致):slug和context_window。<home>/model-catalogs/<profile-id>.json:slug、display_name、context_window、max_context_window、effective_context_window_percent=100;context_window。config.toml写入model_catalog_json = "model-catalogs/<profile-id>.json"。model匹配对应窗口。关键修复
之前存在的 bug
后缀会原样泄漏到
config.toml的model字段:codex 本身不理解
[1M],会按这个带后缀的字符串去 catalog 里匹配 slug。catalog 里生成的 slug 是剥离后缀的deepseek-v4-flash,于是匹配失败,codex 回退到内置 272K 窗口,导致在 ~245K 就触发自动压缩(用户报告的现象)。本次修复
complete_relay_profile_config写入model前调用parse_model_suffix剥离后缀。config.toml 预览时也剥离 model 后缀;界面输入框仍保留后缀,方便用户识别配置。profile.model带后缀、config_contents带后缀、无后缀条目不生成 catalog、用户手写model_catalog_json不被覆盖等场景。主要改动
后端(Rust)
crates/codex-plus-core/src/model_suffix.rsparse_model_suffix、collect_catalog_entries、build_model_catalog_json,处理后缀解析与 catalog 生成crates/codex-plus-core/src/relay_config.rsapply_model_catalog_to_config接入 apply 流程;complete_relay_profile_config写入 model 前剥离后缀crates/codex-plus-core/src/model_catalog.rscrates/codex-plus-core/examples/generate_model_catalog.rscrates/codex-plus-core/tests/model_suffix.rscrates/codex-plus-core/tests/relay_config.rscrates/codex-plus-core/assets/codex-models.json前端(React + TS)
apps/codex-plus-manager/src/App.tsx文档
docs/plans/:阶段一实现计划、前端 suffix 提示设计文档docs/research/:A/B 对拍、字段/路径/副作用调研docs/specs/:验证记录(Ark 端点大上下文验证、前端 suffix 提示验证)验证
cargo test -p codex-plus-core --test relay_config --test model_suffix --test model_catalog --test relay_switch:85 + 9 + 6 + 4 = 104 个测试通过cargo test -p codex-plus-manager:39 个测试通过deepseek-v4-flash[1M]/kimi-k2.6[262K]/minimax-m3[1M],上下文可超过 245K 继续消耗兼容性
config.toml手写model_catalog_json时不会被覆盖。后续可扩展
auto_compact_token_limit目前置为null(codex 内置模型同此行为),后续可按模型/按比例配置压缩阈值([Feature] 按模型粒度配置上下文窗口与自动压缩阈值(参考 cc-switch 的 model_catalog_json 机制) #1171 诉求 2)。