Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(161)

Side by Side Diff: components/proximity_auth/cryptauth/sync_scheduler_impl_unittest.cc

Issue 2502343003: Moved //components/proximity_auth/cryptauth to //components/cryptauth. (Closed)
Patch Set: Fixed proto #includes. Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
(Empty)
1 // Copyright 2015 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "components/proximity_auth/cryptauth/sync_scheduler_impl.h"
6
7 #include <utility>
8
9 #include "base/macros.h"
10 #include "base/memory/ptr_util.h"
11 #include "base/timer/mock_timer.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13
14 namespace proximity_auth {
15
16 using Strategy = SyncScheduler::Strategy;
17 using SyncState = SyncScheduler::SyncState;
18
19 namespace {
20
21 // Constants configuring the the scheduler.
22 const int kElapsedTimeDays = 40;
23 const int kRefreshPeriodDays = 30;
24 const int kRecoveryPeriodSeconds = 10;
25 const double kMaxJitterPercentage = 0.1;
26 const char kTestSchedulerName[] = "TestSyncSchedulerImpl";
27
28 // Returns true if |jittered_time_delta| is within the range of a jittered
29 // |base_time_delta| with a maximum of |max_jitter_ratio|.
30 bool IsTimeDeltaWithinJitter(const base::TimeDelta& base_time_delta,
31 const base::TimeDelta& jittered_time_delta,
32 double max_jitter_ratio) {
33 if (base_time_delta.is_zero())
34 return jittered_time_delta.is_zero();
35
36 base::TimeDelta difference =
37 (jittered_time_delta - base_time_delta).magnitude();
38 double percentage_of_base =
39 difference.InMillisecondsF() / base_time_delta.InMillisecondsF();
40 return percentage_of_base < max_jitter_ratio;
41 }
42
43 // Test harness for the SyncSchedulerImpl to create MockTimers.
44 class TestSyncSchedulerImpl : public SyncSchedulerImpl {
45 public:
46 TestSyncSchedulerImpl(Delegate* delegate,
47 base::TimeDelta refresh_period,
48 base::TimeDelta recovery_period,
49 double max_jitter_ratio)
50 : SyncSchedulerImpl(delegate,
51 refresh_period,
52 recovery_period,
53 max_jitter_ratio,
54 kTestSchedulerName) {}
55
56 ~TestSyncSchedulerImpl() override {}
57
58 base::MockTimer* timer() { return mock_timer_; }
59
60 private:
61 std::unique_ptr<base::Timer> CreateTimer() override {
62 bool retain_user_task = false;
63 bool is_repeating = false;
64 mock_timer_ = new base::MockTimer(retain_user_task, is_repeating);
65 return base::WrapUnique(mock_timer_);
66 }
67
68 // A timer instance for testing. Owned by the parent scheduler.
69 base::MockTimer* mock_timer_;
70
71 DISALLOW_COPY_AND_ASSIGN(TestSyncSchedulerImpl);
72 };
73
74 } // namespace
75
76 class ProximityAuthSyncSchedulerImplTest : public testing::Test,
77 public SyncSchedulerImpl::Delegate {
78 protected:
79 ProximityAuthSyncSchedulerImplTest()
80 : refresh_period_(base::TimeDelta::FromDays(kRefreshPeriodDays)),
81 base_recovery_period_(
82 base::TimeDelta::FromSeconds(kRecoveryPeriodSeconds)),
83 zero_elapsed_time_(base::TimeDelta::FromSeconds(0)),
84 scheduler_(new TestSyncSchedulerImpl(this,
85 refresh_period_,
86 base_recovery_period_,
87 0)) {}
88
89 ~ProximityAuthSyncSchedulerImplTest() override {}
90
91 void OnSyncRequested(
92 std::unique_ptr<SyncScheduler::SyncRequest> sync_request) override {
93 sync_request_ = std::move(sync_request);
94 }
95
96 base::MockTimer* timer() { return scheduler_->timer(); }
97
98 // The time deltas used to configure |scheduler_|.
99 base::TimeDelta refresh_period_;
100 base::TimeDelta base_recovery_period_;
101 base::TimeDelta zero_elapsed_time_;
102
103 // The scheduler instance under test.
104 std::unique_ptr<TestSyncSchedulerImpl> scheduler_;
105
106 std::unique_ptr<SyncScheduler::SyncRequest> sync_request_;
107
108 DISALLOW_COPY_AND_ASSIGN(ProximityAuthSyncSchedulerImplTest);
109 };
110
111 TEST_F(ProximityAuthSyncSchedulerImplTest, ForceSyncSuccess) {
112 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
113 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
114 EXPECT_EQ(SyncState::WAITING_FOR_REFRESH, scheduler_->GetSyncState());
115
116 scheduler_->ForceSync();
117 EXPECT_EQ(SyncState::SYNC_IN_PROGRESS, scheduler_->GetSyncState());
118 EXPECT_TRUE(sync_request_);
119 sync_request_->OnDidComplete(true);
120 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
121 EXPECT_EQ(SyncState::WAITING_FOR_REFRESH, scheduler_->GetSyncState());
122 }
123
124 TEST_F(ProximityAuthSyncSchedulerImplTest, ForceSyncFailure) {
125 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
126 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
127
128 scheduler_->ForceSync();
129 EXPECT_TRUE(sync_request_);
130 sync_request_->OnDidComplete(false);
131 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
132 }
133
134 TEST_F(ProximityAuthSyncSchedulerImplTest, PeriodicRefreshSuccess) {
135 EXPECT_EQ(SyncState::NOT_STARTED, scheduler_->GetSyncState());
136 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
137 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
138
139 EXPECT_EQ(refresh_period_, timer()->GetCurrentDelay());
140 timer()->Fire();
141 EXPECT_EQ(SyncState::SYNC_IN_PROGRESS, scheduler_->GetSyncState());
142 ASSERT_TRUE(sync_request_.get());
143
144 sync_request_->OnDidComplete(true);
145 EXPECT_EQ(SyncState::WAITING_FOR_REFRESH, scheduler_->GetSyncState());
146 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
147 }
148
149 TEST_F(ProximityAuthSyncSchedulerImplTest, PeriodicRefreshFailure) {
150 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
151 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
152 timer()->Fire();
153 sync_request_->OnDidComplete(false);
154 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
155 }
156
157 TEST_F(ProximityAuthSyncSchedulerImplTest, AggressiveRecoverySuccess) {
158 scheduler_->Start(zero_elapsed_time_, Strategy::AGGRESSIVE_RECOVERY);
159 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
160
161 EXPECT_EQ(base_recovery_period_, timer()->GetCurrentDelay());
162 timer()->Fire();
163 EXPECT_EQ(SyncState::SYNC_IN_PROGRESS, scheduler_->GetSyncState());
164 ASSERT_TRUE(sync_request_.get());
165
166 sync_request_->OnDidComplete(true);
167 EXPECT_EQ(SyncState::WAITING_FOR_REFRESH, scheduler_->GetSyncState());
168 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
169 }
170
171 TEST_F(ProximityAuthSyncSchedulerImplTest, AggressiveRecoveryFailure) {
172 scheduler_->Start(zero_elapsed_time_, Strategy::AGGRESSIVE_RECOVERY);
173
174 timer()->Fire();
175 sync_request_->OnDidComplete(false);
176 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
177 }
178
179 TEST_F(ProximityAuthSyncSchedulerImplTest, AggressiveRecoveryBackOff) {
180 scheduler_->Start(zero_elapsed_time_, Strategy::AGGRESSIVE_RECOVERY);
181 base::TimeDelta last_recovery_period = base::TimeDelta::FromSeconds(0);
182
183 for (int i = 0; i < 20; ++i) {
184 timer()->Fire();
185 EXPECT_EQ(SyncState::SYNC_IN_PROGRESS, scheduler_->GetSyncState());
186 sync_request_->OnDidComplete(false);
187 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
188 EXPECT_EQ(SyncState::WAITING_FOR_REFRESH, scheduler_->GetSyncState());
189
190 base::TimeDelta recovery_period = scheduler_->GetTimeToNextSync();
191 EXPECT_LE(last_recovery_period, recovery_period);
192 last_recovery_period = recovery_period;
193 }
194
195 // Backoffs should rapidly converge to the normal refresh period.
196 EXPECT_EQ(refresh_period_, last_recovery_period);
197 }
198
199 TEST_F(ProximityAuthSyncSchedulerImplTest, RefreshFailureRecoverySuccess) {
200 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
201 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
202
203 timer()->Fire();
204 sync_request_->OnDidComplete(false);
205 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
206
207 timer()->Fire();
208 sync_request_->OnDidComplete(true);
209 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
210 }
211
212 TEST_F(ProximityAuthSyncSchedulerImplTest, SyncImmediatelyForPeriodicRefresh) {
213 scheduler_->Start(base::TimeDelta::FromDays(kElapsedTimeDays),
214 Strategy::PERIODIC_REFRESH);
215 EXPECT_TRUE(scheduler_->GetTimeToNextSync().is_zero());
216 EXPECT_TRUE(timer()->GetCurrentDelay().is_zero());
217 timer()->Fire();
218 EXPECT_TRUE(sync_request_);
219
220 EXPECT_EQ(Strategy::PERIODIC_REFRESH, scheduler_->GetStrategy());
221 }
222
223 TEST_F(ProximityAuthSyncSchedulerImplTest,
224 SyncImmediatelyForAggressiveRecovery) {
225 scheduler_->Start(base::TimeDelta::FromDays(kElapsedTimeDays),
226 Strategy::AGGRESSIVE_RECOVERY);
227 EXPECT_TRUE(scheduler_->GetTimeToNextSync().is_zero());
228 EXPECT_TRUE(timer()->GetCurrentDelay().is_zero());
229 timer()->Fire();
230 EXPECT_TRUE(sync_request_);
231
232 EXPECT_EQ(Strategy::AGGRESSIVE_RECOVERY, scheduler_->GetStrategy());
233 }
234
235 TEST_F(ProximityAuthSyncSchedulerImplTest, InitialSyncShorterByElapsedTime) {
236 base::TimeDelta elapsed_time = base::TimeDelta::FromDays(2);
237 scheduler_->Start(elapsed_time, Strategy::PERIODIC_REFRESH);
238 EXPECT_EQ(refresh_period_ - elapsed_time, scheduler_->GetTimeToNextSync());
239 timer()->Fire();
240 EXPECT_TRUE(sync_request_);
241 }
242
243 TEST_F(ProximityAuthSyncSchedulerImplTest, PeriodicRefreshJitter) {
244 scheduler_.reset(new TestSyncSchedulerImpl(
245 this, refresh_period_, base_recovery_period_, kMaxJitterPercentage));
246
247 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
248
249 base::TimeDelta cumulative_jitter = base::TimeDelta::FromSeconds(0);
250 for (int i = 0; i < 10; ++i) {
251 base::TimeDelta next_sync_delta = scheduler_->GetTimeToNextSync();
252 cumulative_jitter += (next_sync_delta - refresh_period_).magnitude();
253 EXPECT_TRUE(IsTimeDeltaWithinJitter(refresh_period_, next_sync_delta,
254 kMaxJitterPercentage));
255 timer()->Fire();
256 sync_request_->OnDidComplete(true);
257 }
258
259 // The probablility that all periods are randomly equal to |refresh_period_|
260 // is so low that we would expect the heat death of the universe before this
261 // test flakes.
262 EXPECT_FALSE(cumulative_jitter.is_zero());
263 }
264
265 TEST_F(ProximityAuthSyncSchedulerImplTest, JitteredTimeDeltaIsNonNegative) {
266 base::TimeDelta zero_delta = base::TimeDelta::FromSeconds(0);
267 double max_jitter_ratio = 1;
268 scheduler_.reset(new TestSyncSchedulerImpl(this, zero_delta, zero_delta,
269 max_jitter_ratio));
270 scheduler_->Start(zero_elapsed_time_, Strategy::PERIODIC_REFRESH);
271
272 for (int i = 0; i < 10; ++i) {
273 base::TimeDelta next_sync_delta = scheduler_->GetTimeToNextSync();
274 EXPECT_GE(zero_delta, next_sync_delta);
275 EXPECT_TRUE(
276 IsTimeDeltaWithinJitter(zero_delta, next_sync_delta, max_jitter_ratio));
277 timer()->Fire();
278 sync_request_->OnDidComplete(true);
279 }
280 }
281
282 TEST_F(ProximityAuthSyncSchedulerImplTest, StartWithNegativeElapsedTime) {
283 // This could happen in rare cases where the system clock changes.
284 scheduler_->Start(base::TimeDelta::FromDays(-1000),
285 Strategy::PERIODIC_REFRESH);
286
287 base::TimeDelta zero_delta = base::TimeDelta::FromSeconds(0);
288 EXPECT_EQ(zero_delta, scheduler_->GetTimeToNextSync());
289 EXPECT_EQ(zero_delta, timer()->GetCurrentDelay());
290 }
291
292 } // namespace proximity_auth
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698