From d6406c4ffd98a0154d3f1c97b3f13d3c66ab2773 Mon Sep 17 00:00:00 2001 From: Oleg Samarin Date: Wed, 29 Apr 2026 12:21:48 +0300 Subject: [PATCH] Fixed model name detection for new CLI format with long label and spaced names - DESC_PAT: relaxed min-space threshold from 3 to 2 to handle "Default (recommended)" label whose 2-space column alignment was skipping the model entry entirely - CURRENTLY_PAT / hintPat / currentlyPat: widened capture from [\w/.-]+ to [^)]+? so names like "Sonnet 4" (containing a space) are extracted correctly instead of returning the full description string - Applied both fixes to ModelMenuParser and the inline patterns in ClaudeSessionController.discoverModels() - Added two new fixture test cases: format1-long-label and format2-currently-with-space Co-Authored-By: Claude Sonnet 4.6 --- CHANGELOG.md | 1 + pom.xml | 2 +- .../nbclaudecodegui/controller/ClaudeSessionController.java | 6 +++--- .../io/github/nbclaudecodegui/process/ModelMenuParser.java | 6 +++--- .../model-menu-parser/format1-long-label.expected.json | 1 + .../process/model-menu-parser/format1-long-label.src.txt | 3 +++ .../format2-currently-with-space.expected.json | 1 + .../model-menu-parser/format2-currently-with-space.src.txt | 3 +++ 8 files changed, 16 insertions(+), 7 deletions(-) create mode 100644 src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.expected.json create mode 100644 src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.src.txt create mode 100644 src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.expected.json create mode 100644 src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.src.txt diff --git a/CHANGELOG.md b/CHANGELOG.md index 4c6639e7..83c421e7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,4 @@ +- Fixed model name detection for new Claude CLI format where the default item has a long label ("Default (recommended)") with only 2-space alignment, and for model names that include a space (e.g. "Sonnet 4") - Fixed model combo not becoming active when a session starts with a blocking dialog (e.g. "Resuming session" prompt on --continue/--resume startup) - Improved keyboard navigation in choice menus: arrow keys, Tab, Shift+Tab - Added terminal font and font size settings (Tools → Options → Claude Code → General); defaults to auto-detection preferring Adwaita Mono for full Unicode coverage of Claude Code TUI symbols (https://github.com/nbclaudecodegui/NetbeansClaudeCodeGui/issues/18) diff --git a/pom.xml b/pom.xml index f70cc2c8..72996e5a 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ io.github.nbclaudecodegui netbeans-claude-code-gui - 0.22.32-SNAPSHOT + 0.22.33-SNAPSHOT nbm Netbeans Claude Code GUI NetBeans plugin that provides a GUI for Claude Code CLI — run claude code sessions directly inside the IDE. diff --git a/src/main/java/io/github/nbclaudecodegui/controller/ClaudeSessionController.java b/src/main/java/io/github/nbclaudecodegui/controller/ClaudeSessionController.java index d7397700..d504edbc 100644 --- a/src/main/java/io/github/nbclaudecodegui/controller/ClaudeSessionController.java +++ b/src/main/java/io/github/nbclaudecodegui/controller/ClaudeSessionController.java @@ -808,7 +808,7 @@ void discoverModels() { // Scan the rolling PTY line buffer for the /model hint line, which is // shorter and never truncated (e.g. "/model … (currently anthropic/claude-sonnet-4.6)"). String hintCurrentModel = null; - Pattern hintPat = Pattern.compile("\\(currently\\s+([\\w/.-]+)\\)"); + Pattern hintPat = Pattern.compile("\\(currently\\s+([^)]+?)\\s*\\)"); synchronized (recentPtyLines) { for (String ptyLine : recentPtyLines) { Matcher hm = hintPat.matcher(ptyLine); @@ -820,8 +820,8 @@ void discoverModels() { int selIdx; if (menuOpt.isPresent() && !menuOpt.get().options().isEmpty()) { List opts = menuOpt.get().options(); - Pattern descPat = Pattern.compile("(?:\u2714\\s+|\\s{3,})(.+?)(?:\\s*[·\u00b7].*)?$"); - Pattern currentlyPat = Pattern.compile("\\(currently\\s+([\\w/.-]+)\\)"); + Pattern descPat = Pattern.compile("(?:\u2714\\s+|\\s{2,})(.+?)(?:\\s*[·\u00b7].*)?$"); + Pattern currentlyPat = Pattern.compile("\\(currently\\s+([^)]+?)\\s*\\)"); models = new ArrayList<>(); selIdx = -1; for (int i = 0; i < opts.size(); i++) { diff --git a/src/main/java/io/github/nbclaudecodegui/process/ModelMenuParser.java b/src/main/java/io/github/nbclaudecodegui/process/ModelMenuParser.java index edf0a86f..d3518c9f 100644 --- a/src/main/java/io/github/nbclaudecodegui/process/ModelMenuParser.java +++ b/src/main/java/io/github/nbclaudecodegui/process/ModelMenuParser.java @@ -39,13 +39,13 @@ public class ModelMenuParser { */ public record ModelDiscovery(List models, int currentIndex) {} - /** Extracts the description part after ✔ or 3+ spaces. */ + /** Extracts the description part after ✔ or 2+ spaces. */ private static final Pattern DESC_PAT = - Pattern.compile("(?:\u2714\\s+|\\s{3,})(.+)$"); + Pattern.compile("(?:\u2714\\s+|\\s{2,})(.+)$"); /** Extracts the model id from "(currently X)" in description. */ private static final Pattern CURRENTLY_PAT = - Pattern.compile("\\(currently\\s+([\\w/.-]+)\\)"); + Pattern.compile("\\(currently\\s+([^)]+?)\\s*\\)"); /** Fallback: "Title Case Word N.M" at the tail of the left part. */ private static final Pattern VERSION_TAIL_PAT = diff --git a/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.expected.json b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.expected.json new file mode 100644 index 00000000..32a98888 --- /dev/null +++ b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.expected.json @@ -0,0 +1 @@ +{"models": ["Opus 4.7 with 1M context", "Sonnet 4.6", "Haiku 4.5"], "currentIndex": 2} diff --git a/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.src.txt b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.src.txt new file mode 100644 index 00000000..36d12e84 --- /dev/null +++ b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format1-long-label.src.txt @@ -0,0 +1,3 @@ + 1. Default (recommended) Opus 4.7 with 1M context · Most capable for complex work + 2. Sonnet Sonnet 4.6 · Best for everyday tasks + ❯ 3. Haiku ✔ Haiku 4.5 · Fastest for quick answers diff --git a/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.expected.json b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.expected.json new file mode 100644 index 00000000..c54e3b90 --- /dev/null +++ b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.expected.json @@ -0,0 +1 @@ +{"models": ["Sonnet 4", "Sonnet 4.6", "Haiku 4.5"], "currentIndex": 0} diff --git a/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.src.txt b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.src.txt new file mode 100644 index 00000000..1fc708aa --- /dev/null +++ b/src/test/resources/io/github/nbclaudecodegui/process/model-menu-parser/format2-currently-with-space.src.txt @@ -0,0 +1,3 @@ +❯ 1. Default (recommended) ✔ Use the default model (currently Sonnet 4) · $3/$15 per Mtok + 2. Sonnet Sonnet 4.6 · Best for everyday tasks + 3. Haiku Haiku 4.5 · Fastest for quick answers