pub struct App {
pub metrics: MetricsSnapshot,
pub should_quit: bool,
pub subagent_sidebar: SubAgentSidebarState,
/* private fields */
}Expand description
Central state machine for the TUI dashboard.
App owns all widget state, the render cache, the message history, and
the event channel endpoints. The main loop in crate::run_tui calls
draw once per frame and routes events through
handle_event and
handle_agent_event.
§Construction
use tokio::sync::mpsc;
use zeph_tui::App;
let (user_tx, _user_rx) = mpsc::channel(64);
let (_agent_tx, agent_rx) = mpsc::channel(64);
let app = App::new(user_tx, agent_rx);Use the builder methods to wire optional components:
with_metrics_rx— live metrics watch channel.with_cancel_signal— Ctrl-C cancel notify.with_command_tx— slash-command dispatch channel.
Fields§
§metrics: MetricsSnapshot§should_quit: boolInteractive selection state for the subagent sidebar (stays global per arch v2 E5).
Implementations§
Source§impl App
impl App
Sourcepub fn handle_event(&mut self, event: AppEvent)
pub fn handle_event(&mut self, event: AppEvent)
Dispatch a top-level AppEvent to the appropriate handler.
Called once per event in the main crate::run_tui loop.
Sourcepub fn poll_agent_event(
&mut self,
) -> impl Future<Output = Option<AgentEvent>> + use<'_>
pub fn poll_agent_event( &mut self, ) -> impl Future<Output = Option<AgentEvent>> + use<'_>
Await the next AgentEvent from the agent channel.
Returns None when all senders have been dropped (agent exited).
Called from the select! block in crate::run_tui.
Sourcepub fn try_recv_agent_event(&mut self) -> Result<AgentEvent, TryRecvError>
pub fn try_recv_agent_event(&mut self) -> Result<AgentEvent, TryRecvError>
Non-blocking poll for a pending AgentEvent.
Used to drain the channel after a first event has been received, coalescing multiple events into a single render frame.
§Errors
Returns TryRecvError::Empty if no events are pending, or
TryRecvError::Disconnected if the sender has been dropped.
Sourcepub fn handle_agent_event(&mut self, event: AgentEvent)
pub fn handle_agent_event(&mut self, event: AgentEvent)
Handle an AgentEvent and update widget state accordingly.
This is the main state-transition function for agent-driven updates: appending streaming chunks, recording tool events, displaying confirm dialogs, and wiring late-bound channels (cancel signal, metrics).
pub fn confirm_state(&self) -> Option<&ConfirmState>
Source§impl App
impl App
Sourcepub fn has_recent_security_events(&self) -> bool
pub fn has_recent_security_events(&self) -> bool
Returns true if there are security events within the last 60 seconds.
Sourcepub fn poll_pending_file_index(&mut self)
pub fn poll_pending_file_index(&mut self)
Checks if the background file index build has completed and, if so, installs the result and opens the picker.
Source§impl App
impl App
Sourcepub fn new(
user_input_tx: Sender<String>,
agent_event_rx: Receiver<AgentEvent>,
) -> Self
pub fn new( user_input_tx: Sender<String>, agent_event_rx: Receiver<AgentEvent>, ) -> Self
Create a new App with the given I/O channels.
The app starts in insert mode with the splash screen visible and no messages in the buffer.
§Arguments
user_input_tx— sender used to forward the user’s typed text to the agent loop viaTuiChannel.agent_event_rx— receiver forAgentEventproduced by the agent.
§Examples
use tokio::sync::mpsc;
use zeph_tui::App;
let (user_tx, _user_rx) = mpsc::channel(64);
let (_agent_tx, agent_rx) = mpsc::channel(64);
let app = App::new(user_tx, agent_rx);
assert!(app.show_splash());Sourcepub fn show_splash(&self) -> bool
pub fn show_splash(&self) -> bool
Return true while the splash screen should be displayed.
The splash screen is hidden as soon as the first chat message arrives.
Sourcepub fn show_side_panels(&self) -> bool
pub fn show_side_panels(&self) -> bool
Return true when the side panels column is visible.
Controlled by the s keybinding and automatically disabled on narrow
terminals (< 80 columns).
Sourcepub fn plan_view_active(&self) -> bool
pub fn plan_view_active(&self) -> bool
Returns true when the user has toggled back to subagents view (plan view overridden).
Sourcepub fn render_cache(&self) -> &RenderCache
pub fn render_cache(&self) -> &RenderCache
Returns the active session’s render cache.
Sourcepub fn render_cache_mut(&mut self) -> &mut RenderCache
pub fn render_cache_mut(&mut self) -> &mut RenderCache
Returns a mutable reference to the active session’s render cache.
Sourcepub fn view_target(&self) -> &AgentViewTarget
pub fn view_target(&self) -> &AgentViewTarget
Returns the current chat area view target (main conversation or sub-agent transcript).
Sourcepub fn transcript_cache(&self) -> Option<&TranscriptCache>
pub fn transcript_cache(&self) -> Option<&TranscriptCache>
Returns the cached transcript for the currently-focused sub-agent, if any.
Sourcepub fn load_history(&mut self, messages: &[(&str, &str)])
pub fn load_history(&mut self, messages: &[(&str, &str)])
Populate the message buffer from a persisted session history.
Each element is a (role, content) pair where role is one of
"user", "assistant", or "tool". Tool outputs are detected by a
sentinel suffix and rendered as MessageRole::Tool messages.
The splash screen is hidden after loading if any messages are present.
Sourcepub fn with_cancel_signal(self, signal: Arc<Notify>) -> Self
pub fn with_cancel_signal(self, signal: Arc<Notify>) -> Self
Attach a cancel signal that Ctrl-C in the TUI will trigger.
§Examples
use std::sync::Arc;
use tokio::sync::{Notify, mpsc};
use zeph_tui::App;
let (tx, _rx) = mpsc::channel(1);
let (_atx, arx) = mpsc::channel(1);
let notify = Arc::new(Notify::new());
let _app = App::new(tx, arx).with_cancel_signal(notify);Sourcepub fn with_metrics_rx(self, rx: Receiver<MetricsSnapshot>) -> Self
pub fn with_metrics_rx(self, rx: Receiver<MetricsSnapshot>) -> Self
Attach a metrics watch channel for live dashboard updates.
The current snapshot is read immediately; subsequent updates are polled
by poll_metrics each frame.
§Examples
use tokio::sync::{mpsc, watch};
use zeph_tui::{App, MetricsSnapshot};
let (tx, _rx) = mpsc::channel(1);
let (_atx, arx) = mpsc::channel(1);
let (_metrics_tx, metrics_rx) = watch::channel(MetricsSnapshot::default());
let _app = App::new(tx, arx).with_metrics_rx(metrics_rx);Sourcepub fn with_command_tx(self, tx: Sender<TuiCommand>) -> Self
pub fn with_command_tx(self, tx: Sender<TuiCommand>) -> Self
Attach the command dispatch sender used for slash-command routing.
§Examples
use tokio::sync::mpsc;
use zeph_tui::{App, TuiCommand};
let (tx, _rx) = mpsc::channel(1);
let (_atx, arx) = mpsc::channel(1);
let (cmd_tx, _cmd_rx) = mpsc::channel(8);
let _app = App::new(tx, arx).with_command_tx(cmd_tx);Sourcepub fn with_task_supervisor(self, supervisor: TaskSupervisor) -> Self
pub fn with_task_supervisor(self, supervisor: TaskSupervisor) -> Self
Wire a TaskSupervisor into the App for the task registry panel.
The supervisor’s task list is snapshotted once per render tick before
terminal.draw(), keeping the draw closure free of mutex contention.
Toggle the panel visibility with /tasks.
§Examples
use tokio::sync::mpsc;
use tokio_util::sync::CancellationToken;
use zeph_common::task_supervisor::TaskSupervisor;
use zeph_tui::App;
let (user_tx, _) = mpsc::channel(64);
let (_, agent_rx) = mpsc::channel(64);
let cancel = CancellationToken::new();
let supervisor = TaskSupervisor::new(cancel);
let _app = App::new(user_tx, agent_rx).with_task_supervisor(supervisor);Sourcepub fn supervisor_activity_label(&self) -> Option<String>
pub fn supervisor_activity_label(&self) -> Option<String>
Return a truncated label for active TaskSupervisor tasks, or None when idle.
Used by crate::widgets::chat::render_activity to show a braille spinner with
the name of the first active (Running/Restarting) task when no other status
is being displayed.
Sourcepub fn set_cancel_signal(&mut self, signal: Arc<Notify>)
pub fn set_cancel_signal(&mut self, signal: Arc<Notify>)
Wire a cancel signal into a running App instance.
Used by the two-phase TUI startup path to connect the agent’s cancel signal after the agent has been constructed (Phase 2).
Sourcepub fn set_metrics_rx(&mut self, rx: Receiver<MetricsSnapshot>)
pub fn set_metrics_rx(&mut self, rx: Receiver<MetricsSnapshot>)
Wire a metrics receiver into a running App instance.
Used by the two-phase TUI startup path to connect the metrics channel after the metrics watch channel has been created (Phase 2).
Sourcepub fn poll_metrics(&mut self)
pub fn poll_metrics(&mut self)
Check the metrics watch channel for an updated snapshot and apply it.
Also clamps the sidebar selection and triggers a transcript reload if the sub-agent’s turn count has advanced. Called once per render frame.
Sourcepub fn set_view_target(&mut self, target: AgentViewTarget)
pub fn set_view_target(&mut self, target: AgentViewTarget)
Switch the chat view target. Clears render cache and scroll offset. All view changes MUST go through this method (W5).
Sourcepub fn poll_pending_transcript(&mut self)
pub fn poll_pending_transcript(&mut self)
Poll the pending transcript load and install result if ready.
Sourcepub fn visible_messages(&self) -> Vec<ChatMessage>
pub fn visible_messages(&self) -> Vec<ChatMessage>
Returns the messages to display in the chat area.
Always returns an owned Vec — the cost is one clone of at most
MAX_TUI_MESSAGES (2000) ref-counted strings inside ChatMessage.
When viewing a subagent, returns transcript entries converted to ChatMessage.
When no transcript is loaded yet, returns a loading placeholder.
Sourcepub fn transcript_truncation_info(&self) -> Option<String>
pub fn transcript_truncation_info(&self) -> Option<String>
Returns the truncation info string if the transcript was truncated.
Sourcepub fn messages(&self) -> &[ChatMessage]
pub fn messages(&self) -> &[ChatMessage]
Return a slice of all chat messages currently in the buffer.
For the currently-displayed messages (which may be a sub-agent
transcript) use visible_messages instead.
Sourcepub fn input_mode(&self) -> InputMode
pub fn input_mode(&self) -> InputMode
Return the current input mode (normal vs. insert).
Sourcepub fn cursor_position(&self) -> usize
pub fn cursor_position(&self) -> usize
Return the cursor byte position within the input string.
Sourcepub fn scroll_offset(&self) -> usize
pub fn scroll_offset(&self) -> usize
Return the number of lines the chat view is scrolled up from the bottom.
0 means the view is at the bottom (latest messages visible).
Sourcepub fn tool_expanded(&self) -> bool
pub fn tool_expanded(&self) -> bool
Return true when tool-output blocks are expanded to full height.
Sourcepub fn paste_state(&self) -> Option<&PasteState>
pub fn paste_state(&self) -> Option<&PasteState>
Return the active paste indicator state, if any.
Some when a multiline paste is in the input buffer and no edit
keypress has occurred since the paste. None otherwise.
Sourcepub fn compact_tools(&self) -> bool
pub fn compact_tools(&self) -> bool
Return true when tool blocks use compact single-line rendering.
Sourcepub fn show_source_labels(&self) -> bool
pub fn show_source_labels(&self) -> bool
Return true when source-label badges are shown on assistant messages.
Sourcepub fn set_show_source_labels(&mut self, v: bool)
pub fn set_show_source_labels(&mut self, v: bool)
Toggle source-label visibility.
Clears the render cache so all messages are re-rendered with the new setting on the next frame.
Sourcepub fn set_hyperlinks(&mut self, links: Vec<HyperlinkSpan>)
pub fn set_hyperlinks(&mut self, links: Vec<HyperlinkSpan>)
Replace the current hyperlink span list with links.
Called by the render loop after each frame to store spans detected in the terminal buffer so they can be emitted as OSC 8 sequences.
Sourcepub fn take_hyperlinks(&mut self) -> Vec<HyperlinkSpan>
pub fn take_hyperlinks(&mut self) -> Vec<HyperlinkSpan>
Take ownership of the accumulated hyperlink spans, clearing the list.
Called once per frame; the caller writes OSC 8 sequences to the terminal.
Sourcepub fn status_label(&self) -> Option<&str>
pub fn status_label(&self) -> Option<&str>
Return the current activity status label, if any.
Displayed in the activity bar with a spinner when non-None
(e.g. "Searching memory…", "Executing tool: bash").
Sourcepub fn queued_count(&self) -> usize
pub fn queued_count(&self) -> usize
Return the number of messages queued or pending for the agent.
Displayed in the input bar to indicate backpressure.
Sourcepub fn editing_queued(&self) -> bool
pub fn editing_queued(&self) -> bool
Return true when the user is currently editing a queued message.
Sourcepub fn is_agent_busy(&self) -> bool
pub fn is_agent_busy(&self) -> bool
Return true when the agent is actively processing (streaming or running a tool).
Used by the render loop to decide whether to show the activity spinner.
Sourcepub fn has_running_tool(&self) -> bool
pub fn has_running_tool(&self) -> bool
Return true when the last message is a streaming tool output.
Sourcepub fn throbber_state(&self) -> &ThrobberState
pub fn throbber_state(&self) -> &ThrobberState
Return a reference to the throbber animation state.
Used by the status widget to render the spinner frame.
Sourcepub fn throbber_state_mut(&mut self) -> &mut ThrobberState
pub fn throbber_state_mut(&mut self) -> &mut ThrobberState
Return a mutable reference to the throbber animation state.
Called by the tick handler to advance the spinner frame each tick.
Auto Trait Implementations§
impl Freeze for App
impl !RefUnwindSafe for App
impl Send for App
impl Sync for App
impl Unpin for App
impl UnsafeUnpin for App
impl !UnwindSafe for App
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<T> IntoRequest<T> for T
impl<T> IntoRequest<T> for T
Source§fn into_request(self) -> Request<T>
fn into_request(self) -> Request<T>
T in a tonic::Request