From a9dcf2b6e606f52829a5aa9510f4bfe447be88b9 Mon Sep 17 00:00:00 2001 From: Hunter Bown Date: Tue, 5 May 2026 01:57:25 -0500 Subject: [PATCH] style: cargo fmt sweep across community PRs MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 47 fmt drifts had accumulated from the squash-merged community PRs on this branch (#653, #654, #655, #645, #658, #668, #659, #661, #660, #667, #656). Pure formatting — no behavioural changes — applied via `cargo fmt --all` to satisfy CI's `cargo fmt --all -- --check` gate. Co-Authored-By: Claude Opus 4.7 (1M context) --- crates/execpolicy/src/bash_arity.rs | 8 +-- crates/tui/src/client.rs | 58 ++++++++++----------- crates/tui/src/commands/skills.rs | 10 +--- crates/tui/src/core/engine.rs | 28 +++++----- crates/tui/src/execpolicy/rules.rs | 1 - crates/tui/src/sandbox/opensandbox.rs | 23 ++------ crates/tui/src/skills/install.rs | 9 ++-- crates/tui/src/tools/fim.rs | 11 +--- crates/tui/src/tools/large_output_router.rs | 3 +- crates/tui/src/tools/mod.rs | 2 +- crates/tui/src/tools/registry.rs | 11 +--- crates/tui/src/tools/shell.rs | 4 +- crates/tui/src/tools/spec.rs | 8 ++- crates/tui/src/tools/subagent/mod.rs | 5 +- crates/tui/src/tui/app.rs | 38 +++++--------- crates/tui/src/tui/plan_prompt.rs | 19 ++++--- crates/tui/src/tui/sidebar.rs | 6 +-- crates/tui/src/tui/user_input.rs | 19 ++++--- crates/tui/src/tui/widgets/mod.rs | 7 +-- 19 files changed, 109 insertions(+), 161 deletions(-) diff --git a/crates/execpolicy/src/bash_arity.rs b/crates/execpolicy/src/bash_arity.rs index 225a75cc..0902dca1 100644 --- a/crates/execpolicy/src/bash_arity.rs +++ b/crates/execpolicy/src/bash_arity.rs @@ -363,13 +363,15 @@ impl BashArityDict { // (preserves backward compatibility with exact-match allow rules). let command_lower = command.trim().to_ascii_lowercase(); // Normalise whitespace in both sides before comparing. - let pattern_norm: String = pattern_lower.split_whitespace().collect::>().join(" "); + let pattern_norm: String = pattern_lower + .split_whitespace() + .collect::>() + .join(" "); let command_norm: String = command_lower .split_whitespace() .collect::>() .join(" "); - command_norm == pattern_norm - || command_norm.starts_with(&format!("{pattern_norm} ")) + command_norm == pattern_norm || command_norm.starts_with(&format!("{pattern_norm} ")) } /// Iterate over all entries in the dictionary. diff --git a/crates/tui/src/client.rs b/crates/tui/src/client.rs index c60b6abe..eba6a459 100644 --- a/crates/tui/src/client.rs +++ b/crates/tui/src/client.rs @@ -954,35 +954,35 @@ impl DeepSeekClient { /// /// Returns the generated text (the "middle" between `prompt` and `suffix`). pub async fn fim_completion( - &self, - model: &str, - prompt: &str, - suffix: &str, - max_tokens: u32, -) -> anyhow::Result { - let url = api_url(&self.base_url, "beta/completions"); - let body = json!({ - "model": model, - "prompt": prompt, - "suffix": suffix, - "max_tokens": max_tokens, - }); - let response = self - .send_with_retry(|| self.http_client.post(&url).json(&body)) - .await?; - let status = response.status(); - if !status.is_success() { - let error_text = bounded_error_text(response, ERROR_BODY_MAX_BYTES).await; - anyhow::bail!("FIM API error: HTTP {status}: {error_text}"); - } - let response_text = response.text().await.unwrap_or_default(); - let value: serde_json::Value = - serde_json::from_str(&response_text).context("Failed to parse FIM API response")?; - let text = value - .pointer("/choices/0/text") - .and_then(serde_json::Value::as_str) - .ok_or_else(|| anyhow::anyhow!("FIM response missing choices[0].text"))?; - Ok(text.to_string()) + &self, + model: &str, + prompt: &str, + suffix: &str, + max_tokens: u32, + ) -> anyhow::Result { + let url = api_url(&self.base_url, "beta/completions"); + let body = json!({ + "model": model, + "prompt": prompt, + "suffix": suffix, + "max_tokens": max_tokens, + }); + let response = self + .send_with_retry(|| self.http_client.post(&url).json(&body)) + .await?; + let status = response.status(); + if !status.is_success() { + let error_text = bounded_error_text(response, ERROR_BODY_MAX_BYTES).await; + anyhow::bail!("FIM API error: HTTP {status}: {error_text}"); + } + let response_text = response.text().await.unwrap_or_default(); + let value: serde_json::Value = + serde_json::from_str(&response_text).context("Failed to parse FIM API response")?; + let text = value + .pointer("/choices/0/text") + .and_then(serde_json::Value::as_str) + .ok_or_else(|| anyhow::anyhow!("FIM response missing choices[0].text"))?; + Ok(text.to_string()) } } diff --git a/crates/tui/src/commands/skills.rs b/crates/tui/src/commands/skills.rs index 638be45d..1d0f0227 100644 --- a/crates/tui/src/commands/skills.rs +++ b/crates/tui/src/commands/skills.rs @@ -317,9 +317,7 @@ fn sync_skills(app: &mut App) -> CommandResult { }); match result { - Ok(SyncResult::RegistryDenied(host)) => { - CommandResult::error(network_denied_message(&host)) - } + Ok(SyncResult::RegistryDenied(host)) => CommandResult::error(network_denied_message(&host)), Ok(SyncResult::RegistryNeedsApproval(host)) => { CommandResult::error(needs_approval_message(&host)) } @@ -334,11 +332,7 @@ fn sync_skills(app: &mut App) -> CommandResult { match outcome { SkillSyncOutcome::Downloaded { name, path } => { downloaded += 1; - let _ = writeln!( - out, - " [+] {name} — downloaded to {}", - path.display() - ); + let _ = writeln!(out, " [+] {name} — downloaded to {}", path.display()); } SkillSyncOutcome::Fresh { name } => { fresh += 1; diff --git a/crates/tui/src/core/engine.rs b/crates/tui/src/core/engine.rs index 02f04e70..071a1f4b 100644 --- a/crates/tui/src/core/engine.rs +++ b/crates/tui/src/core/engine.rs @@ -318,7 +318,9 @@ pub struct Engine { /// Session-scoped workshop variable store (#548). Shared across all tool /// calls so `last_tool_result` persists within the session and can be /// promoted to the parent context via `promote_to_context`. - workshop_vars: Option>>, + workshop_vars: Option< + std::sync::Arc>, + >, /// External sandbox backend (#516). When `Some`, exec_shell routes commands /// through this instead of spawning a local process. sandbox_backend: Option>, @@ -441,14 +443,17 @@ impl Engine { // Workshop variable store (#548). Created unconditionally so the Arc // can be handed to every ToolContext; routing is gated on the router // field being Some rather than on the vars Arc being present. - let workshop_vars: Option>> = - if config.workshop.is_some() { - Some(std::sync::Arc::new(tokio::sync::Mutex::new( - crate::tools::large_output_router::WorkshopVariables::default(), - ))) - } else { - None - }; + let workshop_vars: Option< + std::sync::Arc< + tokio::sync::Mutex, + >, + > = if config.workshop.is_some() { + Some(std::sync::Arc::new(tokio::sync::Mutex::new( + crate::tools::large_output_router::WorkshopVariables::default(), + ))) + } else { + None + }; // External sandbox backend (#516). Logged but non-fatal: if the // backend fails to construct, the engine continues with local @@ -1333,9 +1338,8 @@ impl Engine { // routing of the synthesis call itself. if let Some(workshop_cfg) = self.config.workshop.as_ref() { if let Some(vars_arc) = self.workshop_vars.as_ref() { - let router = crate::tools::large_output_router::LargeOutputRouter::new( - workshop_cfg.clone(), - ); + let router = + crate::tools::large_output_router::LargeOutputRouter::new(workshop_cfg.clone()); ctx = ctx.with_large_output_router(router, vars_arc.clone()); } } diff --git a/crates/tui/src/execpolicy/rules.rs b/crates/tui/src/execpolicy/rules.rs index 0ec367c8..9e36e545 100644 --- a/crates/tui/src/execpolicy/rules.rs +++ b/crates/tui/src/execpolicy/rules.rs @@ -30,7 +30,6 @@ pub struct RuleSet { pub deny: Vec, } - impl ExecPolicyConfig { pub fn from_str(contents: &str) -> Result { toml::from_str(contents).context("failed to parse execpolicy.toml") diff --git a/crates/tui/src/sandbox/opensandbox.rs b/crates/tui/src/sandbox/opensandbox.rs index d7cf600f..b2ffa4c3 100644 --- a/crates/tui/src/sandbox/opensandbox.rs +++ b/crates/tui/src/sandbox/opensandbox.rs @@ -53,11 +53,7 @@ impl OpenSandboxBackend { /// `"http://localhost:8080"`). `api_key` is optional and sent as /// `Authorization: Bearer ` when set. `timeout_secs` controls the /// HTTP request timeout. - pub fn new( - base_url: String, - api_key: Option, - timeout_secs: u64, - ) -> Result { + pub fn new(base_url: String, api_key: Option, timeout_secs: u64) -> Result { let client = reqwest::Client::builder() .timeout(Duration::from_secs(timeout_secs)) .build() @@ -79,20 +75,13 @@ impl OpenSandboxBackend { #[async_trait] impl SandboxBackend for OpenSandboxBackend { - async fn exec( - &self, - cmd: &str, - env: &HashMap, - ) -> Result { + async fn exec(&self, cmd: &str, env: &HashMap) -> Result { let request_body = SandboxRunRequest { cmd: cmd.to_string(), env: env.clone(), }; - let mut req = self - .client - .post(self.run_url()) - .json(&request_body); + let mut req = self.client.post(self.run_url()).json(&request_body); if let Some(ref api_key) = self.api_key { req = req.bearer_auth(api_key); @@ -106,11 +95,7 @@ impl SandboxBackend for OpenSandboxBackend { let status = response.status(); if !status.is_success() { let body = response.text().await.unwrap_or_default(); - anyhow::bail!( - "OpenSandbox returned HTTP {}: {}", - status.as_u16(), - body - ); + anyhow::bail!("OpenSandbox returned HTTP {}: {}", status.as_u16(), body); } let parsed: SandboxRunResponse = response diff --git a/crates/tui/src/skills/install.rs b/crates/tui/src/skills/install.rs index dc0879a4..225cd471 100644 --- a/crates/tui/src/skills/install.rs +++ b/crates/tui/src/skills/install.rs @@ -604,9 +604,7 @@ async fn sync_one_skill( if matches!(source, InstallSource::Registry(_)) { return SkillSyncOutcome::Failed { name: name.to_string(), - reason: format!( - "registry entry for '{name}' must not point to another registry entry" - ), + reason: format!("registry entry for '{name}' must not point to another registry entry"), }; } @@ -741,9 +739,8 @@ async fn sync_one_skill( // Determine whether this is a tarball or a plain SKILL.md. // Heuristic: the URL ends with `.tar.gz` or `.tgz`, or the content // starts with the gzip magic bytes (0x1f 0x8b). - let is_tarball = url.ends_with(".tar.gz") - || url.ends_with(".tgz") - || bytes.starts_with(&[0x1f, 0x8b]); + let is_tarball = + url.ends_with(".tar.gz") || url.ends_with(".tgz") || bytes.starts_with(&[0x1f, 0x8b]); let final_path: PathBuf; diff --git a/crates/tui/src/tools/fim.rs b/crates/tui/src/tools/fim.rs index b375a508..c2ef5bef 100644 --- a/crates/tui/src/tools/fim.rs +++ b/crates/tui/src/tools/fim.rs @@ -163,11 +163,7 @@ impl ToolSpec for FimEditTool { let generated_len = generated_text.len(); let new_content = format!("{}{}{}", fim_prompt, generated_text, fim_suffix); fs::write(&resolved, &new_content).map_err(|e| { - ToolError::execution_failed(format!( - "Failed to write {}: {}", - resolved.display(), - e - )) + ToolError::execution_failed(format!("Failed to write {}: {}", resolved.display(), e)) })?; let result = FimEditResult { @@ -178,10 +174,7 @@ impl ToolSpec for FimEditTool { suffix_start, message: format!( "FIM edit applied to `{}`. Generated {} chars between prefix_anchor end (byte {}) and suffix_anchor start (byte {}).", - path, - generated_len, - prefix_end, - suffix_start, + path, generated_len, prefix_end, suffix_start, ), }; diff --git a/crates/tui/src/tools/large_output_router.rs b/crates/tui/src/tools/large_output_router.rs index 0f600ef5..6821693c 100644 --- a/crates/tui/src/tools/large_output_router.rs +++ b/crates/tui/src/tools/large_output_router.rs @@ -311,8 +311,7 @@ mod tests { #[test] fn wrap_synthesis_includes_provenance_header() { - let wrapped = - LargeOutputRouter::wrap_synthesis("web_search", "key facts here", 5000, 4096); + let wrapped = LargeOutputRouter::wrap_synthesis("web_search", "key facts here", 5000, 4096); assert!(wrapped.contains("workshop-synthesis")); assert!(wrapped.contains("web_search")); assert!(wrapped.contains("5000")); diff --git a/crates/tui/src/tools/mod.rs b/crates/tui/src/tools/mod.rs index d5f19ffa..37dcc577 100644 --- a/crates/tui/src/tools/mod.rs +++ b/crates/tui/src/tools/mod.rs @@ -12,9 +12,9 @@ pub mod finance; pub mod fetch_url; pub mod fim; pub mod git; -pub mod large_output_router; pub mod git_history; pub mod github; +pub mod large_output_router; pub mod parallel; pub mod plan; pub mod project; diff --git a/crates/tui/src/tools/registry.rs b/crates/tui/src/tools/registry.rs index e3e12eda..fe943b42 100644 --- a/crates/tui/src/tools/registry.rs +++ b/crates/tui/src/tools/registry.rs @@ -135,10 +135,7 @@ impl ToolRegistry { // Large-output routing (#548): if the result exceeds the threshold and // the caller did not request `raw=true`, synthesise via the workshop. - let raw_bypass = input - .get("raw") - .and_then(|v| v.as_bool()) - .unwrap_or(false); + let raw_bypass = input.get("raw").and_then(|v| v.as_bool()).unwrap_or(false); if let Some(router) = ctx.large_output_router.as_ref() { use crate::tools::large_output_router::{LargeOutputRouter, RouteDecision}; @@ -161,11 +158,7 @@ impl ToolRegistry { // the registry layer. A follow-up can wire in the Flash // client when the async LLM call is safe here. let preview_chars = 1_200usize; - let preview: String = result - .content - .chars() - .take(preview_chars) - .collect(); + let preview: String = result.content.chars().take(preview_chars).collect(); let ellipsis = if result.content.chars().count() > preview_chars { "\n… [output truncated — full text in workshop variable `last_tool_result`]" } else { diff --git a/crates/tui/src/tools/shell.rs b/crates/tui/src/tools/shell.rs index b622e701..5e71e94a 100644 --- a/crates/tui/src/tools/shell.rs +++ b/crates/tui/src/tools/shell.rs @@ -1728,9 +1728,7 @@ impl ToolSpec for ExecShellTool { } } Err(e) => { - return Ok(ToolResult::error(format!( - "Sandbox backend error: {e}" - ))); + return Ok(ToolResult::error(format!("Sandbox backend error: {e}"))); } }; diff --git a/crates/tui/src/tools/spec.rs b/crates/tui/src/tools/spec.rs index 052fb9c4..91f9ff8e 100644 --- a/crates/tui/src/tools/spec.rs +++ b/crates/tui/src/tools/spec.rs @@ -132,7 +132,9 @@ pub struct ToolContext { /// Per-session workshop variable store (#548). Holds the raw content of /// the most recent large-tool routing event so the parent can call /// `promote_to_context` later. `None` when the router is disabled. - pub workshop_vars: Option>>, + pub workshop_vars: Option< + std::sync::Arc>, + >, } impl ToolContext { @@ -459,7 +461,9 @@ impl ToolContext { pub fn with_large_output_router( mut self, router: crate::tools::large_output_router::LargeOutputRouter, - vars: std::sync::Arc>, + vars: std::sync::Arc< + tokio::sync::Mutex, + >, ) -> Self { self.large_output_router = Some(router); self.workshop_vars = Some(vars); diff --git a/crates/tui/src/tools/subagent/mod.rs b/crates/tui/src/tools/subagent/mod.rs index 0731ede1..d63bac68 100644 --- a/crates/tui/src/tools/subagent/mod.rs +++ b/crates/tui/src/tools/subagent/mod.rs @@ -1641,9 +1641,8 @@ impl ToolSpec for AgentSpawnTool { } else { self.runtime.context.workspace.join(file_path) }; - let file_contents = std::fs::read_to_string(&abs_path).unwrap_or_else(|e| { - format!("") - }); + let file_contents = std::fs::read_to_string(&abs_path) + .unwrap_or_else(|e| format!("")); let prefixed = format!( "\n```\n{file_contents}\n```\n\n{}", spawn_request.prompt diff --git a/crates/tui/src/tui/app.rs b/crates/tui/src/tui/app.rs index e36e5bf8..08af4795 100644 --- a/crates/tui/src/tui/app.rs +++ b/crates/tui/src/tui/app.rs @@ -1067,8 +1067,7 @@ impl App { let ui_locale = resolve_locale(&settings.locale); let composer_density = ComposerDensity::from_setting(&settings.composer_density); let composer_border = settings.composer_border; - let composer_vim_enabled = - settings.composer_vim_mode.trim().to_ascii_lowercase() == "vim"; + let composer_vim_enabled = settings.composer_vim_mode.trim().to_ascii_lowercase() == "vim"; let transcript_spacing = TranscriptSpacing::from_setting(&settings.transcript_spacing); let sidebar_width_percent = settings.sidebar_width_percent; let sidebar_focus = SidebarFocus::from_setting(&settings.sidebar_focus); @@ -2783,9 +2782,7 @@ impl App { let text = self.input.clone(); let cursor_byte = byte_index_at_char(&text, self.cursor_position); // Walk backward until we find a newline or the start of the string. - let line_start_byte = text[..cursor_byte] - .rfind('\n') - .map_or(0, |idx| idx + 1); + let line_start_byte = text[..cursor_byte].rfind('\n').map_or(0, |idx| idx + 1); self.cursor_position = char_count(&text[..line_start_byte]); self.needs_redraw = true; } @@ -2795,11 +2792,10 @@ impl App { let text = self.input.clone(); let cursor_byte = byte_index_at_char(&text, self.cursor_position); // Walk forward to the next newline or end-of-string. - let line_end_char = text[cursor_byte..] - .find('\n') - .map_or_else(|| char_count(&text), |rel| { - char_count(&text[..cursor_byte + rel]) - }); + let line_end_char = text[cursor_byte..].find('\n').map_or_else( + || char_count(&text), + |rel| char_count(&text[..cursor_byte + rel]), + ); self.cursor_position = line_end_char; self.needs_redraw = true; } @@ -2887,9 +2883,7 @@ impl App { pub fn vim_delete_line(&mut self) { let text = self.input.clone(); let cursor_byte = byte_index_at_char(&text, self.cursor_position); - let line_start_byte = text[..cursor_byte] - .rfind('\n') - .map_or(0, |idx| idx + 1); + let line_start_byte = text[..cursor_byte].rfind('\n').map_or(0, |idx| idx + 1); let line_end_byte = text[cursor_byte..] .find('\n') .map_or(text.len(), |rel| cursor_byte + rel); @@ -2974,18 +2968,15 @@ impl App { let rest = &text[cursor_byte..]; if let Some(rel_nl) = rest.find('\n') { // Column offset on the current line. - let line_start_byte = text[..cursor_byte] - .rfind('\n') - .map_or(0, |i| i + 1); + let line_start_byte = text[..cursor_byte].rfind('\n').map_or(0, |i| i + 1); let col = char_count(&text[line_start_byte..cursor_byte]); let next_line_start = cursor_byte + rel_nl + 1; let next_line = &text[next_line_start..]; let next_line_len = next_line.find('\n').unwrap_or(next_line.len()); - let next_line_char_len = char_count(&text[next_line_start - ..next_line_start + next_line_len]); + let next_line_char_len = + char_count(&text[next_line_start..next_line_start + next_line_len]); let target_col = col.min(next_line_char_len); - self.cursor_position = - char_count(&text[..next_line_start]) + target_col; + self.cursor_position = char_count(&text[..next_line_start]) + target_col; self.needs_redraw = true; } else { self.history_down(); @@ -3003,13 +2994,10 @@ impl App { let col = char_count(&text[line_start_byte..cursor_byte]); // Find start of the previous line. let prev_line_end = prev_nl; // byte of the newline itself - let prev_start = text[..prev_line_end] - .rfind('\n') - .map_or(0, |i| i + 1); + let prev_start = text[..prev_line_end].rfind('\n').map_or(0, |i| i + 1); let prev_line_len = char_count(&text[prev_start..prev_line_end]); let target_col = col.min(prev_line_len); - self.cursor_position = - char_count(&text[..prev_start]) + target_col; + self.cursor_position = char_count(&text[..prev_start]) + target_col; self.needs_redraw = true; } else { self.history_up(); diff --git a/crates/tui/src/tui/plan_prompt.rs b/crates/tui/src/tui/plan_prompt.rs index c72b801f..e75c203f 100644 --- a/crates/tui/src/tui/plan_prompt.rs +++ b/crates/tui/src/tui/plan_prompt.rs @@ -46,16 +46,15 @@ fn render_modal_chrome(area: Rect, popup_area: Rect, buf: &mut Buffer) { .min(shadow_bottom.saturating_sub(shadow_y)); if shadow_width > 0 && shadow_height > 0 { - Block::default() - .render( - Rect { - x: shadow_x, - y: shadow_y, - width: shadow_width, - height: shadow_height, - }, - buf, - ); + Block::default().render( + Rect { + x: shadow_x, + y: shadow_y, + width: shadow_width, + height: shadow_height, + }, + buf, + ); } Clear.render(popup_area, buf); diff --git a/crates/tui/src/tui/sidebar.rs b/crates/tui/src/tui/sidebar.rs index 5516406e..6501ea20 100644 --- a/crates/tui/src/tui/sidebar.rs +++ b/crates/tui/src/tui/sidebar.rs @@ -30,8 +30,7 @@ pub fn render_sidebar(f: &mut Frame, area: Rect, app: &App) { if area.width < 24 || area.height < 8 { // Paint a styled block over the area so stale cells from a previous // (wider) frame don't persist as bleed-through artifacts (#400). - Block::default() - .render(area, f.buffer_mut()); + Block::default().render(area, f.buffer_mut()); return; } @@ -740,8 +739,7 @@ fn render_context_panel(f: &mut Frame, area: Rect, app: &App) { fn render_sidebar_section(f: &mut Frame, area: Rect, title: &str, lines: Vec>) { if area.width < 4 || area.height < 3 { // Clear stale cells before bailing out (#400). - Block::default() - .render(area, f.buffer_mut()); + Block::default().render(area, f.buffer_mut()); return; } diff --git a/crates/tui/src/tui/user_input.rs b/crates/tui/src/tui/user_input.rs index 022f3e23..708e437a 100644 --- a/crates/tui/src/tui/user_input.rs +++ b/crates/tui/src/tui/user_input.rs @@ -33,16 +33,15 @@ fn render_modal_chrome(area: Rect, popup_area: Rect, buf: &mut Buffer) { .min(shadow_bottom.saturating_sub(shadow_y)); if shadow_width > 0 && shadow_height > 0 { - Block::default() - .render( - Rect { - x: shadow_x, - y: shadow_y, - width: shadow_width, - height: shadow_height, - }, - buf, - ); + Block::default().render( + Rect { + x: shadow_x, + y: shadow_y, + width: shadow_width, + height: shadow_height, + }, + buf, + ); } Clear.render(popup_area, buf); diff --git a/crates/tui/src/tui/widgets/mod.rs b/crates/tui/src/tui/widgets/mod.rs index 133a3c7c..1a6f12ec 100644 --- a/crates/tui/src/tui/widgets/mod.rs +++ b/crates/tui/src/tui/widgets/mod.rs @@ -576,11 +576,8 @@ impl Renderable for ComposerWidget<'_> { }; let label = self.app.composer.vim_mode.label(); block = block.title_top( - Line::from(Span::styled( - label, - Style::default().fg(color).bold(), - )) - .right_aligned(), + Line::from(Span::styled(label, Style::default().fg(color).bold())) + .right_aligned(), ); } if let Some(hint_line) = hint_line {