Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
16 commits
Select commit Hold shift + click to select a range
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
83 changes: 77 additions & 6 deletions CONFIGURATION.md
Original file line number Diff line number Diff line change
Expand Up @@ -157,15 +157,15 @@ Core compression behavior.

#### `compress.maxContextLimit`
- **Type:** `number | \`${number}%\``
- **Default:** `"55%"`
- **Default:** `"80%"`
- **Status:** ACTIVE
- **Description:** Upper context usage threshold (as % of model context window or absolute tokens). When exceeded, ACP nudges the model to compress. Example: `"55%"` or `100000`.
- **Description:** Upper context usage threshold (as % of model context window or absolute tokens). When exceeded, ACP nudges the model to compress. Example: `"80%"` or `100000`.

#### `compress.minContextLimit`
- **Type:** `number | \`${number}%\``
- **Default:** `"45%"`
- **Default:** `"80%"`
- **Status:** ACTIVE
- **Description:** Lower context usage threshold. ACP stops nudging when usage drops below this level.
- **Description:** Lower context usage threshold for turn/iteration reminder nudges. ACP stops injecting those reminders when usage drops below this level (or when the limit cannot be resolved to a concrete value, e.g. a `"X%"` limit with an unknown model context window). Growth nudges are governed separately by `minNudgeContextPercent`.

#### `compress.modelMaxLimits`
- **Type:** `Record<string, number | \`${number}%\`>`
Expand All @@ -187,9 +187,41 @@ Core compression behavior.

#### `compress.minNudgeContextPercent`
- **Type:** `number`
- **Default:** `15`
- **Default:** `5`
- **Status:** ACTIVE
- **Description:** Floor for growth-triggered nudges, as a percentage of the model context window: a growth nudge requires context usage at or above this percentage (in addition to the growth threshold). Over-max (`maxContextLimit`) and the 98% emergency-override nudges bypass the floor. If the model context window is unknown, the floor is unresolvable and growth nudges fall back to growth-only behavior. Turn/iteration reminder nudges are governed by `minContextLimit`, not this field. The default is deliberately low: with the default `nudgeGrowthTokens` (50K), a 5% floor stays inert for typical working cycles and only binds on very large (≥2M-class) windows — a higher default (e.g. 15%) would bind on ≥400K windows and shift every compress cycle's working range upward on large-window models. Set `0` to disable the floor entirely, or raise it (e.g. 15–30%) to keep growth nudges waiting until a larger share of the window is in use. Can be narrowed per provider / per model via [`compress.providers`](#compressproviders) (issue #344).

