pacenotes_installer/
size.rs1const KB: u64 = 1024;
5const MB: u64 = 1024 * KB;
6const GB: u64 = 1024 * MB;
7
8pub fn human(bytes: u64) -> String {
11 let (divisor, unit) = unit_for(bytes);
12 if divisor == 1 {
13 return format!("{bytes} {unit}");
14 }
15 let (whole, tenth) = tenths(bytes, divisor);
16 format!("{whole}.{tenth} {unit}")
17}
18
19pub fn human_progress(done: u64, total: u64) -> String {
22 if total == 0 {
23 return human(done);
24 }
25 let (divisor, unit) = unit_for(total);
26 if divisor == 1 {
27 return format!("{done} / {total} {unit}");
28 }
29 let (done_whole, done_tenth) = tenths(done, divisor);
30 let (total_whole, total_tenth) = tenths(total, divisor);
31 format!("{done_whole}.{done_tenth} / {total_whole}.{total_tenth} {unit}")
32}
33
34fn tenths(bytes: u64, divisor: u64) -> (u64, u64) {
36 let scaled = (bytes * 10 + divisor / 2) / divisor;
37 (scaled / 10, scaled % 10)
38}
39
40fn unit_for(bytes: u64) -> (u64, &'static str) {
41 match bytes {
42 0..KB => (1, "B"),
43 KB..MB => (KB, "kB"),
44 MB..GB => (MB, "MB"),
45 _ => (GB, "GB"),
46 }
47}
48
49#[cfg(test)]
50mod tests {
51 #[test]
53 fn a_real_package_reads_as_explorer_shows_it() {
54 assert_eq!(super::human(43_609_253), "41.6 MB");
55 }
56
57 #[test]
58 fn a_small_package_is_counted_in_bytes_and_kb() {
59 assert_eq!(super::human(5_861), "5.7 kB");
60 assert_eq!(super::human(997), "997 B");
61 assert_eq!(super::human(0), "0 B");
62 }
63
64 #[test]
65 fn the_unit_turns_over_at_the_boundary() {
66 assert_eq!(super::human(1023), "1023 B");
67 assert_eq!(super::human(1024), "1.0 kB");
68 assert_eq!(super::human(1024 * 1024 - 1), "1024.0 kB");
69 assert_eq!(super::human(1024 * 1024), "1.0 MB");
70 assert_eq!(super::human(1024 * 1024 * 1024), "1.0 GB");
71 }
72
73 #[test]
75 fn a_transfer_shows_both_numbers_in_the_total_s_unit() {
76 assert_eq!(
77 super::human_progress(13_000_000, 43_609_253),
78 "12.4 / 41.6 MB"
79 );
80 assert_eq!(super::human_progress(1_020_000, 1_048_576), "1.0 / 1.0 MB");
81 assert_eq!(super::human_progress(500, 5_861), "0.5 / 5.7 kB");
82 }
83
84 #[test]
85 fn an_unknown_total_still_reports_what_arrived() {
86 assert_eq!(super::human_progress(43_609_253, 0), "41.6 MB");
87 }
88}