// ! Progress tracking for CLI operations use indicatif::{MultiProgress, ProgressBar, ProgressStyle}; use std::time::Duration; /// Progress tracker for long-running operations pub struct ProgressTracker { multi: MultiProgress, } impl ProgressTracker { /// Create a new progress tracker pub fn new() -> Self { Self { multi: MultiProgress::new(), } } /// Create a progress bar for an operation pub fn create_bar(&self, total: u64, message: &str) -> ProgressBar { let pb = self.multi.add(ProgressBar::new(total)); pb.set_style( ProgressStyle::default_bar() .template("{msg}\n{spinner:.green} [{elapsed_precise}] [{wide_bar:.cyan/blue}] {pos}/{len} ({eta})") .unwrap() .progress_chars("#>-") ); pb.set_message(message.to_string()); pb.enable_steady_tick(Duration::from_millis(100)); pb } /// Create a spinner for indeterminate operations pub fn create_spinner(&self, message: &str) -> ProgressBar { let pb = self.multi.add(ProgressBar::new_spinner()); pb.set_style( ProgressStyle::default_spinner() .template("{spinner:.green} {msg}") .unwrap(), ); pb.set_message(message.to_string()); pb.enable_steady_tick(Duration::from_millis(100)); pb } /// Finish all progress bars pub fn finish_all(&self) { // Progress bars auto-finish when dropped } } impl Default for ProgressTracker { fn default() -> Self { Self::new() } }