File tree Expand file tree Collapse file tree 3 files changed +39
-8
lines changed Expand file tree Collapse file tree 3 files changed +39
-8
lines changed Original file line number Diff line number Diff line change @@ -20,6 +20,11 @@ impl SystemTimeTools {
20
20
pub fn shift ( duration : Duration ) {
21
21
* SYSTEM_TIME_SHIFT . write ( ) . unwrap ( ) += duration;
22
22
}
23
+
24
+ /// Simulates the system clock being rewound by `duration`.
25
+ pub fn shift_backwards ( duration : Duration ) {
26
+ * SYSTEM_TIME_SHIFT . write ( ) . unwrap ( ) -= duration;
27
+ }
23
28
}
24
29
25
30
#[ cfg( test) ]
Original file line number Diff line number Diff line change @@ -159,7 +159,19 @@ pub async fn maybe_send_statistics(context: &Context) -> Result<Option<ChatId>>
159
159
let last_sending_time = context. get_config_i64 ( Config :: StatsLastSent ) . await ?;
160
160
let next_sending_time = last_sending_time. saturating_add ( SENDING_INTERVAL_SECONDS ) ;
161
161
if next_sending_time <= time ( ) {
162
+ // Setting this config at the beginning avoids endless loops when things do not
163
+ // work out for whatever reason.
164
+ context
165
+ . set_config_internal ( Config :: StatsLastSent , Some ( & time ( ) . to_string ( ) ) )
166
+ . await ?;
167
+
162
168
return Ok ( Some ( send_statistics ( context) . await ?) ) ;
169
+ } else if time ( ) < last_sending_time {
170
+ // The clock was rewound.
171
+ // Reset the config, so that the statistics will be sent normally in a week.
172
+ context
173
+ . set_config_internal ( Config :: StatsLastSent , Some ( & time ( ) . to_string ( ) ) )
174
+ . await ?;
163
175
}
164
176
}
165
177
Ok ( None )
@@ -184,14 +196,6 @@ pub(crate) async fn should_send_statistics(context: &Context) -> Result<bool> {
184
196
async fn send_statistics ( context : & Context ) -> Result < ChatId > {
185
197
info ! ( context, "Sending statistics." ) ;
186
198
187
- // Setting this config at the beginning avoids endless loops when things do not
188
- // work out for whatever reason.
189
- context
190
- . set_config_internal ( Config :: StatsLastSent , Some ( & time ( ) . to_string ( ) ) )
191
- . await
192
- . log_err ( context)
193
- . ok ( ) ;
194
-
195
199
let chat_id = get_statistics_bot ( context) . await ?;
196
200
197
201
let mut msg = Message :: new ( Viewtype :: File ) ;
Original file line number Diff line number Diff line change @@ -43,6 +43,28 @@ async fn test_maybe_send_statistics() -> Result<()> {
43
43
Ok ( ( ) )
44
44
}
45
45
46
+ #[ tokio:: test( flavor = "multi_thread" , worker_threads = 2 ) ]
47
+ async fn test_rewound_time ( ) -> Result < ( ) > {
48
+ let alice = & TestContext :: new_alice ( ) . await ;
49
+ alice. set_config_bool ( Config :: StatsSending , true ) . await ?;
50
+
51
+ const EIGHT_DAYS : Duration = Duration :: from_secs ( 3600 * 24 * 14 ) ;
52
+ SystemTime :: shift ( EIGHT_DAYS ) ;
53
+
54
+ maybe_send_statistics ( alice) . await ?. unwrap ( ) ;
55
+
56
+ // The system's time is rewound
57
+ SystemTime :: shift_backwards ( EIGHT_DAYS ) ;
58
+
59
+ assert ! ( maybe_send_statistics( alice) . await ?. is_none( ) ) ;
60
+
61
+ // After eight days pass again, statistics are sent again
62
+ SystemTime :: shift ( EIGHT_DAYS ) ;
63
+ maybe_send_statistics ( alice) . await ?. unwrap ( ) ;
64
+
65
+ Ok ( ( ) )
66
+ }
67
+
46
68
#[ tokio:: test( flavor = "multi_thread" , worker_threads = 2 ) ]
47
69
async fn test_statistics_one_contact ( ) -> Result < ( ) > {
48
70
let mut tcm = TestContextManager :: new ( ) ;
You can’t perform that action at this time.
0 commit comments