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, {\"periodInMinutes\": 0.001}]", |
108 "[\"7\", {\"delayInMinutes\": 7, \"repeating\": true}]", | 121 "[\"7\", {\"periodInMinutes\": 7}]", |
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->period_in_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, {\"periodInMinutes\": 0.001}]"); |
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->period_in_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, {\"when\": 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->period_in_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 |
| 218 TEST_F(ExtensionAlarmsTest, CreateRepeatingWithQuickFirstCall) { |
| 219 current_time_ = base::Time::FromDoubleT(9.99); |
| 220 CreateAlarm("[null, {\"when\": 10001, \"periodInMinutes\": 0.001}]"); |
| 221 |
| 222 const Alarm* alarm = |
| 223 alarm_manager_->GetAlarm(extension_->id(), ""); |
| 224 ASSERT_TRUE(alarm); |
| 225 EXPECT_EQ("", alarm->js_alarm->name); |
| 226 EXPECT_DOUBLE_EQ(10001, alarm->js_alarm->scheduled_time); |
| 227 EXPECT_THAT(alarm->js_alarm->period_in_minutes, |
| 228 testing::Pointee(testing::DoubleEq(0.001))); |
| 229 |
| 230 current_time_ = base::Time::FromDoubleT(10.1); |
| 231 // Now wait for the alarm to fire. Our test delegate will quit the |
| 232 // MessageLoop when that happens. |
| 233 MessageLoop::current()->Run(); |
| 234 |
| 235 ASSERT_TRUE(alarm_manager_->GetAlarm(extension_->id(), "")); |
| 236 EXPECT_THAT(alarm_delegate_->alarms_seen, testing::ElementsAre("")); |
| 237 |
| 238 current_time_ = base::Time::FromDoubleT(10.7); |
| 239 MessageLoop::current()->Run(); |
| 240 |
| 241 ASSERT_TRUE(alarm_manager_->GetAlarm(extension_->id(), "")); |
| 242 EXPECT_THAT(alarm_delegate_->alarms_seen, testing::ElementsAre("", "")); |
| 243 } |
| 244 |
174 TEST_F(ExtensionAlarmsTest, CreateDupe) { | 245 TEST_F(ExtensionAlarmsTest, CreateDupe) { |
| 246 current_time_ = base::Time::FromDoubleT(10); |
| 247 |
175 // Create 2 duplicate alarms. The first should be overridden. | 248 // Create 2 duplicate alarms. The first should be overridden. |
176 RunFunction(new AlarmsCreateFunction(), "[\"dup\", {\"delayInMinutes\": 1}]"); | 249 CreateAlarm("[\"dup\", {\"delayInMinutes\": 1}]"); |
177 RunFunction(new AlarmsCreateFunction(), "[\"dup\", {\"delayInMinutes\": 7}]"); | 250 CreateAlarm("[\"dup\", {\"delayInMinutes\": 7}]"); |
178 | 251 |
179 { | 252 { |
180 const AlarmManager::AlarmList* alarms = | 253 const AlarmManager::AlarmList* alarms = |
181 alarm_manager_->GetAllAlarms(extension_->id()); | 254 alarm_manager_->GetAllAlarms(extension_->id()); |
182 ASSERT_TRUE(alarms); | 255 ASSERT_TRUE(alarms); |
183 EXPECT_EQ(1u, alarms->size()); | 256 EXPECT_EQ(1u, alarms->size()); |
184 EXPECT_EQ(7, (*alarms)[0]->delay_in_minutes); | 257 EXPECT_DOUBLE_EQ(430000, (*alarms)[0].js_alarm->scheduled_time); |
185 } | 258 } |
186 } | 259 } |
187 | 260 |
188 TEST_F(ExtensionAlarmsTest, CreateDelayBelowMinimum) { | 261 TEST_F(ExtensionAlarmsTest, CreateDelayBelowMinimum) { |
189 // Create an alarm with delay below the minimum accepted value. | 262 // Create an alarm with delay below the minimum accepted value. |
190 std::string error = RunFunctionAndReturnError(new AlarmsCreateFunction(), | 263 std::string error = RunFunctionAndReturnError( |
| 264 new AlarmsCreateFunction(&base::MockTimeProvider::StaticNow), |
191 "[\"negative\", {\"delayInMinutes\": -0.2}]"); | 265 "[\"negative\", {\"delayInMinutes\": -0.2}]"); |
192 EXPECT_FALSE(error.empty()); | 266 EXPECT_FALSE(error.empty()); |
193 } | 267 } |
194 | 268 |
195 TEST_F(ExtensionAlarmsTest, Get) { | 269 TEST_F(ExtensionAlarmsTest, Get) { |
| 270 current_time_ = base::Time::FromDoubleT(4); |
| 271 |
196 // Create 2 alarms, and make sure we can query them. | 272 // Create 2 alarms, and make sure we can query them. |
197 CreateAlarms(2); | 273 CreateAlarms(2); |
198 | 274 |
199 // Get the default one. | 275 // Get the default one. |
200 { | 276 { |
201 AlarmManager::Alarm alarm; | 277 JsAlarm alarm; |
202 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( | 278 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( |
203 new AlarmsGetFunction(), "[null]")); | 279 new AlarmsGetFunction(), "[null]")); |
204 ASSERT_TRUE(result.get()); | 280 ASSERT_TRUE(result.get()); |
205 EXPECT_TRUE(AlarmManager::Alarm::Populate(*result, &alarm)); | 281 EXPECT_TRUE(JsAlarm::Populate(*result, &alarm)); |
206 EXPECT_EQ("", alarm.name); | 282 EXPECT_EQ("", alarm.name); |
207 EXPECT_EQ(0.001, alarm.delay_in_minutes); | 283 EXPECT_DOUBLE_EQ(4060, alarm.scheduled_time); |
208 EXPECT_TRUE(alarm.repeating); | 284 EXPECT_THAT(alarm.period_in_minutes, |
| 285 testing::Pointee(testing::DoubleEq(0.001))); |
209 } | 286 } |
210 | 287 |
211 // Get "7". | 288 // Get "7". |
212 { | 289 { |
213 AlarmManager::Alarm alarm; | 290 JsAlarm alarm; |
214 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( | 291 scoped_ptr<base::DictionaryValue> result(RunFunctionAndReturnDict( |
215 new AlarmsGetFunction(), "[\"7\"]")); | 292 new AlarmsGetFunction(), "[\"7\"]")); |
216 ASSERT_TRUE(result.get()); | 293 ASSERT_TRUE(result.get()); |
217 EXPECT_TRUE(AlarmManager::Alarm::Populate(*result, &alarm)); | 294 EXPECT_TRUE(JsAlarm::Populate(*result, &alarm)); |
218 EXPECT_EQ("7", alarm.name); | 295 EXPECT_EQ("7", alarm.name); |
219 EXPECT_EQ(7, alarm.delay_in_minutes); | 296 EXPECT_EQ(424000, alarm.scheduled_time); |
220 EXPECT_TRUE(alarm.repeating); | 297 EXPECT_THAT(alarm.period_in_minutes, testing::Pointee(7)); |
221 } | 298 } |
222 | 299 |
223 // Get a non-existent one. | 300 // Get a non-existent one. |
224 { | 301 { |
225 std::string error = RunFunctionAndReturnError( | 302 std::string error = RunFunctionAndReturnError( |
226 new AlarmsGetFunction(), "[\"nobody\"]"); | 303 new AlarmsGetFunction(), "[\"nobody\"]"); |
227 EXPECT_FALSE(error.empty()); | 304 EXPECT_FALSE(error.empty()); |
228 } | 305 } |
229 } | 306 } |
230 | 307 |
231 TEST_F(ExtensionAlarmsTest, GetAll) { | 308 TEST_F(ExtensionAlarmsTest, GetAll) { |
232 // Test getAll with 0 alarms. | 309 // Test getAll with 0 alarms. |
233 { | 310 { |
234 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( | 311 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( |
235 new AlarmsGetAllFunction(), "[]")); | 312 new AlarmsGetAllFunction(), "[]")); |
236 AlarmManager::AlarmList alarms = ToAlarmList(result.get()); | 313 std::vector<linked_ptr<JsAlarm> > alarms = ToAlarmList(result.get()); |
237 EXPECT_EQ(0u, alarms.size()); | 314 EXPECT_EQ(0u, alarms.size()); |
238 } | 315 } |
239 | 316 |
240 // Create 2 alarms, and make sure we can query them. | 317 // Create 2 alarms, and make sure we can query them. |
241 CreateAlarms(2); | 318 CreateAlarms(2); |
242 | 319 |
243 { | 320 { |
244 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( | 321 scoped_ptr<base::ListValue> result(RunFunctionAndReturnList( |
245 new AlarmsGetAllFunction(), "[null]")); | 322 new AlarmsGetAllFunction(), "[null]")); |
246 AlarmManager::AlarmList alarms = ToAlarmList(result.get()); | 323 std::vector<linked_ptr<JsAlarm> > alarms = ToAlarmList(result.get()); |
247 EXPECT_EQ(2u, alarms.size()); | 324 EXPECT_EQ(2u, alarms.size()); |
248 | 325 |
249 // Test the "7" alarm. | 326 // Test the "7" alarm. |
250 AlarmManager::Alarm* alarm = alarms[0].get(); | 327 JsAlarm* alarm = alarms[0].get(); |
251 if (alarm->name != "7") | 328 if (alarm->name != "7") |
252 alarm = alarms[1].get(); | 329 alarm = alarms[1].get(); |
253 EXPECT_EQ("7", alarm->name); | 330 EXPECT_EQ("7", alarm->name); |
254 EXPECT_EQ(7, alarm->delay_in_minutes); | 331 EXPECT_THAT(alarm->period_in_minutes, testing::Pointee(7)); |
255 EXPECT_TRUE(alarm->repeating); | |
256 } | 332 } |
257 } | 333 } |
258 | 334 |
259 TEST_F(ExtensionAlarmsTest, Clear) { | 335 TEST_F(ExtensionAlarmsTest, Clear) { |
260 // Clear a non-existent one. | 336 // Clear a non-existent one. |
261 { | 337 { |
262 std::string error = RunFunctionAndReturnError( | 338 std::string error = RunFunctionAndReturnError( |
263 new AlarmsClearFunction(), "[\"nobody\"]"); | 339 new AlarmsClearFunction(), "[\"nobody\"]"); |
264 EXPECT_FALSE(error.empty()); | 340 EXPECT_FALSE(error.empty()); |
265 } | 341 } |
266 | 342 |
267 // Create 3 alarms. | 343 // Create 3 alarms. |
268 CreateAlarms(3); | 344 CreateAlarms(3); |
269 | 345 |
270 // Clear all but the 0.001-minute alarm. | 346 // Clear all but the 0.001-minute alarm. |
271 { | 347 { |
272 RunFunction(new AlarmsClearFunction(), "[\"7\"]"); | 348 RunFunction(new AlarmsClearFunction(), "[\"7\"]"); |
273 RunFunction(new AlarmsClearFunction(), "[\"0\"]"); | 349 RunFunction(new AlarmsClearFunction(), "[\"0\"]"); |
274 | 350 |
275 const AlarmManager::AlarmList* alarms = | 351 const AlarmManager::AlarmList* alarms = |
276 alarm_manager_->GetAllAlarms(extension_->id()); | 352 alarm_manager_->GetAllAlarms(extension_->id()); |
277 ASSERT_TRUE(alarms); | 353 ASSERT_TRUE(alarms); |
278 EXPECT_EQ(1u, alarms->size()); | 354 EXPECT_EQ(1u, alarms->size()); |
279 EXPECT_EQ(0.001, (*alarms)[0]->delay_in_minutes); | 355 EXPECT_THAT((*alarms)[0].js_alarm->period_in_minutes, |
| 356 testing::Pointee(0.001)); |
280 } | 357 } |
281 | 358 |
282 // Now wait for the alarms to fire, and ensure the cancelled alarms don't | 359 // Now wait for the alarms to fire, and ensure the cancelled alarms don't |
283 // fire. | 360 // fire. |
284 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); | 361 alarm_manager_->ScheduleNextPoll(base::TimeDelta::FromSeconds(0)); |
285 MessageLoop::current()->Run(); | 362 MessageLoop::current()->Run(); |
286 | 363 |
287 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); | 364 ASSERT_EQ(1u, alarm_delegate_->alarms_seen.size()); |
288 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); | 365 EXPECT_EQ("", alarm_delegate_->alarms_seen[0]); |
289 | 366 |
290 // Ensure the 0.001-minute alarm is still there, since it's repeating. | 367 // Ensure the 0.001-minute alarm is still there, since it's repeating. |
291 { | 368 { |
292 const AlarmManager::AlarmList* alarms = | 369 const AlarmManager::AlarmList* alarms = |
293 alarm_manager_->GetAllAlarms(extension_->id()); | 370 alarm_manager_->GetAllAlarms(extension_->id()); |
294 ASSERT_TRUE(alarms); | 371 ASSERT_TRUE(alarms); |
295 EXPECT_EQ(1u, alarms->size()); | 372 EXPECT_EQ(1u, alarms->size()); |
296 EXPECT_EQ(0.001, (*alarms)[0]->delay_in_minutes); | 373 EXPECT_THAT((*alarms)[0].js_alarm->period_in_minutes, |
| 374 testing::Pointee(0.001)); |
297 } | 375 } |
298 } | 376 } |
299 | 377 |
300 TEST_F(ExtensionAlarmsTest, ClearAll) { | 378 TEST_F(ExtensionAlarmsTest, ClearAll) { |
301 // ClearAll with no alarms set. | 379 // ClearAll with no alarms set. |
302 { | 380 { |
303 scoped_ptr<base::Value> result(RunFunctionWithExtension( | 381 scoped_ptr<base::Value> result(RunFunctionWithExtension( |
304 new AlarmsClearAllFunction(), "[]")); | 382 new AlarmsClearAllFunction(), "[]")); |
305 EXPECT_FALSE(result.get()); | 383 EXPECT_FALSE(result.get()); |
306 } | 384 } |
(...skipping 13 matching lines...) Expand all Loading... |
320 const AlarmManager::AlarmList* alarms = | 398 const AlarmManager::AlarmList* alarms = |
321 alarm_manager_->GetAllAlarms(extension_->id()); | 399 alarm_manager_->GetAllAlarms(extension_->id()); |
322 ASSERT_FALSE(alarms); | 400 ASSERT_FALSE(alarms); |
323 } | 401 } |
324 } | 402 } |
325 | 403 |
326 class ExtensionAlarmsSchedulingTest : public ExtensionAlarmsTest { | 404 class ExtensionAlarmsSchedulingTest : public ExtensionAlarmsTest { |
327 public: | 405 public: |
328 // Get the time that the alarm named is scheduled to run. | 406 // Get the time that the alarm named is scheduled to run. |
329 base::Time GetScheduledTime(const std::string& alarm_name) { | 407 base::Time GetScheduledTime(const std::string& alarm_name) { |
330 const extensions::AlarmManager::Alarm* alarm = | 408 const extensions::Alarm* alarm = |
331 alarm_manager_->GetAlarm(extension_->id(), alarm_name); | 409 alarm_manager_->GetAlarm(extension_->id(), alarm_name); |
332 CHECK(alarm); | 410 CHECK(alarm); |
333 return alarm_manager_->scheduled_times_[alarm].time; | 411 return base::Time::FromJsTime(alarm->js_alarm->scheduled_time); |
334 } | 412 } |
335 }; | 413 }; |
336 | 414 |
337 TEST_F(ExtensionAlarmsSchedulingTest, PollScheduling) { | 415 TEST_F(ExtensionAlarmsSchedulingTest, PollScheduling) { |
338 { | 416 { |
339 RunFunction(new AlarmsCreateFunction(), | 417 CreateAlarm("[\"a\", {\"periodInMinutes\": 6}]"); |
340 "[\"a\", {\"delayInMinutes\": 6, \"repeating\": true}]"); | 418 CreateAlarm("[\"bb\", {\"periodInMinutes\": 8}]"); |
341 RunFunction(new AlarmsCreateFunction(), | |
342 "[\"bb\", {\"delayInMinutes\": 8, \"repeating\": true}]"); | |
343 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); | 419 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); |
344 alarm_manager_->RemoveAllAlarms(extension_->id()); | 420 alarm_manager_->RemoveAllAlarms(extension_->id()); |
345 } | 421 } |
346 { | 422 { |
347 RunFunction(new AlarmsCreateFunction(), | 423 CreateAlarm("[\"a\", {\"delayInMinutes\": 10}]"); |
348 "[\"a\", {\"delayInMinutes\": 10}]"); | 424 CreateAlarm("[\"bb\", {\"delayInMinutes\": 21}]"); |
349 RunFunction(new AlarmsCreateFunction(), | |
350 "[\"bb\", {\"delayInMinutes\": 21}]"); | |
351 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); | 425 EXPECT_EQ(GetScheduledTime("a"), alarm_manager_->next_poll_time_); |
352 alarm_manager_->RemoveAllAlarms(extension_->id()); | 426 alarm_manager_->RemoveAllAlarms(extension_->id()); |
353 } | 427 } |
354 { | 428 { |
355 RunFunction(new AlarmsCreateFunction(), | 429 current_time_ = base::Time::FromDoubleT(10); |
356 "[\"a\", {\"delayInMinutes\": 10, \"repeating\": true}]"); | 430 CreateAlarm("[\"a\", {\"periodInMinutes\": 10}]"); |
357 linked_ptr<AlarmManager::Alarm> alarm(new AlarmManager::Alarm()); | 431 Alarm alarm; |
358 alarm->name = "bb"; | 432 alarm.js_alarm->name = "bb"; |
359 alarm->delay_in_minutes = 30; | 433 alarm.js_alarm->scheduled_time = 30 * 60000; |
360 alarm->repeating = true; | 434 alarm.js_alarm->period_in_minutes.reset(new double(30)); |
361 alarm_manager_->AddAlarmImpl(extension_->id(), alarm, | 435 alarm_manager_->AddAlarmImpl(extension_->id(), alarm); |
362 base::TimeDelta::FromMinutes(3)); | 436 EXPECT_DOUBLE_EQ(GetScheduledTime("a").ToDoubleT(), |
363 EXPECT_EQ(GetScheduledTime("bb"), alarm_manager_->next_poll_time_); | 437 alarm_manager_->next_poll_time_.ToDoubleT()); |
364 alarm_manager_->RemoveAllAlarms(extension_->id()); | 438 alarm_manager_->RemoveAllAlarms(extension_->id()); |
365 } | 439 } |
366 { | 440 { |
367 linked_ptr<AlarmManager::Alarm> alarm(new AlarmManager::Alarm()); | 441 current_time_ = base::Time::FromDoubleT(3 * 60 + 1); |
368 alarm->name = "bb"; | 442 Alarm alarm; |
369 alarm->delay_in_minutes = 3; | 443 alarm.js_alarm->name = "bb"; |
370 alarm->repeating = true; | 444 alarm.js_alarm->scheduled_time = 3 * 60000; |
371 alarm_manager_->AddAlarmImpl(extension_->id(), alarm, | 445 alarm.js_alarm->period_in_minutes.reset(new double(3)); |
372 base::TimeDelta::FromSeconds(0)); | 446 alarm_manager_->AddAlarmImpl(extension_->id(), alarm); |
373 MessageLoop::current()->Run(); | 447 MessageLoop::current()->Run(); |
374 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(3), | 448 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(3), |
375 alarm_manager_->next_poll_time_); | 449 alarm_manager_->next_poll_time_); |
376 alarm_manager_->RemoveAllAlarms(extension_->id()); | 450 alarm_manager_->RemoveAllAlarms(extension_->id()); |
377 } | 451 } |
378 { | 452 { |
379 RunFunction(new AlarmsCreateFunction(), | 453 current_time_ = base::Time::FromDoubleT(4 * 60 + 1); |
380 "[\"a\", {\"delayInMinutes\": 2, \"repeating\": true}]"); | 454 CreateAlarm("[\"a\", {\"periodInMinutes\": 2}]"); |
381 alarm_manager_->RemoveAlarm(extension_->id(), "a"); | 455 alarm_manager_->RemoveAlarm(extension_->id(), "a"); |
382 linked_ptr<AlarmManager::Alarm> alarm2(new AlarmManager::Alarm()); | 456 Alarm alarm2; |
383 alarm2->name = "bb"; | 457 alarm2.js_alarm->name = "bb"; |
384 alarm2->delay_in_minutes = 4; | 458 alarm2.js_alarm->scheduled_time = 4 * 60000; |
385 alarm2->repeating = true; | 459 alarm2.js_alarm->period_in_minutes.reset(new double(4)); |
386 alarm_manager_->AddAlarmImpl(extension_->id(), alarm2, | 460 alarm_manager_->AddAlarmImpl(extension_->id(), alarm2); |
387 base::TimeDelta::FromMinutes(3)); | 461 Alarm alarm3; |
388 linked_ptr<AlarmManager::Alarm> alarm3(new AlarmManager::Alarm()); | 462 alarm3.js_alarm->name = "ccc"; |
389 alarm3->name = "ccc"; | 463 alarm3.js_alarm->scheduled_time = 25 * 60000; |
390 alarm3->delay_in_minutes = 25; | 464 alarm3.js_alarm->period_in_minutes.reset(new double(25)); |
391 alarm3->repeating = true; | 465 alarm_manager_->AddAlarmImpl(extension_->id(), alarm3); |
392 alarm_manager_->AddAlarmImpl(extension_->id(), alarm3, | |
393 base::TimeDelta::FromSeconds(0)); | |
394 MessageLoop::current()->Run(); | 466 MessageLoop::current()->Run(); |
395 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(4), | 467 EXPECT_EQ(alarm_manager_->last_poll_time_ + base::TimeDelta::FromMinutes(4), |
396 alarm_manager_->next_poll_time_); | 468 alarm_manager_->next_poll_time_); |
397 alarm_manager_->RemoveAllAlarms(extension_->id()); | 469 alarm_manager_->RemoveAllAlarms(extension_->id()); |
398 } | 470 } |
399 } | 471 } |
400 | 472 |
| 473 TEST_F(ExtensionAlarmsSchedulingTest, ReleasedExtensionPollsInfrequently) { |
| 474 extension_ = utils::CreateEmptyExtensionWithLocation( |
| 475 extensions::Extension::INTERNAL); |
| 476 current_time_ = base::Time::FromJsTime(300000); |
| 477 CreateAlarm("[\"a\", {\"when\": 300010}]"); |
| 478 CreateAlarm("[\"b\", {\"when\": 360000}]"); |
| 479 |
| 480 // In released extensions, we set the granularity to at least 5 |
| 481 // minutes, but AddAlarm schedules its next poll precisely. |
| 482 EXPECT_DOUBLE_EQ(300010, alarm_manager_->next_poll_time_.ToJsTime()); |
| 483 |
| 484 // Run an iteration to see the effect of the granularity. |
| 485 current_time_ = base::Time::FromJsTime(300020); |
| 486 MessageLoop::current()->Run(); |
| 487 EXPECT_DOUBLE_EQ(300020, alarm_manager_->last_poll_time_.ToJsTime()); |
| 488 EXPECT_DOUBLE_EQ(600020, alarm_manager_->next_poll_time_.ToJsTime()); |
| 489 } |
| 490 |
401 TEST_F(ExtensionAlarmsSchedulingTest, TimerRunning) { | 491 TEST_F(ExtensionAlarmsSchedulingTest, TimerRunning) { |
402 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 492 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
403 RunFunction(new AlarmsCreateFunction(), | 493 CreateAlarm("[\"a\", {\"delayInMinutes\": 0.001}]"); |
404 "[\"a\", {\"delayInMinutes\": 0.001}]"); | |
405 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); | 494 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); |
406 MessageLoop::current()->Run(); | 495 MessageLoop::current()->Run(); |
407 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 496 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
408 RunFunction(new AlarmsCreateFunction(), | 497 CreateAlarm("[\"bb\", {\"delayInMinutes\": 10}]"); |
409 "[\"bb\", {\"delayInMinutes\": 10}]"); | |
410 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); | 498 EXPECT_TRUE(alarm_manager_->timer_.IsRunning()); |
411 alarm_manager_->RemoveAllAlarms(extension_->id()); | 499 alarm_manager_->RemoveAllAlarms(extension_->id()); |
412 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); | 500 EXPECT_FALSE(alarm_manager_->timer_.IsRunning()); |
413 } | 501 } |
414 | 502 |
415 } // namespace extensions | 503 } // namespace extensions |
OLD | NEW |