annotate rust/hg-core/src/progress.rs @ 52156:e6a44bc91bc2 stable

rust-update: make `update_from_null` respect `worker.numcpu` config option This was overlooked in the original series. This is important for tests (because we run many at once), and for the occasional end user that wants to keep their CPU usage in check. A future series should clean up this `worker` parameter tunelling business by rewriting the config in Rust, but doing so on stable would be a very bad idea.
author Rapha?l Gom?s <rgomes@octobus.net>
date Tue, 05 Nov 2024 15:21:09 +0100
parents 92e23ba257d1
children a876ab6c3fd5
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
52065
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
1 //! Progress-bar related things
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
2
52066
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
3 use std::{
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
4 sync::atomic::{AtomicBool, Ordering},
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
5 time::Duration,
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
6 };
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
7
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
8 use indicatif::{ProgressBar, ProgressDrawTarget, ProgressStyle};
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
9
52065
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
10 /// A generic determinate progress bar trait
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
11 pub trait Progress: Send + Sync + 'static {
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
12 /// Set the current position and optionally the total
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
13 fn update(&self, pos: u64, total: Option<u64>);
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
14 /// Increment the current position and optionally the total
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
15 fn increment(&self, step: u64, total: Option<u64>);
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
16 /// Declare that progress is over and the progress bar should be deleted
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
17 fn complete(self);
3ae7c43ad8aa rust: add `Progress` trait for progress bars
Rapha?l Gom?s <rgomes@octobus.net>
parents:
diff changeset
18 }
52066
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
19
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
20 const PROGRESS_DELAY: Duration = Duration::from_secs(1);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
21
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
22 /// A generic (determinate) progress bar. Stays hidden until [`PROGRESS_DELAY`]
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
23 /// to prevent flickering a progress bar for super fast operations.
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
24 pub struct HgProgressBar {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
25 progress: ProgressBar,
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
26 has_been_shown: AtomicBool,
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
27 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
28
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
29 impl HgProgressBar {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
30 // TODO pass config to check progress.disable/assume-tty/delay/etc.
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
31 /// Return a new progress bar with `topic` as the prefix.
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
32 /// The progress and total are both set to 0, and it is hidden until the
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
33 /// next call to `update` given that more than a second has elapsed.
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
34 pub fn new(topic: &str) -> Self {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
35 let template =
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
36 format!("{} {{wide_bar}} {{pos}}/{{len}} {{eta}} ", topic);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
37 let style = ProgressStyle::with_template(&template).unwrap();
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
38 let progress_bar = ProgressBar::new(0).with_style(style);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
39 // Hide the progress bar and only show it if we've elapsed more
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
40 // than a second
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
41 progress_bar.set_draw_target(ProgressDrawTarget::hidden());
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
42 Self {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
43 progress: progress_bar,
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
44 has_been_shown: false.into(),
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
45 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
46 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
47
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
48 /// Called whenever the progress changes to determine whether to start
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
49 /// showing the progress bar
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
50 fn maybe_show(&self) {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
51 if self.progress.is_hidden()
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
52 && self.progress.elapsed() > PROGRESS_DELAY
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
53 {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
54 // Catch a race condition whereby we check if it's hidden, then
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
55 // set the draw target from another thread, then do it again from
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
56 // this thread, which results in multiple progress bar lines being
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
57 // left drawn.
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
58 let has_been_shown =
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
59 self.has_been_shown.fetch_or(true, Ordering::Relaxed);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
60 if !has_been_shown {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
61 // Here we are certain that we're the only thread that has
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
62 // set `has_been_shown` and we can change the draw target
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
63 self.progress.set_draw_target(ProgressDrawTarget::stderr());
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
64 self.progress.tick();
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
65 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
66 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
67 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
68 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
69
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
70 impl Progress for HgProgressBar {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
71 fn update(&self, pos: u64, total: Option<u64>) {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
72 self.progress.update(|state| {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
73 state.set_pos(pos);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
74 if let Some(t) = total {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
75 state.set_len(t)
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
76 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
77 });
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
78 self.maybe_show();
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
79 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
80
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
81 fn increment(&self, step: u64, total: Option<u64>) {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
82 self.progress.inc(step);
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
83 if let Some(t) = total {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
84 self.progress.set_length(t)
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
85 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
86 self.maybe_show();
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
87 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
88
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
89 fn complete(self) {
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
90 self.progress.finish_and_clear();
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
91 }
92e23ba257d1 rust-hg-cpython: add an `HgProgressBar` util
Rapha?l Gom?s <rgomes@octobus.net>
parents: 52065
diff changeset
92 }