From 0eda9045cd7de0a82f7dcd850a24d17696e6e608 Mon Sep 17 00:00:00 2001 From: Shautvast Date: Wed, 18 Feb 2026 08:59:42 +0100 Subject: [PATCH] Cancel stale body fetch requests when selection changes quickly Uses Arc to track the most recently wanted email sequence number. The worker skips fetch requests that no longer match, avoiding wasted network calls when scrolling through emails rapidly. Co-Authored-By: Claude Opus 4.6 --- src/lib.rs | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/src/lib.rs b/src/lib.rs index fc7bf86..5601529 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,5 +1,6 @@ use std::io::{Error, Stdout}; -use std::sync::mpsc; +use std::sync::atomic::{AtomicU32, Ordering}; +use std::sync::{mpsc, Arc}; use std::thread; use std::time::{Duration, Instant}; use crossterm::event; @@ -49,6 +50,7 @@ fn worker_loop( config: Config, cmd_rx: mpsc::Receiver, result_tx: mpsc::Sender, + wanted_body_seq: Arc, ) { let mut session: Option = None; @@ -63,6 +65,10 @@ fn worker_loop( let _ = result_tx.send(WorkerResult::FetchedMore(result)); } WorkerCmd::FetchBody { seq } => { + // Skip if a newer body request has been made + if wanted_body_seq.load(Ordering::Relaxed) != seq { + continue; + } let result = inbox::fetch_body(&mut session, seq, &config); let _ = result_tx.send(WorkerResult::Body { seq, result }); } @@ -83,9 +89,11 @@ pub fn main(config: &Config, terminal: &mut Terminal>) let (cmd_tx, cmd_rx) = mpsc::channel(); let (result_tx, result_rx) = mpsc::channel(); + let wanted_body_seq = Arc::new(AtomicU32::new(0)); let worker_config = config.clone(); + let worker_wanted = Arc::clone(&wanted_body_seq); let worker = thread::spawn(move || { - worker_loop(worker_config, cmd_rx, result_tx); + worker_loop(worker_config, cmd_rx, result_tx, worker_wanted); }); // Send initial refresh @@ -129,6 +137,7 @@ pub fn main(config: &Config, terminal: &mut Terminal>) preview_body.clear(); preview_scroll = 0; body_loading = true; + wanted_body_seq.store(seq, Ordering::Relaxed); let _ = cmd_tx.send(WorkerCmd::FetchBody { seq }); } } else { @@ -301,6 +310,7 @@ pub fn main(config: &Config, terminal: &mut Terminal>) preview_body.clear(); preview_scroll = 0; body_loading = true; + wanted_body_seq.store(seq, Ordering::Relaxed); let _ = cmd_tx.send(WorkerCmd::FetchBody { seq }); } } @@ -320,6 +330,7 @@ pub fn main(config: &Config, terminal: &mut Terminal>) preview_body.clear(); preview_scroll = 0; body_loading = true; + wanted_body_seq.store(seq, Ordering::Relaxed); let _ = cmd_tx.send(WorkerCmd::FetchBody { seq }); } } @@ -347,6 +358,7 @@ pub fn main(config: &Config, terminal: &mut Terminal>) preview_body.clear(); preview_scroll = 0; body_loading = true; + wanted_body_seq.store(new_seq, Ordering::Relaxed); let _ = cmd_tx.send(WorkerCmd::FetchBody { seq: new_seq }); } }