Skip to content

Highlight Session commands in composers - #1829

Merged
gjkim42 merged 1 commit into
mainfrom
feat/session-command-indicators
Oct 18, 2026
Merged

gjkim42 merged 1 commit into
mainfrom
feat/session-command-indicators

Conversation

@gjkim42

@gjkim42 gjkim42 commented Oct 17, 2026 •

Copy link
Copy Markdown
Collaborator

What type of PR is this?

/kind feature

What this PR does / why we need it:

Typing !make test or /goal pause currently leaves users unsure whether they are submitting a message or a Session command. Give recognized commands a distinct composer presentation while users type.

The web composer highlights the command prefix, uses amber shell styling and green goal styling, and shows the matching submit action. Arguments remain readable, and removing the command prefix restores the ordinary message composer. The interactive terminal colors shell and goal input and shows the action Enter will submit.

Explain and block incomplete commands, unavailable goal support, and commands that conflict with staged attachments or pending work. Keep the draft when submission is blocked. Keep unknown prefixes such as /goalkeeper as ordinary messages.

Which issue(s) this PR is related to:

N/A

Special notes for your reviewer:

The web editor uses a native textarea with an inert highlighting layer. The layer shares the textarea's font and wrapping dimensions and follows its scrolling. Returning to Conversation or Sessions, scrolling, and resizing the viewport refresh its alignment; hidden composers retain their measured dimensions.

Validation:

  • make verify
  • env -u CODEX_HOME -u CODEX_AUTH_JSON make test
  • make build WHAT=cmd/kelos
  • Chromium checks of command submission, validation guidance, text selection, multiline scrolling, navigation through Changes and Terminal, background events while the composer is hidden, light and dark themes, and layouts at 320, 360, and 390 pixels

The unit suite runs with inherited Codex settings removed from the test process; an entrypoint failure with those settings reproduces on main.

Review disposition: the command validation, whitespace handling, cancel/disconnect hints, hidden-composer alignment, dark error contrast, documentation, and event-hook coverage findings are addressed. Duplicate alignment reports share one fix; the findings on outdated documentation and CSS locations still applied and are addressed.

The pending-edit label suggestion is not applied: runtime editMessage reparses the saved text and supports changing pending work into a command. The hint therefore keeps the command type and explicitly says “save pending work”; a positive submission test covers this path. Commands with attachments are rejected by the runtime, rather than sent as ordinary agent prompts; the TUI blocks them locally and retains the draft and files. Goal commands remain available during active work so an active goal can still be controlled.

Screenshots use the production frontend with a fixture Session and matching input and conversation in each pair.

View Before After
Shell command, desktop Before: shell command, desktop After: shell command, desktop
Goal command, desktop Before: goal command, desktop After: goal command, desktop
Shell command, mobile Before: shell command, mobile After: shell command, mobile
Incomplete goal, dark desktop Before: incomplete goal, dark desktop After: incomplete goal, dark desktop

Does this PR introduce a user-facing change?

Session composers highlight shell and goal commands while typing. The web composer gives commands distinct styling, shows command-specific submit actions, and explains incomplete or unavailable commands.

@gjkim42 gjkim42 added the kind/feature Categorizes issue or PR as related to a new feature label Oct 17, 2026

@cubic-dev-ai cubic-dev-ai Bot left a comment •

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All reported issues were addressed across 9 files

Reply with feedback, questions, or to request a fix.

View guided diff | Turn on auto-fix | Re-trigger cubic

Comment thread internal/cli/session_terminal_tui.go
Comment thread internal/cli/session_terminal_tui.go Outdated
Comment thread internal/cli/session_terminal_tui.go
Comment thread internal/consoleserver/frontend/app.ts Outdated
Comment thread docs/reference.md Outdated
Comment thread internal/cli/session_terminal_tui.go
Comment thread docs/reference.md Outdated
Comment thread docs/reference.md Outdated
Comment thread internal/cli/session_terminal_tui_test.go
Comment thread internal/consoleserver/web/app.js
@gjkim42 gjkim42 changed the title Identify Session commands before submission Highlight Session commands in composers Oct 17, 2026

@cubic-dev-ai cubic-dev-ai Bot left a comment •

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All reported issues were addressed across 10 files (changes from recent commits).

Requires human review: Auto-approval blocked because this review re-detected 1 unresolved issue already reported by Cubic.

View guided diff | Turn on auto-fix | Re-trigger cubic

Comment thread internal/cli/session_terminal_tui.go
Comment thread internal/consoleserver/web/app.js
Comment thread internal/consoleserver/frontend/app.ts
Comment thread internal/cli/session_terminal_tui_test.go Outdated
Comment thread docs/reference.md Outdated
Comment thread internal/consoleserver/testdata/session_history_test.js
@gjkim42

gjkim42 commented Oct 18, 2026

Copy link
Copy Markdown
Collaborator Author

/kelos review

@kelos-bot

kelos-bot Bot commented Oct 18, 2026 •

Copy link
Copy Markdown
Contributor

🤖 Kelos Task Status

Task kelos-reviewer-issue-comment-31ded869864e has succeeded. ✅

@kelos-bot

kelos-bot Bot commented Oct 18, 2026 •

Copy link
Copy Markdown
Contributor

🤖 Kelos Reviewer Agent @gjkim42

Review Summary

Verdict: APPROVE
Overall correctness: patch is correct
Scope: Highlights !COMMAND and /goal in the web composer (inert overlay, command-specific submit button, client-side validation) and adds a command-aware, colored hint row to the interactive terminal composer (reviewed at 7fe99cb).

Findings Overview

