From 465d8b77a3782f85e2c45ea8a92d5fac3a0c4e93 Mon Sep 17 00:00:00 2001 From: Steve Yegge Date: Sun, 21 Dec 2025 23:19:08 -0800 Subject: [PATCH] Show mail subject preview inline in status bar MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Instead of just showing unread count, display truncated subject of first unread message directly in the status bar. More useful than click-to-view since terminal mouse support varies. - Mayor: 20 char limit for subject preview - Worker (crew/polecat): 25 char limit - Falls back to count if subject unavailable 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 --- internal/cmd/statusline.go | 45 +++++++++++++++++++++++++++++++++----- 1 file changed, 39 insertions(+), 6 deletions(-) diff --git a/internal/cmd/statusline.go b/internal/cmd/statusline.go index 21e35c7a..36ecf001 100644 --- a/internal/cmd/statusline.go +++ b/internal/cmd/statusline.go @@ -97,11 +97,15 @@ func runWorkerStatusLine(rigName, polecat, crew, issue string) error { parts = append(parts, issue) } - // Mail count + // Mail preview if identity != "" { - unread := getUnreadMailCount(identity) + unread, subject := getMailPreview(identity, 25) if unread > 0 { - parts = append(parts, fmt.Sprintf("\U0001F4EC %d", unread)) + if subject != "" { + parts = append(parts, fmt.Sprintf("\U0001F4EC %s", subject)) + } else { + parts = append(parts, fmt.Sprintf("\U0001F4EC %d", unread)) + } } } @@ -141,15 +145,19 @@ func runMayorStatusLine(t *tmux.Tmux) error { } rigCount := len(rigs) - // Get mayor mail - unread := getUnreadMailCount("mayor/") + // Get mayor mail with preview + unread, subject := getMailPreview("mayor/", 20) // Build status var parts []string parts = append(parts, fmt.Sprintf("%s %d polecats", AgentTypeIcons[AgentMayor], polecatCount)) parts = append(parts, fmt.Sprintf("%d rigs", rigCount)) if unread > 0 { - parts = append(parts, fmt.Sprintf("\U0001F4EC %d", unread)) + if subject != "" { + parts = append(parts, fmt.Sprintf("\U0001F4EC %s", subject)) + } else { + parts = append(parts, fmt.Sprintf("\U0001F4EC %d", unread)) + } } fmt.Print(strings.Join(parts, " | ") + " |") @@ -320,3 +328,28 @@ func getUnreadMailCount(identity string) int { return unread } + +// getMailPreview returns unread count and a truncated subject of the first unread message. +// Returns (count, subject) where subject is empty if no unread mail. +func getMailPreview(identity string, maxLen int) (int, string) { + workDir, err := findMailWorkDir() + if err != nil { + return 0, "" + } + + mailbox := mail.NewMailboxBeads(identity, workDir) + + // Get unread messages + messages, err := mailbox.ListUnread() + if err != nil || len(messages) == 0 { + return 0, "" + } + + // Get first message subject, truncated + subject := messages[0].Subject + if len(subject) > maxLen { + subject = subject[:maxLen-1] + "…" + } + + return len(messages), subject +}