From 83a52609575363b6dcb7b486717c700aca68c3bf Mon Sep 17 00:00:00 2001 From: roboomp Date: Tue, 16 Jun 2026 01:09:37 +0000 Subject: [PATCH] fix(coding-agent): accepted max thinking alias Mapped the user-facing max thinking selector to the canonical xhigh effort so DeepSeek V4 Pro selectors and --thinking can request provider maximum reasoning.\n\nFixes #2727 --- packages/coding-agent/CHANGELOG.md | 4 +++ packages/coding-agent/src/thinking.ts | 26 +++++++++++++++---- .../test/auto-thinking-classifier.test.ts | 13 ++++++++++ 3 files changed, 38 insertions(+), 5 deletions(-) diff --git a/packages/coding-agent/CHANGELOG.md b/packages/coding-agent/CHANGELOG.md index ce58d520d..5e2fb4e99 100644 --- a/packages/coding-agent/CHANGELOG.md +++ b/packages/coding-agent/CHANGELOG.md @@ -2,6 +2,10 @@ ## [Unreleased] +### Fixed + +- Accepted `max` as an alias for the top thinking level (`xhigh`) in selectors and `--thinking`, so DeepSeek V4 Pro can be selected with its provider-facing maximum effort ([#2727](https://github.com/can1357/oh-my-pi/issues/2727)). + ## [16.0.1] - 2026-06-15 ### Breaking Changes diff --git a/packages/coding-agent/src/thinking.ts b/packages/coding-agent/src/thinking.ts index f7361dd63..96a25655f 100644 --- a/packages/coding-agent/src/thinking.ts +++ b/packages/coding-agent/src/thinking.ts @@ -32,26 +32,42 @@ const THINKING_LEVEL_METADATA: Record = { [ThinkingLevel.High]: { value: ThinkingLevel.High, label: "high", description: "Deep reasoning (~16k tokens)" }, [ThinkingLevel.XHigh]: { value: ThinkingLevel.XHigh, - label: "xhigh", + label: "max", description: "Maximum reasoning (~32k tokens)", }, }; -const THINKING_LEVELS = new Set([ThinkingLevel.Inherit, ThinkingLevel.Off, ...THINKING_EFFORTS]); -const EFFORT_LEVELS = new Set(THINKING_EFFORTS); +const EFFORT_BY_SELECTOR: Readonly> = { + [Effort.Minimal]: Effort.Minimal, + [Effort.Low]: Effort.Low, + [Effort.Medium]: Effort.Medium, + [Effort.High]: Effort.High, + [Effort.XHigh]: Effort.XHigh, + max: Effort.XHigh, +}; +const THINKING_LEVEL_BY_SELECTOR: Readonly> = { + [ThinkingLevel.Inherit]: ThinkingLevel.Inherit, + [ThinkingLevel.Off]: ThinkingLevel.Off, + [ThinkingLevel.Minimal]: ThinkingLevel.Minimal, + [ThinkingLevel.Low]: ThinkingLevel.Low, + [ThinkingLevel.Medium]: ThinkingLevel.Medium, + [ThinkingLevel.High]: ThinkingLevel.High, + [ThinkingLevel.XHigh]: ThinkingLevel.XHigh, + max: ThinkingLevel.XHigh, +}; /** * Parses a provider-facing effort value. */ export function parseEffort(value: string | null | undefined): Effort | undefined { - return value !== undefined && value !== null && EFFORT_LEVELS.has(value) ? (value as Effort) : undefined; + return value === undefined || value === null ? undefined : EFFORT_BY_SELECTOR[value]; } /** * Parses an agent-local thinking selector. */ export function parseThinkingLevel(value: string | null | undefined): ThinkingLevel | undefined { - return value !== undefined && value !== null && THINKING_LEVELS.has(value) ? (value as ThinkingLevel) : undefined; + return value === undefined || value === null ? undefined : THINKING_LEVEL_BY_SELECTOR[value]; } /** diff --git a/packages/coding-agent/test/auto-thinking-classifier.test.ts b/packages/coding-agent/test/auto-thinking-classifier.test.ts index 3d4eb539e..3a9ed8227 100644 --- a/packages/coding-agent/test/auto-thinking-classifier.test.ts +++ b/packages/coding-agent/test/auto-thinking-classifier.test.ts @@ -3,10 +3,12 @@ import { ThinkingLevel } from "@oh-my-pi/pi-agent-core"; import { Effort } from "@oh-my-pi/pi-ai"; import { getBundledModel } from "@oh-my-pi/pi-catalog/models"; import { parseDifficultyBucket, parseDifficultyLevel } from "@oh-my-pi/pi-coding-agent/auto-thinking/classifier"; +import { parseModelString } from "@oh-my-pi/pi-coding-agent/config/model-resolver"; import { AUTO_THINKING, clampAutoThinkingEffort, parseConfiguredThinkingLevel, + parseEffort, parseThinkingLevel, } from "@oh-my-pi/pi-coding-agent/thinking"; @@ -41,4 +43,15 @@ describe("auto thinking classifier helpers", () => { expect(clampAutoThinkingEffort(model, Effort.XHigh)).toBe(Effort.High); expect(clampAutoThinkingEffort(model, Effort.Minimal)).toBe(Effort.Low); }); + + it("accepts max as the top thinking selector alias", () => { + expect(parseEffort("max")).toBe(Effort.XHigh); + expect(parseThinkingLevel("max")).toBe(ThinkingLevel.XHigh); + expect(parseConfiguredThinkingLevel("max")).toBe(ThinkingLevel.XHigh); + expect(parseModelString("deepseek/deepseek-v4-pro:max")).toEqual({ + provider: "deepseek", + id: "deepseek-v4-pro", + thinkingLevel: ThinkingLevel.XHigh, + }); + }); });