1 extern crate backoff;
2 extern crate instant;
3 
4 use backoff::backoff::Backoff;
5 use backoff::exponential::ExponentialBackoff;
6 use backoff::{Clock, SystemClock};
7 
8 use instant::Instant;
9 use std::cell::RefCell;
10 use std::time::Duration;
11 
12 struct Inner {
13     i: Duration,
14     start: Instant,
15 }
16 
17 struct TestClock(RefCell<Inner>);
18 
19 impl TestClock {
new(i: Duration, start: Instant) -> TestClock20     fn new(i: Duration, start: Instant) -> TestClock {
21         TestClock(RefCell::new(Inner { i: i, start: start }))
22     }
23 }
24 
25 impl Clock for TestClock {
now(&self) -> Instant26     fn now(&self) -> Instant {
27         let mut inner = self.0.borrow_mut();
28         let t = inner.start + inner.i;
29         inner.i += Duration::from_secs(1);
30         t
31     }
32 }
33 
34 impl Default for TestClock {
default() -> Self35     fn default() -> Self {
36         TestClock::new(Duration::from_secs(1), Instant::now())
37     }
38 }
39 
40 #[test]
get_elapsed_time()41 fn get_elapsed_time() {
42     let mut exp = ExponentialBackoff::default();
43     exp.clock = TestClock::new(Duration::new(0, 0), Instant::now());
44     exp.reset();
45 
46     let elapsed_time = exp.get_elapsed_time();
47     assert_eq!(elapsed_time, Duration::new(1, 0));
48 }
49 
50 #[test]
max_elapsed_time()51 fn max_elapsed_time() {
52     let mut exp = ExponentialBackoff::default();
53     exp.clock = TestClock::new(Duration::new(0, 0), Instant::now());
54     // Change the currentElapsedTime to be 0 ensuring that the elapsed time will be greater
55     // than the max elapsed time.
56     exp.start_time = Instant::now() - Duration::new(1000, 0);
57     assert!(exp.next_backoff().is_none());
58 }
59 
60 #[test]
backoff()61 fn backoff() {
62     let mut exp = ExponentialBackoff::<SystemClock>::default();
63     exp.initial_interval = Duration::from_millis(500);
64     exp.randomization_factor = 0.1;
65     exp.multiplier = 2.0;
66     exp.max_interval = Duration::from_secs(5);
67     exp.max_elapsed_time = Some(Duration::new(16 * 60, 0));
68     exp.reset();
69 
70     let expected_results_millis = [500, 1000, 2000, 4000, 5000, 5000, 5000, 5000, 5000, 5000];
71     let expected_results = expected_results_millis
72         .iter()
73         .map(|&ms| Duration::from_millis(ms))
74         .collect::<Vec<_>>();
75 
76     for i in expected_results {
77         assert_eq!(i, exp.current_interval);
78         exp.next_backoff();
79     }
80 }
81