Track WIM scans to avoid stacking scans

This commit is contained in:
2Shirt 2025-12-04 22:36:38 -08:00
parent c4c174b546
commit 87ccc80602
Signed by: 2Shirt
GPG key ID: 152FAC923B0E132C
4 changed files with 63 additions and 21 deletions

View file

@ -262,6 +262,9 @@ impl App {
self.last_tick_key_events.drain(..); self.last_tick_key_events.drain(..);
// Check background task(s) // Check background task(s)
self.tasks.poll()?; self.tasks.poll()?;
if let Ok(mut wim_sources) = self.state.wim_sources.lock() {
wim_sources.poll();
}
} }
Action::Quit => self.should_quit = true, Action::Quit => self.should_quit = true,
Action::Suspend => self.should_suspend = true, Action::Suspend => self.should_suspend = true,

View file

@ -23,7 +23,7 @@ use color_eyre::Result;
use crossterm::event::KeyEvent; use crossterm::event::KeyEvent;
use ratatui::{ use ratatui::{
prelude::*, prelude::*,
widgets::{Block, Borders, Clear, HighlightSpacing, List, ListItem, Padding, Paragraph}, widgets::{Block, Borders, Clear, List, ListItem, Padding, Paragraph},
}; };
use tokio::sync::mpsc::UnboundedSender; use tokio::sync::mpsc::UnboundedSender;
@ -111,12 +111,16 @@ impl Component for WimScan {
if let Ok(wim_sources) = self.wim_sources.lock() { if let Ok(wim_sources) = self.wim_sources.lock() {
// Local // Local
let mut left_list = Vec::new(); let mut left_list = Vec::new();
left_list.extend( if wim_sources.thread_local.is_some() {
wim_sources left_list.push(ListItem::new("Scanning..."));
.local } else {
.iter() left_list.extend(
.map(|wimfile| ListItem::new(format!("{}\n\n", wimfile.path))), wim_sources
); .local
.iter()
.map(|wimfile| ListItem::new(format!("{}\n\n", wimfile.path))),
);
}
let left_list = List::new(left_list).block( let left_list = List::new(left_list).block(
Block::default() Block::default()
.borders(Borders::ALL) .borders(Borders::ALL)
@ -126,12 +130,16 @@ impl Component for WimScan {
// Network // Network
let mut right_list = Vec::new(); let mut right_list = Vec::new();
right_list.extend(wim_sources.network.iter().map(|wimfile| { if wim_sources.thread_network.is_some() {
ListItem::new(format!( right_list.push(ListItem::new("Scanning..."));
"{}\n\n", } else {
wimfile.path.split("\\").last().unwrap_or(&wimfile.path) right_list.extend(wim_sources.network.iter().map(|wimfile| {
)) ListItem::new(format!(
})); "{}\n\n",
wimfile.path.split("\\").last().unwrap_or(&wimfile.path)
))
}));
}
let right_list = List::new(right_list).block( let right_list = List::new(right_list).block(
Block::default() Block::default()
.borders(Borders::ALL) .borders(Borders::ALL)

View file

@ -90,17 +90,27 @@ impl State {
pub fn scan_wim_local(&mut self, scan_type: ScanType) { pub fn scan_wim_local(&mut self, scan_type: ScanType) {
let disk_list_arc = self.disk_list.clone(); let disk_list_arc = self.disk_list.clone();
let wim_sources_arc = self.wim_sources.clone(); let wim_sources_arc = self.wim_sources.clone();
tokio::task::spawn(async move { let wim_sources_arc_inner = self.wim_sources.clone();
scan_local_drives(disk_list_arc, wim_sources_arc, scan_type); if let Ok(mut wim_sources) = wim_sources_arc.lock()
}); && wim_sources.thread_local.is_none()
{
wim_sources.thread_local = Some(tokio::task::spawn(async move {
scan_local_drives(disk_list_arc, wim_sources_arc_inner, scan_type);
}));
}
} }
pub fn scan_wim_network(&mut self) { pub fn scan_wim_network(&mut self) {
let config = self.config.clone();
let wim_sources_arc = self.wim_sources.clone(); let wim_sources_arc = self.wim_sources.clone();
tokio::task::spawn(async move { let wim_sources_arc_inner = self.wim_sources.clone();
scan_network_share(config, wim_sources_arc); if let Ok(mut wim_sources) = wim_sources_arc.lock()
}); && wim_sources.thread_network.is_none()
{
let config = self.config.clone();
wim_sources.thread_network = Some(tokio::task::spawn(async move {
scan_network_share(config, wim_sources_arc_inner);
}));
}
} }
} }

View file

@ -1,4 +1,3 @@
use core::system::disk::bytes_to_string;
// This file is part of Deja-Vu. // This file is part of Deja-Vu.
// //
// Deja-Vu is free software: you can redistribute it and/or modify it // Deja-Vu is free software: you can redistribute it and/or modify it
@ -26,8 +25,11 @@ use std::{
}; };
use tempfile::NamedTempFile; use tempfile::NamedTempFile;
use tokio::task::JoinHandle;
use xml::reader::{EventReader, XmlEvent}; use xml::reader::{EventReader, XmlEvent};
use core::system::disk::bytes_to_string;
static WIMINFO_EXE: LazyLock<String> = LazyLock::new(|| { static WIMINFO_EXE: LazyLock<String> = LazyLock::new(|| {
let program_files = let program_files =
PathBuf::from(env::var("PROGRAMFILES").expect("Failed to resolve %PROGRAMFILES%")); PathBuf::from(env::var("PROGRAMFILES").expect("Failed to resolve %PROGRAMFILES%"));
@ -156,6 +158,8 @@ impl fmt::Display for WimImage {
pub struct WimSources { pub struct WimSources {
pub local: Vec<WimFile>, pub local: Vec<WimFile>,
pub network: Vec<WimFile>, pub network: Vec<WimFile>,
pub thread_local: Option<JoinHandle<()>>,
pub thread_network: Option<JoinHandle<()>>,
} }
impl WimSources { impl WimSources {
@ -187,6 +191,23 @@ impl WimSources {
list list
} }
pub fn poll(&mut self) {
let thread = self.thread_local.take();
if let Some(local) = thread
&& !local.is_finished()
{
// Task still going, keep tracking
self.thread_local = Some(local);
}
let thread = self.thread_network.take();
if let Some(network) = thread
&& !network.is_finished()
{
// Task still going, keep tracking
self.thread_network = Some(network);
}
}
pub fn reset_all(&mut self) { pub fn reset_all(&mut self) {
self.local.clear(); self.local.clear();
self.network.clear(); self.network.clear();