#### `compress.providers`
- **Type:** `Record<string, ProviderOverrides>` where `ProviderOverrides = Partial<CompressOverridableConfig> & { models?: Record<string, Partial<CompressOverridableConfig>> }` (all fields optional at both levels)
- **Default:** `undefined`
- **Status:** ACTIVE
- **Description:** Minimum context usage percentage before any nudges are shown. Below this, no nudges are injected.
- **Description:** Nested per-provider / per-model overrides for **every tunable compress field**, resolved field-by-field with the cascade **model > provider > global** (mirrors the sibling project billion-context-pi, issue #344). Deeper levels only override when the field is explicitly set — unset fields never clear shallower values. `0` / `false` are explicit values, not "unset". Unknown provider/model ids fall back to the global value. Percentages and `"X%"` limits resolve against the active model's context window. Across the three config file layers (global → config dir → project) the maps deep-merge per provider/model key — a project layer can narrow one provider without wiping others configured in lower layers.
- **Overridable fields:** `maxContextLimit`, `emergencyThresholdPercent`, `minNudgeContextPercent`, `nudgeFrequency`, `iterationNudgeThreshold`, `toolOutputNudgeThreshold`, `nudgeGrowthTokens`, `minNudgeGrowthRatio`, `minNudgeGrowthFloor`, `nudgeForce`, `protectedTools`, `showCompression`, `summaryBuffer`, `protectTags`, `protectUserMessages`, `maxSummaryLengthHard`, `minCompressRange`, `maxVisibleSegments`, `keepEmbedMaxChars`, `lastSegmentSoftBlock`, `preserveRecentMessages`, `preserveRecentTokens`, `preserveLastUserMessage`.
- **Not overridable:** `permission` (session-level, fixed before model info is known), the deprecated `minContextLimit` / `modelMinLimits` family, the flat `modelMaxLimits` map (legacy), and `providers` itself. For `maxContextLimit` the precedence when set nested is **nested override > `modelMaxLimits` flat map > global**. `protectedTools` set here affects the compress tool and nudge-side logic; the system-prompt protected-tools listing (shown at prompt build time, before model info is available) always reflects the global value.

```jsonc
{
"compress": {
"maxContextLimit": "55%",
"minNudgeContextPercent": 5,
"nudgeGrowthTokens": 50000,
"providers": {
"anthropic": {
"minNudgeContextPercent": 8,
"nudgeForce": "strong",
"models": {
"claude-sonnet-4-6": {
"minNudgeContextPercent": 30,
"maxContextLimit": "70%",
"nudgeGrowthTokens": 20000
}
}
}
}
}
}
```
In this example, for `anthropic/claude-sonnet-4-6`: the floor is 30%, the over-max band starts at 70% of the window instead of the global 55% (a larger working range before over-max nudges kick in), the growth threshold is 20K, and nudges use the `strong` tone (inherited from the provider level). Every other Anthropic model gets the 8% floor and `strong` tone but keeps the global band and 50K growth threshold; everything else uses the pure global values. Provider keys are provider ids and model keys are model ids (as reported by the active session, e.g. `anthropic`, `claude-sonnet-4-6`).

#### `compress.nudgeGrowthTokens`
- **Type:** `number`
Expand Down Expand Up @@ -447,6 +479,45 @@ Post-compression quality evaluation. Runs after each compression to verify summa
}
```

### Per-model growth-nudge floor (nested providers.models)
```jsonc
{
"compress": {
"minNudgeContextPercent": 5,
"providers": {
"anthropic": {
"minNudgeContextPercent": 8,
"models": {
"claude-sonnet-4-6": { "minNudgeContextPercent": 30 },
"claude-haiku-4-5": { "minNudgeContextPercent": 0 }
}
}
}
}
}
```
Floors resolve as model > provider > global (field-by-field). `0` disables the floor for that model — useful for small-window models where the growth threshold alone is the right signal.

### Per-model tuning of any compress field (nested providers.models)
The same cascade works for every tunable field, not just the floor — e.g. give one heavy model a tighter growth threshold and a lower over-max band while its siblings keep the global profile:
```jsonc
{
"compress": {
"providers": {
"anthropic": {
"models": {
"claude-sonnet-4-6": {
"nudgeGrowthTokens": 20000,
"maxContextLimit": "40%"
}
}
}
}
}
}
```
See the [`compress.providers`](#compressproviders) reference for the full overridable field list.

### Protect sensitive files
```jsonc
{
Expand Down
75 changes: 73 additions & 2 deletions CONFIGURATION.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -187,9 +187,41 @@ ACP 从最多三层配置文件中读取(后加载的覆盖先加载的):

#### `compress.minNudgeContextPercent`
- **类型:** `number`
- **默认值:** `15`
- **默认值:** `5`
- **状态:** ACTIVE
- **说明:** 增长触发型 nudge 的上下文使用率下限(占模型上下文窗口的百分比):增长 nudge 要求上下文使用率达到或超过此百分比(此外还需满足增长阈值)。超过上限(`maxContextLimit`)与 98% 紧急覆盖的 nudge 不受此下限约束。若模型上下文窗口未知,则无法计算该下限,增长 nudge 回退为仅按增长触发的行为。轮次/迭代提醒 nudge 由 `minContextLimit` 控制,而非此字段。默认值刻意设低:在默认 `nudgeGrowthTokens`(50K)下,5% 下限对典型工作周期不生效,仅在非常大的(≥2M 级)窗口上才生效——更高的默认值(如 15%)会在 ≥400K 窗口上生效,并推高大型窗口模型上每个压缩周期的工作区间。设为 `0` 可完全禁用该下限,或调高(如 15–30%)使增长 nudge 等待更大的窗口占用比例。可通过 [`compress.providers`](#compressproviders) 按 provider / 按模型细化(issue #344)。

#### `compress.providers`
- **类型:** `Record<string, ProviderOverrides>`,其中 `ProviderOverrides = Partial<CompressOverridableConfig> & { models?: Record<string, Partial<CompressOverridableConfig>> }`(两级均所有字段可选)
- **默认值:** `undefined`
- **状态:** ACTIVE
- **说明:** 触发任何 nudge 的最低上下文使用率百分比。低于此值时不注入 nudge。
- **说明:** 对**所有可调 compress 字段**的嵌套按 provider / 按模型覆盖,逐字段按 **模型 > provider > 全局** 级联解析(与姊妹项目 billion-context-pi 一致,issue #344)。深层仅在该字段被显式设置时才覆盖——未设置的字段不会清空浅层取值;`0` / `false` 是显式值,而非“未设置”。未知的 provider/model id 回退到全局值。百分比与 `"X%"` 限额按当前激活模型的上下文窗口换算。在三个配置文件层(全局 → 配置目录 → 项目)之间,该映射按 provider/model 键深度合并——项目层可以只细化某个 provider 而不清掉低层配置的其他 provider。
- **可覆盖字段:** `maxContextLimit`、`emergencyThresholdPercent`、`minNudgeContextPercent`、`nudgeFrequency`、`iterationNudgeThreshold`、`toolOutputNudgeThreshold`、`nudgeGrowthTokens`、`minNudgeGrowthRatio`、`minNudgeGrowthFloor`、`nudgeForce`、`protectedTools`、`showCompression`、`summaryBuffer`、`protectTags`、`protectUserMessages`、`maxSummaryLengthHard`、`minCompressRange`、`maxVisibleSegments`、`keepEmbedMaxChars`、`lastSegmentSoftBlock`、`preserveRecentMessages`、`preserveRecentTokens`、`preserveLastUserMessage`。
- **不可覆盖:** `permission`(会话级,在得知模型信息前已固定)、已废弃的 `minContextLimit` / `modelMinLimits` 系列、旧版扁平 `modelMaxLimits` 映射、以及 `providers` 本身。`maxContextLimit` 在嵌套层设置时的优先级为 **嵌套覆盖 > `modelMaxLimits` 扁平映射 > 全局**。在此设置的 `protectedTools` 影响压缩工具与 nudge 侧逻辑;系统提示词中的受保护工具列表(在提示词构建时生成,早于模型信息可用)始终反映全局值。

```jsonc
{
"compress": {
"maxContextLimit": "55%",
"minNudgeContextPercent": 5,
"nudgeGrowthTokens": 50000,
"providers": {
"anthropic": {
"minNudgeContextPercent": 8,
"nudgeForce": "strong",
"models": {
"claude-sonnet-4-6": {
"minNudgeContextPercent": 30,
"maxContextLimit": "70%",
"nudgeGrowthTokens": 20000
}
}
}
}
}
}
```
此例中,对 `anthropic/claude-sonnet-4-6`:下限为 30%,超限(over-max)区间从窗口的 70% 开始(而非全局 55%,即更大的工作区间),增长阈值为 20K,nudge 语气为 `strong`(继承自 provider 层)。其他 Anthropic 模型获得 8% 下限与 `strong` 语气,但保留全局的区间与 50K 增长阈值;其余全部使用纯全局值。provider 键为 provider id,model 键为模型 id(取自当前激活会话上报的标识,如 `anthropic`、`claude-sonnet-4-6`)。

#### `compress.nudgeGrowthTokens`
- **类型:** `number`
Expand Down Expand Up @@ -447,6 +479,45 @@ ACP 从最多三层配置文件中读取(后加载的覆盖先加载的):
}
```

### 按模型设置增长 nudge 下限(嵌套 providers.models)
```jsonc
{
"compress": {
"minNudgeContextPercent": 5,
"providers": {
"anthropic": {
"minNudgeContextPercent": 8,
"models": {
"claude-sonnet-4-6": { "minNudgeContextPercent": 30 },
"claude-haiku-4-5": { "minNudgeContextPercent": 0 }
}
}
}
}
}
```
下限按 **模型 > provider > 全局** 逐字段解析。`0` 表示为该模型禁用下限——适用于小窗口模型,仅靠增长阈值触发即可。

### 按模型调优任意 compress 字段(嵌套 providers.models)
同样的级联适用于所有可调字段,而不仅是下限——例如给某个重度使用的模型设置更紧的增长阈值与更低的超限区间,而同 provider 的其他模型保持全局配置:
```jsonc
{
"compress": {
"providers": {
"anthropic": {
"models": {
"claude-sonnet-4-6": {
"nudgeGrowthTokens": 20000,
"maxContextLimit": "40%"
}
}
}
}
}
}
```
完整可覆盖字段列表见 [`compress.providers`](#compressproviders) 参考节。

### 保护敏感文件
```jsonc
{
Expand Down
53 changes: 48 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -324,11 +324,12 @@ Each level overrides the previous, so project settings take priority over global
// Soft upper threshold: above this, ACP keeps injecting strong
// compression nudges (based on nudgeFrequency), so compression is
// much more likely. Accepts: number or "X%" of model context window.
"maxContextLimit": "55%",
// Soft lower threshold for reminder nudges: below this, turn/iteration
// reminders are off (compression less likely). At/above this, reminders
// are on. Accepts: number or "X%" of model context window.
"minContextLimit": "45%",
"maxContextLimit": "80%",
// Soft lower threshold for turn/iteration reminder nudges: below this,
// those reminders are off (compression less likely). At/above this, they
// are on. Growth nudges have their own floor: minNudgeContextPercent.
// Accepts: number or "X%" of model context window.
"minContextLimit": "80%",
// Optional per-model override for maxContextLimit by providerID/modelID.
// If present, this wins over the global maxContextLimit.
// Accepts: number or "X%".
Expand All @@ -343,6 +344,21 @@ Each level overrides the previous, so project settings take priority over global
// "openai/gpt-5.3-codex": 50000,
// "anthropic/claude-sonnet-4.6": "25%"
// },
// Nested per-provider/per-model overrides for ANY compress field
// (23 fields: thresholds, nudge behavior, protection, ...).
// Resolution is per field: model > provider > global. Unknown
// provider/model IDs fall back to the global value.
// "providers": {
// "anthropic": {
// "nudgeGrowthTokens": 50000,
// "models": {
// "claude-sonnet-4.6": {
// "maxContextLimit": "70%",
// "minNudgeContextPercent": 10
// }
// }
// }
// },
// How often the context-limit nudge fires (1 = every fetch, 5 = every 5th)
"nudgeFrequency": 5,
// Start adding compression reminders after this many
Expand Down Expand Up @@ -402,6 +418,33 @@ Each level overrides the previous, so project settings take priority over global

</details>

### Per-Provider / Per-Model Overrides

Any `compress` field can be overridden per provider and per model via the nested `compress.providers` map:

```jsonc
{
"compress": {
"maxContextLimit": "80%",
"providers": {
"anthropic": {
"nudgeGrowthTokens": 20000,
"models": {
"claude-sonnet-4.6": { "maxContextLimit": "70%", "nudgeForce": "strong" }
}
},
"openai": { "nudgeGrowthTokens": 40000 }
}
}
}
```

Resolution is **per field**: model > provider > global. Unknown provider/model IDs fall back to the global value. A nested `maxContextLimit` also wins over the legacy flat `modelMaxLimits` map. Overrides deep-merge across the three config layers (global → config dir → project) per provider/model key.

Not overridable here: `permission`, the deprecated `minContextLimit` family, and the flat `model*Limits` maps themselves.

See the [`compress.providers`](./CONFIGURATION.md#compressproviders) reference in CONFIGURATION.md for the full 23-field list and recipes.

### Prompt Overrides

ACP exposes six editable prompts:
Expand Down
42 changes: 42 additions & 0 deletions README.zh-CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,21 @@ ACP 使用自己的配置文件,按以下顺序搜索:
// "openai/gpt-5.3-codex": 50000,
// "anthropic/claude-sonnet-4.6": "25%"
// },
// 嵌套的 provider/model 级覆盖:可覆盖任意 compress 字段
// (23 项:阈值、nudge 行为、保护策略等)。
// 逐字段解析优先级:model > provider > 全局。
// 未知的 provider/model ID 回退到全局值。
// "providers": {
// "anthropic": {
// "nudgeGrowthTokens": 50000,
// "models": {
// "claude-sonnet-4.6": {
// "maxContextLimit": "70%",
// "minNudgeContextPercent": 10
// }
// }
// }
// },
// How often the context-limit nudge fires (1 = every fetch, 5 = every 5th)
"nudgeFrequency": 5,
// Start adding compression reminders after this many
Expand Down Expand Up @@ -355,6 +370,33 @@ ACP 使用自己的配置文件,按以下顺序搜索:

</details>

### 按 Provider / 按模型覆盖

任意 `compress` 字段都可通过嵌套的 `compress.providers` 按 provider 和按模型覆盖:

```jsonc
{
"compress": {
"maxContextLimit": "80%",
"providers": {
"anthropic": {
"nudgeGrowthTokens": 20000,
"models": {
"claude-sonnet-4.6": { "maxContextLimit": "70%", "nudgeForce": "strong" }
}
},
"openai": { "nudgeGrowthTokens": 40000 }
}
}
}
```

解析为**逐字段**优先级:model > provider > 全局。未知的 provider/model ID 回退到全局值。嵌套的 `maxContextLimit` 同时优先于旧版扁平 `modelMaxLimits` 映射。多层配置(全局 → 配置目录 → 项目)按 provider/model 键深合并。

不可覆盖:`permission`、已废弃的 `minContextLimit` 系列,以及扁平 `model*Limits` 映射自身。

完整 23 项字段清单与配方见 CONFIGURATION.zh-CN.md 的 [`compress.providers`](./CONFIGURATION.zh-CN.md#compressproviders) 参考节。

### Prompt 覆盖

ACP 暴露六个可编辑的 prompt:
Expand Down
Loading
Loading