Refresh buttons turn from the press to the end of their scan; quick checks keep the count (#232, #233)
The buttons followed the feeds being checked, so they stopped between one feed and the next;
7ecbe82 held them for 600 ms over each gap. Now pressing one starts it, and scan_done stops
it only when it is the end of the scan asked for: scan_done carries `only` and `forced`, so a
scheduled scan finishing first does not stop a button whose scan is queued behind it. An
error event, a job that failed without a scan_done, stops them all.
A row's spinner stood in for its unread count from the moment its feed was checked; most
checks take milliseconds, so each count blinked as the scan went by. It now waits 300 ms.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -17,6 +17,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
|
||||
- Check every feed looks up the site icons of feeds without artwork a few at a time, alongside the fetches, instead of one after another (#228).
|
||||
- A feed's server that sends nothing for 15 s is given up on, instead of holding a scan for the full 30 s; a feed that keeps sending still has 30 s (#230).
|
||||
- A scan's trace names the feed each fetch is for (#229).
|
||||
- `scan_done` on the event stream says which feed or folder the scan was limited to and whether someone asked for it (`only`, `forced`), so a page can tell the end of its own scan from a scheduled one's (#233).
|
||||
|
||||
## [1.1.0] - 2026-10-13
|
||||
|
||||
|
||||
@@ -36,7 +36,15 @@ pub enum Event {
|
||||
DeadairDone { feed: String, enclosure: i64, saved_s: i64 },
|
||||
Reaped { path: String, bytes: u64 },
|
||||
/// Terminal: a client that asked for work stops reading here.
|
||||
ScanDone { feeds: usize },
|
||||
ScanDone {
|
||||
feeds: usize,
|
||||
/// The feed or folder the scan was limited to, and whether someone asked for it: a page
|
||||
/// stops the button they pressed at the end of their scan, not at a scheduled one's (#233).
|
||||
#[serde(default)]
|
||||
only: Option<String>,
|
||||
#[serde(default)]
|
||||
forced: bool,
|
||||
},
|
||||
ReapDone { files: usize, bytes: u64 },
|
||||
Status { feeds: usize, pending: i64, downloaded: i64 },
|
||||
Error { msg: String },
|
||||
@@ -82,7 +90,7 @@ impl Event {
|
||||
Event::FeedStart { feed } => format!("{feed}: checking"),
|
||||
Event::TorrentDeferred { feed, .. } => format!("{feed}: torrent deferred"),
|
||||
Event::DeadairDone { feed, saved_s, .. } => format!("{feed}: DeadAir found the silences, {saved_s} s shorter"),
|
||||
Event::ScanDone { feeds } => format!("scan complete, {feeds} feed(s)"),
|
||||
Event::ScanDone { feeds, .. } => format!("scan complete, {feeds} feed(s)"),
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -434,7 +442,7 @@ mod tests {
|
||||
|
||||
#[test]
|
||||
fn only_completion_events_end_a_client_session() {
|
||||
assert!(Event::ScanDone { feeds: 1 }.is_terminal());
|
||||
assert!(Event::ScanDone { feeds: 1, only: None, forced: false }.is_terminal());
|
||||
assert!(Event::ReapDone { files: 0, bytes: 0 }.is_terminal());
|
||||
assert!(!Event::FeedDone {
|
||||
feed: "a".into(),
|
||||
|
||||
@@ -1361,7 +1361,7 @@ async fn fetch(ctx: &Arc<Ctx>, only: Option<&str>, force: bool, scope: &[String]
|
||||
}
|
||||
}
|
||||
}
|
||||
ctx.out.emit(Event::ScanDone { feeds: scanned });
|
||||
ctx.out.emit(Event::ScanDone { feeds: scanned, only: only.map(str::to_owned), forced: force });
|
||||
// What people subscribe to may have changed, and new feeds have titles now: share it.
|
||||
ctx.directory_wake.notify_one();
|
||||
Ok(())
|
||||
@@ -2321,7 +2321,7 @@ async fn download_one(ctx: &Arc<Ctx>, id: i64) -> Result<()> {
|
||||
}
|
||||
}
|
||||
// Terminal, so a UI waiting on this request stops here.
|
||||
ctx.out.emit(Event::ScanDone { feeds: 1 });
|
||||
ctx.out.emit(Event::ScanDone { feeds: 1, only: None, forced: false });
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user