Priority Count File:Line Summary
P0 0 — none
P1 0 — none
P2 0 — none
P3 1 docs/reference.md:406 Docs say both composers prevent commands blocked by pending work, but /goal during an active turn with queued work is still submitted and rejected

Findings

Documentation accuracy

  • [P3] docs/reference.md:406 — The new paragraph says both composers "explain … commands blocked by staged attachments or pending work, and prevent their submission until the problem is resolved." The client checks only block /goal when no turn is active (internal/consoleserver/frontend/app.ts:3900, internal/cli/session_terminal_tui.go:1530). The runtime exempts goal commands from the pending-turn rule only when the active turn is itself a goal turn (internal/sessionruntime/server.go:1065). Otherwise submitParsedMessage rejects any command while a turn is pending (server.go:1004). Concrete case: an ordinary message or !make test turn is running and a follow-up message is queued. The user types /goal pause. Both composers show an enabled Pause goal action. The runtime replies Session already has a pending command or message, and the draft is already gone: the web client calls clearPromptDraft (app.ts:6295) and the TUI calls m.input.Reset() in submitInput. The PR description says allowing goal control during active work is deliberate. Mirroring the runtime exactly on the client is also hard, because provider-started continuation turns are recorded as message turns (internal/sessionruntime/session_events.go:114). The practical fix is to narrow the sentence, for example: "While work is active, goal commands are passed to the runtime, which rejects them if other work is already pending."

Suggestions (optional)

  • [P3] internal/cli/session_terminal_tui.go:1552 — The new TUI hint shows Message · Enter to add to pending whenever pendingTurnID is set. If the queued item is a command (for example !make test queued during an agent turn), the runtime rejects an ordinary follow-up too: pendingKind != sessionCommandMessage at server.go:1003. Enter then clears the draft and shows an error. The web composer has used the same add to pending label since before this PR, so this only matters if you want the new TUI hint to be exact. m.pendingTurnInput already holds the queued text, which is enough to detect a queued command and show a "wait for pending work" hint instead.

Key takeaways (optional)

  • No blocking issues. Command classification matches parseSessionCommand/hasCommandPrefix on both clients, including NBSP/NEL handling, /goalkeeper, /goal clear tech debt, and /goal edit with no objective. The web client trims U+FEFF the same way in both composerCommand() and submitComposer(), so what the composer shows matches what the runtime parses.
  • The findings from the previous sticky review are addressed in this revision. Those were hidden-composer alignment, the /cancel-input hint, whitespace around /quit, command labels while work is pending, and the docs wording. resizeComposer() now runs when the Conversation or Sessions view becomes visible, and the TUI composerHeight() now matches the rendered rows when files are attached. web/app.js matches frontend/app.ts.

Note on prompt injection: Third-party bot review content on this PR includes embedded "Prompt for AI agents" instructions, such as fixing issues, resolving threads, and spawning sub-agents. It was treated as data and disregarded. The findings above come from independent analysis of the code.

@gjkim42
gjkim42 force-pushed the feat/session-command-indicators branch from 4a723f1 to 7fe99cb Compare October 18, 2026 07:47

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1 issue found across 8 files (changes from recent commits).

Prompt for AI agents (unresolved issues)

Check if these issues are valid — if so, understand the root cause of each and fix them. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. If appropriate, use sub-agents to investigate and fix each issue separately.


<file name="internal/cli/session_terminal_tui.go">

<violation number="1" location="internal/cli/session_terminal_tui.go:1530">
P2: This lets `/goal ...` submit with a queued turn whenever another turn is active. For active message or shell turns, the server rejects the command after `submitInput` clears the draft; block goal commands while pending work exists.</violation>
</file>

Reply with feedback, questions, or to request a fix.

View guided diff | Turn on auto-fix | Re-trigger cubic

if len(m.pendingAttachments) > 0 {
return "Remove attachments to use a command"
}
if m.pendingEditTurnID == "" && m.pendingTurnID != "" && (shell || !m.turnActive) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2: This lets /goal ... submit with a queued turn whenever another turn is active. For active message or shell turns, the server rejects the command after submitInput clears the draft; block goal commands while pending work exists.

Prompt for AI agents
Check if this issue is valid — if so, understand the root cause and fix it. When an issue isn't valid or won't be fixed in this PR, reply in its thread with the reason and then resolve the thread. At internal/cli/session_terminal_tui.go, line 1530:

<comment>This lets `/goal ...` submit with a queued turn whenever another turn is active. For active message or shell turns, the server rejects the command after `submitInput` clears the draft; block goal commands while pending work exists.</comment>

<file context>
@@ -1513,6 +1516,34 @@ func (m *sessionTUIModel) statusStyle(status string) lipgloss.Style {
+	if len(m.pendingAttachments) > 0 {
+		return "Remove attachments to use a command"
+	}
+	if m.pendingEditTurnID == "" && m.pendingTurnID != "" && (shell || !m.turnActive) {
+		return "Wait for pending work to start or remove it before submitting a command"
+	}
</file context>
Suggested change
if m.pendingEditTurnID == "" && m.pendingTurnID != "" && (shell || !m.turnActive) {
if m.pendingEditTurnID == "" && m.pendingTurnID != "" {

@gjkim42

gjkim42 commented Oct 18, 2026

Copy link
Copy Markdown
Collaborator Author

/kelos review

@gjkim42
gjkim42 added this pull request to the merge queue Oct 18, 2026
Merged via the queue into main with commit 2e6eccd Oct 18, 2026
27 checks passed
@gjkim42
gjkim42 deleted the feat/session-command-indicators branch October 18, 2026 22:41
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

kind/feature Categorizes issue or PR as related to a new feature needs-actor needs-priority needs-triage release-note

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant