feat: display ConfigChange hook events in terminal

Detects [ConfigChange Hook] lines in stderr and emits them as
config-change line type with [config] prefix in purple.

Closes #151
This commit is contained in:
2026-02-24 18:07:53 -08:00
committed by Naomi Carrigan
parent 54280b3920
commit 5063a4f415
5 changed files with 37 additions and 11 deletions
+11 -8
View File
@@ -761,18 +761,21 @@ fn handle_stderr(
}
}
// Worktree hook events are informational — emit with a distinct type
let is_worktree_event = line.contains("[WorktreeCreate Hook]")
|| line.contains("[WorktreeRemove Hook]");
// Hook events are informational — emit with distinct types instead of error
let line_type = if line.contains("[WorktreeCreate Hook]")
|| line.contains("[WorktreeRemove Hook]")
{
"worktree"
} else if line.contains("[ConfigChange Hook]") {
"config-change"
} else {
"error"
};
let _ = app.emit(
"claude:output",
OutputEvent {
line_type: if is_worktree_event {
"worktree".to_string()
} else {
"error".to_string()
},
line_type: line_type.to_string(),
content: line,
tool_name: None,
conversation_id: conversation_id.clone(),
+8
View File
@@ -100,6 +100,8 @@
return "terminal-compact-prompt";
case "worktree":
return "terminal-worktree";
case "config-change":
return "terminal-config-change";
default:
return "terminal-default";
}
@@ -121,6 +123,8 @@
return "[rate-limit]";
case "worktree":
return "[worktree]";
case "config-change":
return "[config]";
default:
return "";
}
@@ -394,6 +398,10 @@
color: var(--terminal-worktree, #34d399);
}
.terminal-config-change {
color: var(--terminal-config-change, #a78bfa);
}
.compact-action-btn {
display: inline-flex;
align-items: center;
+12
View File
@@ -42,6 +42,8 @@ function getLineClass(type: string): string {
return "terminal-compact-prompt";
case "worktree":
return "terminal-worktree";
case "config-change":
return "terminal-config-change";
default:
return "terminal-default";
}
@@ -63,6 +65,8 @@ function getLinePrefix(type: string): string {
return "[rate-limit]";
case "worktree":
return "[worktree]";
case "config-change":
return "[config]";
default:
return "";
}
@@ -124,6 +128,10 @@ describe("getLineClass", () => {
expect(getLineClass("worktree")).toBe("terminal-worktree");
});
it("returns terminal-config-change for config-change lines", () => {
expect(getLineClass("config-change")).toBe("terminal-config-change");
});
it("returns terminal-default for unknown line types", () => {
expect(getLineClass("unknown")).toBe("terminal-default");
expect(getLineClass("")).toBe("terminal-default");
@@ -164,6 +172,10 @@ describe("getLinePrefix", () => {
expect(getLinePrefix("worktree")).toBe("[worktree]");
});
it("returns [config] for config-change lines", () => {
expect(getLinePrefix("config-change")).toBe("[config]");
});
it("returns empty string for thinking lines (no prefix)", () => {
expect(getLinePrefix("thinking")).toBe("");
});
+4 -2
View File
@@ -332,7 +332,8 @@ export async function initializeTauriListeners() {
| "thinking"
| "rate-limit"
| "compact-prompt"
| "worktree",
| "worktree"
| "config-change",
content,
tool_name || undefined,
costData,
@@ -350,7 +351,8 @@ export async function initializeTauriListeners() {
| "thinking"
| "rate-limit"
| "compact-prompt"
| "worktree",
| "worktree"
| "config-change",
content,
tool_name || undefined,
costData,
+2 -1
View File
@@ -9,7 +9,8 @@ export interface TerminalLine {
| "thinking"
| "rate-limit"
| "compact-prompt"
| "worktree";
| "worktree"
| "config-change";
content: string;
timestamp: Date;
toolName?: string;