Extension API: status bar / HUD primitive for always-on context surfaces
Problem
Building an "always-on" surface (think Claude Code's statusline / claude-hud:
agent token usage, rolling session/week totals, context-window %) from a Zed
extension today is not possible without user interaction. zed_extension_api
0.7 exposes slash commands, language servers, themes, and context servers,
but no persistent UI primitive an extension can write to.
Concretely, what an extension can do today:
- Register slash commands that render markdown into the Assistant panel.
- Shell out via
process:exec to produce filesystem artifacts.
- Provide LSP / context servers.
What an extension cannot do:
- Render into the status bar.
- Pin a panel / dock entry that updates on a timer.
- Subscribe to "worktree opened" / "extension loaded" lifecycle events with a
worktree handle (the only verified entry point that receives a worktree is
a slash-command callback).
This blocks every "ambient information" extension class:
- Agent usage HUDs (claude-hud / codex usage)
- Build / test status badges
- Token-budget warnings
- Repository context briefs (the use case I am hitting right now in
https://github.com/htahaozlu/zed-context)
Proposal
A minimal status-bar extension surface, e.g.:
[status_bar.context_hud]
description = "Agent token HUD"
position = "right" # left | right
refresh_seconds = 30 # extension is polled / called on a timer
And a corresponding extension callback:
fn render_status_item(
&self,
item: zed::StatusBarItem,
worktree: Option<&zed::Worktree>,
) -> Result<zed::StatusBarOutput>;
with StatusBarOutput carrying short text + optional tooltip + optional
on-click slash command. This is intentionally narrower than a full panel API
and avoids exposing layout primitives, while unblocking the entire ambient
HUD extension class.
Workarounds today
In zed-context we currently:
- Write
.zed-context/hud.md on every slash-command interaction.
- Ask the user to keep that buffer open in a pinned tab.
This is not "always on" in any real sense — the user has to remember to open
the file, the buffer does not auto-refresh on focus, and there is no surface
that survives across worktrees. A small status-bar primitive would make the
whole pattern viable.
Prior art
- VS Code:
vscode.window.createStatusBarItem(...)
- JetBrains: status-bar widget extension points
- Claude Code: external statusline scripts
Extension API: status bar / HUD primitive for always-on context surfaces
Problem
Building an "always-on" surface (think Claude Code's statusline / claude-hud:
agent token usage, rolling session/week totals, context-window %) from a Zed
extension today is not possible without user interaction.
zed_extension_api0.7 exposes slash commands, language servers, themes, and context servers,
but no persistent UI primitive an extension can write to.
Concretely, what an extension can do today:
process:execto produce filesystem artifacts.What an extension cannot do:
worktree handle (the only verified entry point that receives a worktree is
a slash-command callback).
This blocks every "ambient information" extension class:
https://github.com/htahaozlu/zed-context)
Proposal
A minimal status-bar extension surface, e.g.:
And a corresponding extension callback:
with
StatusBarOutputcarrying short text + optional tooltip + optionalon-click slash command. This is intentionally narrower than a full panel API
and avoids exposing layout primitives, while unblocking the entire ambient
HUD extension class.
Workarounds today
In
zed-contextwe currently:.zed-context/hud.mdon every slash-command interaction.This is not "always on" in any real sense — the user has to remember to open
the file, the buffer does not auto-refresh on focus, and there is no surface
that survives across worktrees. A small status-bar primitive would make the
whole pattern viable.
Prior art
vscode.window.createStatusBarItem(...)