# PR #30077 完整报告

- 仓库：`sgl-project/sglang`
- 标题：[refactor] Rename Arg.model_overridable to Arg.resolvable (stack 15/15)
- 合并时间：2026-07-04 17:23
- 原文链接：http://prhub.com.cn/sgl-project/sglang/pull/30077

---

# 执行摘要

- 一句话：重命名 Arg.model_overridable 为 Arg.resolvable
- 推荐动作：值得快速审阅，因变更机械且已通过测试。但作为堆栈的最后一环，建议结合全局 PR #30062 理解整体配置解析重构的背景。

# 功能与动机

PR body 指出：由于 post-process stage 已落地，`model_overridable` 标签实际标记任何可由配置解析写入的字段（model overrides 和 normalization passes alike），`sampling_backend` 和 `page_size` 并非 model overrides。因此需要重命名为 `resolvable` 以准确反映其用途。

# 实现拆解

1. **字段重命名（arg_utils.py）**：将 `Arg` 数据类的 `model_overridable: bool` 字段重命名为 `resolvable: bool`，并同步更新其文档注释。同时将 `model_overridable_fields()` 函数重命名为 `resolvable_fields()`，内部检查逻辑改为 `arg.resolvable`。
2. **调用站点更新（server_args.py）**：在 `ServerArgs` 类的 16 处字段定义中，将所有 `model_overridable=True` 替换为 `resolvable=True`，涉及 dtype、quantization、enable_tf32_matmul 等配置项。
3. **依赖与调用更新（overrides.py）**：更新 import 语句，将 `model_overridable_fields` 替换为 `resolvable_fields`；在 `apply_model_overrides` 和 `apply_declarations_to_server_args` 函数中同步更新调用。
4. **测试配套更新（test_model_overrides.py）**：更新导入和测试断言，将 `model_overridable_fields` 替换为 `resolvable_fields`，并将测试夹具中的 `model_overridable=True` 替换为 `resolvable=True`。

关键文件：
- `python/sglang/srt/arg_groups/arg_utils.py`（模块 参数工具；类别 source；类型 core-logic；符号 model_overridable_fields, resolvable_fields）: 核心更改所在：定义 Arg.resolvable 字段和 resolvable_fields 函数，是整个重命名的起点。
- `python/sglang/srt/server_args.py`（模块 启动参数；类别 source；类型 core-logic）: 包含最多的调用更新，16 处字段的 model_overridable 替换为 resolvable。
- `python/sglang/srt/arg_groups/overrides.py`（模块 覆盖逻辑；类别 source；类型 dependency-wiring）: 依赖更新：导入和引用从 model_overridable_fields 切换为 resolvable_fields。
- `test/registered/unit/test_model_overrides.py`（模块 覆盖测试；类别 test；类型 test-coverage）: 测试配套更新，确保新名称被正确测试。

关键符号：resolvable_fields

## 关键源码片段

### `python/sglang/srt/arg_groups/arg_utils.py`

核心更改所在：定义 Arg.resolvable 字段和 resolvable_fields 函数，是整个重命名的起点。

```python
# Arg 类的核心变更：model_overridable 字段更名为 resolvable
# 注释同步更新，强调此字段表示“可通过配置解析写入”
@dataclasses.dataclass(frozen=True)
class Arg:
    # ... 其他字段省略，仅展示重命名字段 ...
    # When True, this field may be written by config resolution (model
    # overrides and post-process passes): it is part of the whitelist accepted
    # by the apply_model_overrides gate, and its resolved value lives on the
    # flags tier (the server_args field itself stays the pristine user input).
    resolvable: bool = False

# 变更前：model_overridable_fields 函数，现重命名为 resolvable_fields
# 函数逻辑完全不变，只是使用新的字段名
@functools.lru_cache(maxsize=None)
def resolvable_fields(cls) -> frozenset:
    """Names of ``cls`` dataclass fields whose ``Arg`` metadata declares
    ``resolvable=True`` — the whitelist for config resolution.
    Non-dataclass types (e.g. mock config objects in tests) have no Arg
    metadata and yield an empty whitelist."""
    if not dataclasses.is_dataclass(cls):
        return frozenset()
    hints = get_type_hints(cls, include_extras=True)
    names = set()
    for field in dataclasses.fields(cls):
        _, arg = _unwrap_annotated(hints.get(field.name, field.type))
        if arg is not None and arg.resolvable:  # 使用新的字段名
            names.add(field.name)
    return frozenset(names)

```

# 评论区精华

该 PR 无 review 讨论，只有一条机器人注释（gemini-code-assist 配额警告），与变更无关。合并者与作者相同，且为堆栈 PR 的一部分，表明团队内部已达成一致。

- 暂无高价值评论线程

# 风险与影响

- 风险：风险极低。仅为机械重命名，语义不变，且所有调用点已通过同步更新覆盖。但若存在外部脚本或未入库的私有扩展引用了旧名称，可能会出现 ImportError。由于是内部 API，影响可控。
- 影响：
 - **用户影响**：无直接用户可见变化，CLI 参数和行为完全一致。
 - **系统影响**：无运行时行为变化。重命名后的 API 更准确地反映了字段用途，便于后续扩展。
 - **团队影响**：开发者需适应新命名，但仅涉及配置解析基础设施的内部模块。
 - 风险标记：暂无

# 关联脉络

- PR #30062 Global declarative config-resolution stack review: 此 PR 是声明式配置解析堆栈的一部分，全局 review PR #30062 包含完整的堆栈差异和 CI 结果。