From 1b7a2951398576d88b728a49c7a448ff7f4465d6 Mon Sep 17 00:00:00 2001 From: ozymandiashh <234437643+ozymandiashh@users.noreply.github.com> Date: Sun, 21 Jun 2026 15:50:37 +0300 Subject: [PATCH] Distinguish gpt-5.3-codex-spark from base GPT-5.3 Codex label gpt-5.3-codex-spark is a distinct model variant, but the longest-first startsWith(key+'-') matcher (intended for reasoning suffixes -high/-low) swept it into the base 'GPT-5.3 Codex' label, making a distinct model look like the retired base in today/models/status output. Add an explicit display entry in SHORT_NAMES and the codex provider so the longer key wins; -high/-low still fall through to the base. Pricing is unaffected (LiteLLM has no spark entry; cost falls back to the base rate as before). Fixes #461 --- src/models.ts | 1 + src/providers/codex.ts | 1 + tests/models.test.ts | 12 ++++++++++++ tests/providers/codex.test.ts | 15 +++++++++++++++ 4 files changed, 29 insertions(+) diff --git a/src/models.ts b/src/models.ts index d929edaf..4616261f 100644 --- a/src/models.ts +++ b/src/models.ts @@ -621,6 +621,7 @@ const SHORT_NAMES: Record = { 'gpt-5.4-nano': 'GPT-5.4 Nano', 'gpt-5.4-mini': 'GPT-5.4 Mini', 'gpt-5.4': 'GPT-5.4', + 'gpt-5.3-codex-spark': 'GPT-5.3 Codex Spark', 'gpt-5.3-codex': 'GPT-5.3 Codex', 'gpt-5.3': 'GPT-5.3', 'gpt-5.2-pro': 'GPT-5.2 Pro', diff --git a/src/providers/codex.ts b/src/providers/codex.ts index e41a58b2..8cadf0d8 100644 --- a/src/providers/codex.ts +++ b/src/providers/codex.ts @@ -16,6 +16,7 @@ const modelDisplayNames: Record = { 'gpt-5.5': 'GPT-5.5', 'gpt-5.4-mini': 'GPT-5.4 Mini', 'gpt-5.4': 'GPT-5.4', + 'gpt-5.3-codex-spark': 'GPT-5.3 Codex Spark', 'gpt-5.3-codex': 'GPT-5.3 Codex', 'gpt-5.2-low': 'GPT-5.2 Low', 'gpt-5.2': 'GPT-5.2', diff --git a/tests/models.test.ts b/tests/models.test.ts index 2943f2e3..29fe3b72 100644 --- a/tests/models.test.ts +++ b/tests/models.test.ts @@ -51,6 +51,18 @@ describe('getShortModelName', () => { expect(getShortModelName('gpt-5.4-mini')).toBe('GPT-5.4 Mini') }) + // Regression for #461: spark is a distinct variant, not a reasoning suffix. + it('maps gpt-5.3-codex-spark to its own label (not GPT-5.3 Codex)', () => { + const name = getShortModelName('gpt-5.3-codex-spark') + expect(name).not.toBe('GPT-5.3 Codex') + expect(name).toBe('GPT-5.3 Codex Spark') + }) + + it('maps gpt-5.3-codex reasoning suffixes to the base label', () => { + expect(getShortModelName('gpt-5.3-codex-high')).toBe('GPT-5.3 Codex') + expect(getShortModelName('gpt-5.3-codex-low')).toBe('GPT-5.3 Codex') + }) + it('maps claude-opus-4-6 with date suffix', () => { expect(getShortModelName('claude-opus-4-6-20260205')).toBe('Opus 4.6') }) diff --git a/tests/providers/codex.test.ts b/tests/providers/codex.test.ts index 2b7fb962..958139f8 100644 --- a/tests/providers/codex.test.ts +++ b/tests/providers/codex.test.ts @@ -105,6 +105,21 @@ async function writeSession(dir: string, date: string, filename: string, lines: return filePath } +describe('codex provider - model display names', () => { + it('maps gpt-5.3-codex-spark to its own label', () => { + const provider = createCodexProvider(tmpDir) + const name = provider.modelDisplayName('gpt-5.3-codex-spark') + expect(name).not.toBe('GPT-5.3 Codex') + expect(name).toBe('GPT-5.3 Codex Spark') + }) + + it('maps gpt-5.3-codex reasoning suffixes to the base label', () => { + const provider = createCodexProvider(tmpDir) + expect(provider.modelDisplayName('gpt-5.3-codex-high')).toBe('GPT-5.3 Codex') + expect(provider.modelDisplayName('gpt-5.3-codex-low')).toBe('GPT-5.3 Codex') + }) +}) + describe('codex provider - session discovery', () => { it('discovers sessions in YYYY/MM/DD structure', async () => { await writeSession(tmpDir, '2026-04-14', 'rollout-abc123.jsonl', [