OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // This file tests the chrome.alarms extension API. | 5 // This file tests the chrome.alarms extension API. |
6 | 6 |
7 #include "base/values.h" | 7 #include "base/values.h" |
| 8 #include "base/test/mock_time_provider.h" |
8 #include "chrome/browser/browser_process_impl.h" | 9 #include "chrome/browser/browser_process_impl.h" |
9 #include "chrome/browser/extensions/api/alarms/alarm_manager.h" | 10 #include "chrome/browser/extensions/api/alarms/alarm_manager.h" |
10 #include "chrome/browser/extensions/api/alarms/alarms_api.h" | 11 #include "chrome/browser/extensions/api/alarms/alarms_api.h" |
11 #include "chrome/browser/extensions/extension_function_test_utils.h" | 12 #include "chrome/browser/extensions/extension_function_test_utils.h" |
12 #include "chrome/browser/extensions/test_extension_system.h" | 13 #include "chrome/browser/extensions/test_extension_system.h" |
13 #include "chrome/browser/profiles/profile_manager.h" | 14 #include "chrome/browser/profiles/profile_manager.h" |
14 #include "chrome/test/base/browser_with_test_window_test.h" | 15 #include "chrome/test/base/browser_with_test_window_test.h" |
15 #include "chrome/test/base/testing_browser_process.h" | 16 #include "chrome/test/base/testing_browser_process.h" |
| 17 #include "testing/gmock/include/gmock/gmock.h" |
16 #include "testing/gtest/include/gtest/gtest.h" | 18 #include "testing/gtest/include/gtest/gtest.h" |
17 | 19 |
| 20 typedef extensions::api::alarms::Alarm JsAlarm; |
| 21 |
18 namespace utils = extension_function_test_utils; | 22 namespace utils = extension_function_test_utils; |
19 | 23 |
20 namespace extensions { | 24 namespace extensions { |
21 | 25 |
22 namespace { | 26 namespace { |
23 | 27 |
24 // Test delegate which quits the message loop when an alarm fires. | 28 // Test delegate which quits the message loop when an alarm fires. |
25 class AlarmDelegate : public AlarmManager::Delegate { | 29 class AlarmDelegate : public AlarmManager::Delegate { |
26 public: | 30 public: |
27 virtual ~AlarmDelegate() {} | 31 virtual ~AlarmDelegate() {} |
28 virtual void OnAlarm(const std::string& extension_id, | 32 virtual void OnAlarm(const std::string& extension_id, |
29 const AlarmManager::Alarm& alarm) { | 33 const Alarm& alarm) { |
30 alarms_seen.push_back(alarm.name); | 34 alarms_seen.push_back(alarm.js_alarm->name); |
31 MessageLoop::current()->Quit(); | 35 MessageLoop::current()->Quit(); |
32 } | 36 } |
33 | 37 |
34 std::vector<std::string> alarms_seen; | 38 std::vector<std::string> alarms_seen; |
35 }; | 39 }; |
36 | 40 |
37 } // namespace | 41 } // namespace |
38 | 42 |
39 class ExtensionAlarmsTest : public BrowserWithTestWindowTest { | 43 class ExtensionAlarmsTest : public BrowserWithTestWindowTest { |
40 public: | 44 public: |
41 virtual void SetUp() { | 45 virtual void SetUp() { |
42 BrowserWithTestWindowTest::SetUp(); | 46 BrowserWithTestWindowTest::SetUp(); |
43 | 47 |
44 TestExtensionSystem* system = static_cast<TestExtensionSystem*>( | 48 TestExtensionSystem* system = static_cast<TestExtensionSystem*>( |
45 ExtensionSystem::Get(browser()->profile())); | 49 ExtensionSystem::Get(browser()->profile())); |
46 system->CreateAlarmManager(); | 50 system->CreateAlarmManager(&base::MockTimeProvider::StaticNow); |
47 alarm_manager_ = system->alarm_manager(); | 51 alarm_manager_ = system->alarm_manager(); |
48 | 52 |
49 alarm_delegate_ = new AlarmDelegate(); | 53 alarm_delegate_ = new AlarmDelegate(); |
50 alarm_manager_->set_delegate(alarm_delegate_); | 54 alarm_manager_->set_delegate(alarm_delegate_); |
51 | 55 |
52 extension_ = utils::CreateEmptyExtensionWithLocation( | 56 extension_ = utils::CreateEmptyExtensionWithLocation( |
53 extensions::Extension::LOAD); | 57 extensions::Extension::LOAD); |
| 58 |
| 59 current_time_ = base::Time::FromDoubleT(10); |
| 60 ON_CALL(mock_time_, Now()) |
| 61 .WillByDefault(testing::ReturnPointee(¤t_time_)); |
54 } | 62 } |
55 | 63 |
56 base::Value* RunFunctionWithExtension( | 64 base::Value* RunFunctionWithExtension( |
57 UIThreadExtensionFunction* function, const std::string& args) { | 65 UIThreadExtensionFunction* function, const std::string& args) { |
58 function->set_extension(extension_.get()); | 66 function->set_extension(extension_.get()); |
59 return utils::RunFunctionAndReturnResult(function, args, browser()); | 67 return utils::RunFunctionAndReturnResult(function, args, browser()); |
60 } | 68 } |
61 | 69 |
62 base::DictionaryValue* RunFunctionAndReturnDict( | 70 base::DictionaryValue* RunFunctionAndReturnDict( |
63 UIThreadExtensionFunction* function, const std::string& args) { | 71 UIThreadExtensionFunction* function, const std::string& args) { |
(...skipping 11 matching lines...) Expand all Loading... |
75 const std::string& args) { | 83 const std::string& args) { |
76 scoped_ptr<base::Value> result(RunFunctionWithExtension(function, args)); | 84 scoped_ptr<base::Value> result(RunFunctionWithExtension(function, args)); |
77 } | 85 } |
78 | 86 |
79 std::string RunFunctionAndReturnError(UIThreadExtensionFunction* function, | 87 std::string RunFunctionAndReturnError(UIThreadExtensionFunction* function, |
80 const std::string& args) { | 88 const std::string& args) { |
81 function->set_extension(extension_.get()); | 89 function->set_extension(extension_.get()); |
82 return utils::RunFunctionAndReturnError(function, args, browser()); | 90 return utils::RunFunctionAndReturnError(function, args, browser()); |
83 } | 91 } |
84 | 92 |
| 93 void CreateAlarm(const std::string& args) { |
| 94 RunFunction(new AlarmsCreateFunction(&base::MockTimeProvider::StaticNow), |
| 95 args); |
| 96 } |
| 97 |
85 // Takes a JSON result from a function and converts it to a vector of | 98 // Takes a JSON result from a function and converts it to a vector of |
86 // Alarms. | 99 // JsAlarms. |
87 AlarmManager::AlarmList ToAlarmList(base::ListValue* value) { | 100 std::vector<linked_ptr<JsAlarm> > ToAlarmList(base::ListValue* value) { |
88 AlarmManager::AlarmList list; | 101 std::vector<linked_ptr<JsAlarm> > list; |
89 for (size_t i = 0; i < value->GetSize(); ++i) { | 102 for (size_t i = 0; i < value->GetSize(); ++i) { |
90 linked_ptr<AlarmManager::Alarm> alarm(new AlarmManager::Alarm); | 103 linked_ptr<JsAlarm> alarm(new JsAlarm); |
91 base::DictionaryValue* alarm_value; | 104 base::DictionaryValue* alarm_value; |
92 if (!value->GetDictionary(i, &alarm_value)) { | 105 if (!value->GetDictionary(i, &alarm_value)) { |
93 ADD_FAILURE() << "Expected a list of Alarm objects."; | 106 ADD_FAILURE() << "Expected a list of Alarm objects."; |
94 return list; | 107 return list; |
95 } | 108 } |
96 EXPECT_TRUE(AlarmManager::Alarm::Populate(*alarm_value, alarm.get())); | 109 EXPECT_TRUE(JsAlarm::Populate(*alarm_value, alarm.get())); |
97 list.push_back(alarm); | 110 list.push_back(alarm); |
98 } | 111 } |
99 return list; | 112 return list; |
100 } | 113 } |
101 | 114 |
102 // Creates up to 3 alarms using the extension API. | 115 // Creates up to 3 alarms using the extension API. |
103 void CreateAlarms(size_t num_alarms) { | 116 void CreateAlarms(size_t num_alarms) { |
104 CHECK(num_alarms <= 3); | 117 CHECK(num_alarms <= 3); |
105 | 118 |
106 const char* kCreateArgs[] = { | 119 const char* kCreateArgs[] = { |
107 "[null, {\"delayInMinutes\": 0.001, \"repeating\": true}]", | 120 "[null, {\"delayInMinutes\": 0.001, \"repeating\": true}]", |
108 "[\"7\", {\"delayInMinutes\": 7, \"repeating\": true}]", | 121 "[\"7\", {\"delayInMinutes\": 7, \"repeating\": true}]", |
109 "[\"0\", {\"delayInMinutes\": 0}]" | 122 "[\"0\", {\"delayInMinutes\": 0}]" |
110 }; | 123 }; |
111 for (size_t i = 0; i < num_alarms; ++i) { | 124 for (size_t i = 0; i < num_alarms; ++i) { |
112 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( | 125 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( |
113 new AlarmsCreateFunction(), kCreateArgs[i])); | 126 new AlarmsCreateFunction(&base::MockTimeProvider::StaticNow), |
| 127 kCreateArgs[i])); |
114 EXPECT_FALSE(result.get()); | 128 EXPECT_FALSE(result.get()); |
115 } | 129 } |
116 } | 130 } |
117 | 131 |
118 protected: | 132 protected: |
| 133 base::Time current_time_; |
| 134 testing::NiceMock<base::MockTimeProvider> mock_time_; |
119 AlarmManager* alarm_manager_; | 135 AlarmManager* alarm_manager_; |
120 AlarmDelegate* alarm_delegate_; | 136 AlarmDelegate* alarm_delegate_; |
121 scoped_refptr<extensions::Extension> extension_; | 137 scoped_refptr<extensions::Extension> extension_; |
122 }; | 138 }; |
123 | 139 |
124 TEST_F(ExtensionAlarmsTest, Create) { | 140 TEST_F(ExtensionAlarmsTest, Create) { |
| 141 current_time_ = base::Time::FromDoubleT(10); |
125 // Create 1 non-repeating alarm. | 142 // Create 1 non-repeating alarm. |
126 RunFunction(new AlarmsCreateFunction(), "[null, {\"delayInMinutes\": 0}]"); | 143 CreateAlarm("[null, {\"delayInMinutes\": 0}]"); |
127 | 144 |
128 const AlarmManager::Alarm* alarm = | 145 const Alarm* alarm = |
129 alarm_manager_->GetAlarm(extension_->id(), ""); | 146 alarm_manager_->GetAlarm(extension_->id(), ""); |
130 ASSERT_TRUE(alarm); | 147 ASSERT_TRUE(alarm); |
131 EXPECT_EQ("", alarm->name); | 148 EXPECT_EQ("", alarm->js_alarm->name); |
132 EXPECT_EQ(0, alarm->delay_in_minutes); | 149 EXPECT_DOUBLE_EQ(10000, alarm->js_alarm->scheduled_time); |
133 EXPECT_FALSE(alarm->repeating); | 150 EXPECT_FALSE(alarm->js_alarm->repeat_after_minutes.get()); |
134 | 151 |
135 // Now wait for the alarm to fire. Our test delegate will quit the | 152 // Now wait for the alarm to fire. Our test delegate will quit the |
136 // MessageLoop when that happens. | 153 // MessageLoop when that happens. |
137 MessageLoop::current()->Run(); | 154 MessageLoop::current()->Run(); |
138 | 155 |
139 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); | 156 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); |
140 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); | 157 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); |
141 | 158 |
142 // Ensure the alarm is gone. | 159 // Ensure the alarm is gone. |
143 { | 160 { |
144 const AlarmManager::AlarmList* alarms = | 161 const AlarmManager::AlarmList* alarms = |
145 alarm_manager_->GetAllAlarms(extension_->id()); | 162 alarm_manager_->GetAllAlarms(extension_->id()); |
146 ASSERT_FALSE(alarms); | 163 ASSERT_FALSE(alarms); |
147 } | 164 } |
148 } | 165 } |
149 | 166 |
150 TEST_F(ExtensionAlarmsTest, CreateRepeating) { | 167 TEST_F(ExtensionAlarmsTest, CreateRepeating) { |
| 168 current_time_ = base::Time::FromDoubleT(10); |
| 169 |
151 // Create 1 repeating alarm. | 170 // Create 1 repeating alarm. |
152 RunFunction(new AlarmsCreateFunction(), | 171 CreateAlarm("[null, {\"delayInMinutes\": 0.001, \"repeating\": true}]"); |
153 "[null, {\"delayInMinutes\": 0.001, \"repeating\": true}]"); | |
154 | 172 |
155 const AlarmManager::Alarm* alarm = | 173 const Alarm* alarm = |
156 alarm_manager_->GetAlarm(extension_->id(), ""); | 174 alarm_manager_->GetAlarm(extension_->id(), ""); |
157 ASSERT_TRUE(alarm); | 175 ASSERT_TRUE(alarm); |
158 EXPECT_EQ("", alarm->name); | 176 EXPECT_EQ("", alarm->js_alarm->name); |
159 EXPECT_EQ(0.001, alarm->delay_in_minutes); | 177 EXPECT_DOUBLE_EQ(10060, alarm->js_alarm->scheduled_time); |
160 EXPECT_TRUE(alarm->repeating); | 178 EXPECT_THAT(alarm->js_alarm->repeat_after_minutes, |
| 179 testing::Pointee(testing::DoubleEq(0.001))); |
161 | 180 |
| 181 current_time_ += base::TimeDelta::FromSeconds(1); |
162 // Now wait for the alarm to fire. Our test delegate will quit the | 182 // Now wait for the alarm to fire. Our test delegate will quit the |
163 // MessageLoop when that happens. | 183 // MessageLoop when that happens. |
164 MessageLoop::current()->Run(); | 184 MessageLoop::current()->Run(); |
165 | 185 |
| 186 current_time_ += base::TimeDelta::FromSeconds(1); |
166 // Wait again, and ensure the alarm fires again. | 187 // Wait again, and ensure the alarm fires again. |
167 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); | 188 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); |
168 MessageLoop::current()->Run(); | 189 MessageLoop::current()->Run(); |
169 | 190 |
170 ASSERT_EQ(2u, alarm_delegate_->alarms_seen.size()); | 191 ASSERT_EQ(2u, alarm_delegate_->alarms_seen.size()); |
171 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); | 192 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); |
172 } | 193 } |
173 | 194 |
| 195 TEST_F(ExtensionAlarmsTest, CreateAbsolute) { |
| 196 current_time_ = base::Time::FromDoubleT(9.99); |
| 197 CreateAlarm("[null, {\"approxTimeToFire\": 10001}]"); |
| 198 |
| 199 const Alarm* alarm = |
| 200 alarm_manager_->GetAlarm(extension_->id(), ""); |
| 201 ASSERT_TRUE(alarm); |
| 202 EXPECT_EQ("", alarm->js_alarm->name); |
| 203 EXPECT_DOUBLE_EQ(10001, alarm->js_alarm->scheduled_time); |
| 204 EXPECT_THAT(alarm->js_alarm->repeat_after_minutes, |
| 205 testing::IsNull()); |
| 206 |
| 207 current_time_ = base::Time::FromDoubleT(10.1); |
| 208 // Now wait for the alarm to fire. Our test delegate will quit the |
| 209 // MessageLoop when that happens. |
| 210 MessageLoop::current()->Run(); |
| 211 |
| 212 ASSERT_FALSE(alarm_manager_->GetAlarm(extension_->id(), "")); |
| 213 |
| 214 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); |
| 215 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); |
| 216 } |
| 217 |
174 TEST_F(ExtensionAlarmsTest, CreateDupe) { | 218 TEST_F(ExtensionAlarmsTest, CreateDupe) { |
| 219 current_time_ = base::Time::FromDoubleT(10); |
| 220 |
175 // Create 2 duplicate alarms. The first should be overridden. | 221 // Create 2 duplicate alarms. The first should be overridden. |
176 RunFunction(new AlarmsCreateFunction(), "[\"dup\", {\"delayInMinutes\": 1}]"); | 222 CreateAlarm("[\"dup\", {\"delayInMinutes\": 1}]"); |
177 RunFunction(new AlarmsCreateFunction(), "[\"dup\", {\"delayInMinutes\": 7}]"); | 223 CreateAlarm("[\"dup\", {\"delayInMinutes\": 7}]"); |
178 | 224 |
179 { | 225 { |
180 const AlarmManager::AlarmList* alarms = | 226 const AlarmManager::AlarmList* alarms = |
181 alarm_manager_->GetAllAlarms(extension_->id()); | 227 alarm_manager_->GetAllAlarms(extension_->id()); |
182 ASSERT_TRUE(alarms); | 228 ASSERT_TRUE(alarms); |
183 EXPECT_EQ(1u, alarms->size()); | 229 EXPECT_EQ(1u, alarms->size()); |
184 EXPECT_EQ(7, (*alarms)[0]->delay_in_minutes); | 230 EXPECT_DOUBLE_EQ(430000, (*alarms)[0].js_alarm->scheduled_time); |
185 } | 231 } |
186 } | 232 } |
187 | 233 |
188 TEST_F(ExtensionAlarmsTest, CreateDelayBelowMinimum) { | 234 TEST_F(ExtensionAlarmsTest, CreateDelayBelowMinimum) { |
189 // Create an alarm with delay below the minimum accepted value. | 235 // Create an alarm with delay below the minimum accepted value. |
190 std::string error = RunFunctionAndReturnError(new AlarmsCreateFunction(), | 236 std::string error = RunFunctionAndReturnError( |
| 237 new AlarmsCreateFunction(&base::MockTimeProvider::StaticNow), |
191 "[\"negative\", {\"delayInMinutes\": -0.2}]"); | 238 "[\"negative\", {\"delayInMinutes\": -0.2}]"); |
192 EXPECT_FALSE(error.empty()); | 239 EXPECT_FALSE(error.empty()); |
193 } | 240 } |
194 | 241 |
195 TEST_F(ExtensionAlarmsTest, Get) { | 242 TEST_F(ExtensionAlarmsTest, Get) { |
| 243 current_time_ = base::Time::FromDoubleT(4); |
| 244 |
196 // Create 2 alarms, and make sure we can query them. | 245 // Create 2 alarms, and make sure we can query them. |
197 CreateAlarms(2); | 246 CreateAlarms(2); |
198 | 247 |
199 // Get the default one. | 248 // Get the default one. |
200 { | 249 { |
201 AlarmManager::Alarm alarm; | 250 JsAlarm alarm; |
202 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( | 251 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( |
203 new AlarmsGetFunction(), "[null]")); | 252 new AlarmsGetFunction(), "[null]")); |
204 ASSERT_TRUE(result.get()); | 253 ASSERT_TRUE(result.get()); |
205 EXPECT_TRUE(AlarmManager::Alarm::Populate(*result, &alarm)); | 254 EXPECT_TRUE(JsAlarm::Populate(*result, &alarm)); |
206 EXPECT_EQ("", alarm.name); | 255 EXPECT_EQ("", alarm.name); |
207 EXPECT_EQ(0.001, alarm.delay_in_minutes); | 256 EXPECT_DOUBLE_EQ(4060, alarm.scheduled_time); |
208 EXPECT_TRUE(alarm.repeating); | 257 EXPECT_THAT(alarm.repeat_after_minutes, |
| 258 testing::Pointee(testing::DoubleEq(0.001))); |
209 } | 259 } |
210 | 260 |
211 // Get "7". | 261 // Get "7". |
212 { | 262 { |
213 AlarmManager::Alarm alarm; | 263 JsAlarm alarm; |
214 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( | 264 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( |
215 new AlarmsGetFunction(), "[\"7\"]")); | 265 new AlarmsGetFunction(), "[\"7\"]")); |
216 ASSERT_TRUE(result.get()); | 266 ASSERT_TRUE(result.get()); |
217 EXPECT_TRUE(AlarmManager::Alarm::Populate(*result, &alarm)); | 267 EXPECT_TRUE(JsAlarm::Populate(*result, &alarm)); |
218 EXPECT_EQ("7", alarm.name); | 268 EXPECT_EQ("7", alarm.name); |
219 EXPECT_EQ(7, alarm.delay_in_minutes); | 269 EXPECT_EQ(424000, alarm.scheduled_time); |
220 EXPECT_TRUE(alarm.repeating); | 270 EXPECT_THAT(alarm.repeat_after_minutes, testing::Pointee(7)); |
221 } | 271 } |
222 | 272 |
223 // Get a non-existent one. | 273 // Get a non-existent one. |
224 { | 274 { |
225 std::string error = RunFunctionAndReturnError( | 275 std::string error = RunFunctionAndReturnError( |
226 new AlarmsGetFunction(), "[\"nobody\"]"); | 276 new AlarmsGetFunction(), "[\"nobody\"]"); |
227 EXPECT_FALSE(error.empty()); | 277 EXPECT_FALSE(error.empty()); |
228 } | 278 } |
229 } | 279 } |
230 | 280 |
231 TEST_F(ExtensionAlarmsTest, GetAll) { | 281 TEST_F(ExtensionAlarmsTest, GetAll) { |
232 // Test getAll with 0 alarms. | 282 // Test getAll with 0 alarms. |
233 { | 283 { |
234 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( | 284 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( |
235 new AlarmsGetAllFunction(), "[]")); | 285 new AlarmsGetAllFunction(), "[]")); |
236 AlarmManager::AlarmList alarms = ToAlarmList(result.get()); | 286 std::vector<linked_ptr<JsAlarm> > alarms = ToAlarmList(result.get()); |
237 EXPECT_EQ(0u, alarms.size()); | 287 EXPECT_EQ(0u, alarms.size()); |
238 } | 288 } |
239 | 289 |
240 // Create 2 alarms, and make sure we can query them. | 290 // Create 2 alarms, and make sure we can query them. |
241 CreateAlarms(2); | 291 CreateAlarms(2); |
242 | 292 |
243 { | 293 { |
244 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( | 294 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( |
245 new AlarmsGetAllFunction(), "[null]")); | 295 new AlarmsGetAllFunction(), "[null]")); |
246 AlarmManager::AlarmList alarms = ToAlarmList(result.get()); | 296 std::vector<linked_ptr<JsAlarm> > alarms = ToAlarmList(result.get()); |
247 EXPECT_EQ(2u, alarms.size()); | 297 EXPECT_EQ(2u, alarms.size()); |
248 | 298 |
249 // Test the "7" alarm. | 299 // Test the "7" alarm. |
250 AlarmManager::Alarm* alarm = alarms[0].get(); | 300 JsAlarm* alarm = alarms[0].get(); |
251 if (alarm->name != "7") | 301 if (alarm->name != "7") |
252 alarm = alarms[1].get(); | 302 alarm = alarms[1].get(); |
253 EXPECT_EQ("7", alarm->name); | 303 EXPECT_EQ("7", alarm->name); |
254 EXPECT_EQ(7, alarm->delay_in_minutes); | 304 EXPECT_THAT(alarm->repeat_after_minutes, testing::Pointee(7)); |
255 EXPECT_TRUE(alarm->repeating); | |
256 } | 305 } |
257 } | 306 } |
258 | 307 |
259 TEST_F(ExtensionAlarmsTest, Clear) { | 308 TEST_F(ExtensionAlarmsTest, Clear) { |
260 // Clear a non-existent one. | 309 // Clear a non-existent one. |
261 { | 310 { |
262 std::string error = RunFunctionAndReturnError( | 311 std::string error = RunFunctionAndReturnError( |
263 new AlarmsClearFunction(), "[\"nobody\"]"); | 312 new AlarmsClearFunction(), "[\"nobody\"]"); |
264 EXPECT_FALSE(error.empty()); | 313 EXPECT_FALSE(error.empty()); |
265 } | 314 } |
266 | 315 |
267 // Create 3 alarms. | 316 // Create 3 alarms. |
268 CreateAlarms(3); | 317 CreateAlarms(3); |
269 | 318 |
270 // Clear all but the 0.001-minute alarm. | 319 // Clear all but the 0.001-minute alarm. |
271 { | 320 { |
272 RunFunction(new AlarmsClearFunction(), "[\"7\"]"); | 321 RunFunction(new AlarmsClearFunction(), "[\"7\"]"); |
273 RunFunction(new AlarmsClearFunction(), "[\"0\"]"); | 322 RunFunction(new AlarmsClearFunction(), "[\"0\"]"); |
274 | 323 |
275 const AlarmManager::AlarmList* alarms = | 324 const AlarmManager::AlarmList* alarms = |
276 alarm_manager_->GetAllAlarms(extension_->id()); | 325 alarm_manager_->GetAllAlarms(extension_->id()); |
277 ASSERT_TRUE(alarms); | 326 ASSERT_TRUE(alarms); |
278 EXPECT_EQ(1u, alarms->size()); | 327 EXPECT_EQ(1u, alarms->size()); |
279 EXPECT_EQ(0.001, (*alarms)[0]->delay_in_minutes); | 328 EXPECT_THAT((*alarms)[0].js_alarm->repeat_after_minutes, |
| 329 testing::Pointee(0.001)); |
280 } | 330 } |
281 | 331 |
282 // Now wait for the alarms to fire, and ensure the cancelled alarms don't | 332 // Now wait for the alarms to fire, and ensure the cancelled alarms don't |
283 // fire. | 333 // fire. |
284 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); | 334 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); |
285 MessageLoop::current()->Run(); | 335 MessageLoop::current()->Run(); |
286 | 336 |
287 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); | 337 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); |
288 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); | 338 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); |
289 | 339 |
290 // Ensure the 0.001-minute alarm is still there, since it's repeating. | 340 // Ensure the 0.001-minute alarm is still there, since it's repeating. |
291 { | 341 { |
292 const AlarmManager::AlarmList* alarms = | 342 const AlarmManager::AlarmList* alarms = |
293 alarm_manager_->GetAllAlarms(extension_->id()); | 343 alarm_manager_->GetAllAlarms(extension_->id()); |
294 ASSERT_TRUE(alarms); | 344 ASSERT_TRUE(alarms); |
295 EXPECT_EQ(1u, alarms->size()); | 345 EXPECT_EQ(1u, alarms->size()); |
296 EXPECT_EQ(0.001, (*alarms)[0]->delay_in_minutes); | 346 EXPECT_THAT((*alarms)[0].js_alarm->repeat_after_minutes, |
| 347 testing::Pointee(0.001)); |
297 } | 348 } |
298 } | 349 } |
299 | 350 |
300 TEST_F(ExtensionAlarmsTest, ClearAll) { | 351 TEST_F(ExtensionAlarmsTest, ClearAll) { |
301 // ClearAll with no alarms set. | 352 // ClearAll with no alarms set. |
302 { | 353 { |
303 scoped_ptr<base::Value> result(RunFunctionWithExtension( | 354 scoped_ptr<base::Value> result(RunFunctionWithExtension( |
304 new AlarmsClearAllFunction(), "[]")); | 355 new AlarmsClearAllFunction(), "[]")); |
305 EXPECT_FALSE(result.get()); | 356 EXPECT_FALSE(result.get()); |
306 } | 357 } |
(...skipping 13 matching lines...) Expand all Loading... |
320 const AlarmManager::AlarmList* alarms = | 371 const AlarmManager::AlarmList* alarms = |
321 alarm_manager_->GetAllAlarms(extension_->id()); | 372 alarm_manager_->GetAllAlarms(extension_->id()); |
322 ASSERT_FALSE(alarms); | 373 ASSERT_FALSE(alarms); |
323 } | 374 } |
324 } | 375 } |
325 | 376 |
326 class ExtensionAlarmsSchedulingTest : public ExtensionAlarmsTest { | 377 class ExtensionAlarmsSchedulingTest : public ExtensionAlarmsTest { |
327 public: | 378 public: |
328 // Get the time that the alarm named is scheduled to run. | 379 // Get the time that the alarm named is scheduled to run. |
329 base::Time GetScheduledTime(const std::string& alarm_name) { | 380 base::Time GetScheduledTime(const std::string& alarm_name) { |
330 const extensions::AlarmManager::Alarm* alarm = | 381 const extensions::Alarm* alarm = |
331 alarm_manager_->GetAlarm(extension_->id(), alarm_name); | 382 alarm_manager_->GetAlarm(extension_->id(), alarm_name); |
332 CHECK(alarm); | 383 CHECK(alarm); |
333 return alarm_manager_->scheduled_times_[alarm].time; | 384 return base::Time::FromJsTime(alarm->js_alarm->scheduled_time); |
334 } | 385 } |
335 }; | 386 }; |
336 | 387 |
337 TEST_F(ExtensionAlarmsSchedulingTest, PollScheduling) { | 388 TEST_F(ExtensionAlarmsSchedulingTest, PollScheduling) { |
338 { | 389 { |
339 RunFunction(new AlarmsCreateFunction(), | 390 CreateAlarm("[\"a\", {\"delayInMinutes\": 6, \"repeating\": true}]"); |
340 "[\"a\", {\"delayInMinutes\": 6, \"repeating\": true}]"); | 391 CreateAlarm("[\"bb\", {\"delayInMinutes\": 8, \"repeating\": true}]"); |
341 RunFunction(new AlarmsCreateFunction(), | |
342 "[\"bb\", {\"delayInMinutes\": 8, \"repeating\": true}]"); | |
343 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); | 392 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); |
344 alarm_manager_->RemoveAllAlarms(extension_->id()); | 393 alarm_manager_->RemoveAllAlarms(extension_->id()); |
345 } | 394 } |
346 { | 395 { |
347 RunFunction(new AlarmsCreateFunction(), | 396 CreateAlarm("[\"a\", {\"delayInMinutes\": 10}]"); |
348 "[\"a\", {\"delayInMinutes\": 10}]"); | 397 CreateAlarm("[\"bb\", {\"delayInMinutes\": 21}]"); |
349 RunFunction(new AlarmsCreateFunction(), | |
350 "[\"bb\", {\"delayInMinutes\": 21}]"); | |
351 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); | 398 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); |
352 alarm_manager_->RemoveAllAlarms(extension_->id()); | 399 alarm_manager_->RemoveAllAlarms(extension_->id()); |
353 } | 400 } |
354 { | 401 { |
355 RunFunction(new AlarmsCreateFunction(), | 402 current_time_ = base::Time::FromDoubleT(10); |
356 "[\"a\", {\"delayInMinutes\": 10, \"repeating\": true}]"); | 403 CreateAlarm("[\"a\", {\"delayInMinutes\": 10, \"repeating\": true}]"); |
357 linked_ptr<AlarmManager::Alarm> alarm(new AlarmManager::Alarm()); | 404 Alarm alarm; |
358 alarm->name = "bb"; | 405 alarm.js_alarm->name = "bb"; |
359 alarm->delay_in_minutes = 30; | 406 alarm.js_alarm->scheduled_time = 30 * 60000; |
360 alarm->repeating = true; | 407 alarm.js_alarm->repeat_after_minutes.reset(new double(30)); |
361 alarm_manager_->AddAlarmImpl(extension_->id(), alarm, | 408 alarm_manager_->AddAlarmImpl(extension_->id(), alarm); |
362 base::TimeDelta::FromMinutes(3)); | 409 EXPECT_DOUBLE_EQ(GetScheduledTime("a").ToDoubleT(), |
363 EXPECT_EQ(GetScheduledTime("bb"), alarm_manager_->next_poll_time_); | 410 alarm_manager_->next_poll_time_.ToDoubleT()); |
364 alarm_manager_->RemoveAllAlarms(extension_->id()); | 411 alarm_manager_->RemoveAllAlarms(extension_->id()); |
365 } | 412 } |
366 { | 413 { |
367 linked_ptr<AlarmManager::Alarm> alarm(new AlarmManager::Alarm()); | 414 current_time_ = base::Time::FromDoubleT(3 * 60 + 1); |
368 alarm->name = "bb"; | 415 Alarm alarm; |
369 alarm->delay_in_minutes = 3; | 416 alarm.js_alarm->name = "bb"; |
370 alarm->repeating = true; | 417 alarm.js_alarm->scheduled_time = 3 * 60000; |
371 alarm_manager_->AddAlarmImpl(extension_->id(), alarm, | 418 alarm.js_alarm->repeat_after_minutes.reset(new double(3)); |
372 base::TimeDelta::FromSeconds(0)); | 419 alarm_manager_->AddAlarmImpl(extension_->id(), alarm); |
373 MessageLoop::current()->Run(); | 420 MessageLoop::current()->Run(); |
374 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(3), | 421 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(3), |
375 alarm_manager_->next_poll_time_); | 422 alarm_manager_->next_poll_time_); |
376 alarm_manager_->RemoveAllAlarms(extension_->id()); | 423 alarm_manager_->RemoveAllAlarms(extension_->id()); |
377 } | 424 } |
378 { | 425 { |
379 RunFunction(new AlarmsCreateFunction(), | 426 current_time_ = base::Time::FromDoubleT(4 * 60 + 1); |
380 "[\"a\", {\"delayInMinutes\": 2, \"repeating\": true}]"); | 427 CreateAlarm("[\"a\", {\"delayInMinutes\": 2, \"repeating\": true}]"); |
381 alarm_manager_->RemoveAlarm(extension_->id(), "a"); | 428 alarm_manager_->RemoveAlarm(extension_->id(), "a"); |
382 linked_ptr<AlarmManager::Alarm> alarm2(new AlarmManager::Alarm()); | 429 Alarm alarm2; |
383 alarm2->name = "bb"; | 430 alarm2.js_alarm->name = "bb"; |
384 alarm2->delay_in_minutes = 4; | 431 alarm2.js_alarm->scheduled_time = 4 * 60000; |
385 alarm2->repeating = true; | 432 alarm2.js_alarm->repeat_after_minutes.reset(new double(4)); |
386 alarm_manager_->AddAlarmImpl(extension_->id(), alarm2, | 433 alarm_manager_->AddAlarmImpl(extension_->id(), alarm2); |
387 base::TimeDelta::FromMinutes(3)); | 434 Alarm alarm3; |
388 linked_ptr<AlarmManager::Alarm> alarm3(new AlarmManager::Alarm()); | 435 alarm3.js_alarm->name = "ccc"; |
389 alarm3->name = "ccc"; | 436 alarm3.js_alarm->scheduled_time = 25 * 60000; |
390 alarm3->delay_in_minutes = 25; | 437 alarm3.js_alarm->repeat_after_minutes.reset(new double(25)); |
391 alarm3->repeating = true; | 438 alarm_manager_->AddAlarmImpl(extension_->id(), alarm3); |
392 alarm_manager_->AddAlarmImpl(extension_->id(), alarm3, | |
393 base::TimeDelta::FromSeconds(0)); | |
394 MessageLoop::current()->Run(); | 439 MessageLoop::current()->Run(); |
395 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(4), | 440 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(4), |
396 alarm_manager_->next_poll_time_); | 441 alarm_manager_->next_poll_time_); |
397 alarm_manager_->RemoveAllAlarms(extension_->id()); | 442 alarm_manager_->RemoveAllAlarms(extension_->id()); |
398 } | 443 } |
399 } | 444 } |
400 | 445 |
| 446 TEST_F(ExtensionAlarmsSchedulingTest, ReleasedExtensionPollsInfrequently) { |
| 447 extension_ = utils::CreateEmptyExtensionWithLocation( |
| 448 extensions::Extension::INTERNAL); |
| 449 current_time_ = base::Time::FromJsTime(300000); |
| 450 CreateAlarm("[\"a\", {\"approxTimeToFire\": 300010}]"); |
| 451 CreateAlarm("[\"b\", {\"approxTimeToFire\": 360000}]"); |
| 452 |
| 453 // In released extensions, we set the granularity to at least 5 |
| 454 // minutes, but AddAlarm schedules its next poll precisely. |
| 455 EXPECT_DOUBLE_EQ(300010, alarm_manager_->next_poll_time_.ToJsTime()); |
| 456 |
| 457 // Run an iteration to see the effect of the granularity. |
| 458 current_time_ = base::Time::FromJsTime(300020); |
| 459 MessageLoop::current()->Run(); |
| 460 EXPECT_DOUBLE_EQ(300020, alarm_manager_->last_poll_time_.ToJsTime()); |
| 461 EXPECT_DOUBLE_EQ(600020, alarm_manager_->next_poll_time_.ToJsTime()); |
| 462 } |
| 463 |
401 TEST_F(ExtensionAlarmsSchedulingTest, TimerRunning) { | 464 TEST_F(ExtensionAlarmsSchedulingTest, TimerRunning) { |
402 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 465 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
403 RunFunction(new AlarmsCreateFunction(), | 466 CreateAlarm("[\"a\", {\"delayInMinutes\": 0.001}]"); |
404 "[\"a\", {\"delayInMinutes\": 0.001}]"); | |
405 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); | 467 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); |
406 MessageLoop::current()->Run(); | 468 MessageLoop::current()->Run(); |
407 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 469 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
408 RunFunction(new AlarmsCreateFunction(), | 470 CreateAlarm("[\"bb\", {\"delayInMinutes\": 10}]"); |
409 "[\"bb\", {\"delayInMinutes\": 10}]"); | |
410 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); | 471 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); |
411 alarm_manager_->RemoveAllAlarms(extension_->id()); | 472 alarm_manager_->RemoveAllAlarms(extension_->id()); |
412 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 473 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
413 } | 474 } |
414 | 475 |
415 } // namespace extensions | 476 } // namespace extensions |
OLD | NEW |