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 #include "chrome/browser/extensions/api/alarms/alarms_api.h" | 5 #include "chrome/browser/extensions/api/alarms/alarms_api.h" |
6 | 6 |
7 #include "base/string_number_conversions.h" | 7 #include "base/string_number_conversions.h" |
8 #include "base/values.h" | 8 #include "base/values.h" |
9 #include "chrome/browser/extensions/api/alarms/alarm_manager.h" | 9 #include "chrome/browser/extensions/api/alarms/alarm_manager.h" |
10 #include "chrome/browser/extensions/extension_system.h" | 10 #include "chrome/browser/extensions/extension_system.h" |
11 #include "chrome/common/extensions/api/alarms.h" | 11 #include "chrome/common/extensions/api/alarms.h" |
12 #include "extensions/common/error_utils.h" | 12 #include "extensions/common/error_utils.h" |
13 | 13 |
14 namespace alarms = extensions::api::alarms; | 14 namespace alarms = extensions::api::alarms; |
15 | 15 |
16 namespace extensions { | 16 namespace extensions { |
17 | 17 |
18 namespace { | 18 namespace { |
19 | 19 |
20 const char kDefaultAlarmName[] = ""; | 20 const char kDefaultAlarmName[] = ""; |
21 const char kAlarmNotFound[] = "No alarm named '*' exists."; | 21 const char kAlarmNotFound[] = "No alarm named '*' exists."; |
22 const char kDelayLessThanMinimum[] = "* is less than minimum of * minutes."; | |
23 const char kDelayIsNonInteger[] = "* is not an integer value."; | |
24 const char kBothRelativeAndAbsoluteTime[] = | 22 const char kBothRelativeAndAbsoluteTime[] = |
25 "Cannot set both when and delayInMinutes."; | 23 "Cannot set both when and delayInMinutes."; |
26 const char kNoScheduledTime[] = | 24 const char kNoScheduledTime[] = |
27 "Must set at least one of when, delayInMinutes, or periodInMinutes."; | 25 "Must set at least one of when, delayInMinutes, or periodInMinutes."; |
28 const int kReleaseDelayMinimum = 5; | 26 const int kReleaseDelayMinimum = 1; |
29 const int kDevDelayMinimum = 0; | 27 const int kDevDelayMinimum = 0; |
30 | 28 |
31 bool ValidateDelay(double delay_in_minutes, | 29 bool ValidateAlarmCreateInfo(const std::string& alarm_name, |
32 const Extension* extension, | 30 const alarms::AlarmCreateInfo& create_info, |
33 const std::string& delay_or_period, | |
34 std::string* error) { | |
35 double delay_minimum = kDevDelayMinimum; | |
36 if (extension->location() != Extension::LOAD) { | |
37 // In release mode we check for integer delay values and a stricter delay | |
38 // minimum. | |
39 if (delay_in_minutes != static_cast<int>(delay_in_minutes)) { | |
40 *error = ErrorUtils::FormatErrorMessage( | |
41 kDelayIsNonInteger, | |
42 delay_or_period); | |
43 return false; | |
44 } | |
45 delay_minimum = kReleaseDelayMinimum; | |
46 } | |
47 | |
48 // Validate against our found delay minimum. | |
49 if (delay_in_minutes < delay_minimum) { | |
50 *error = ErrorUtils::FormatErrorMessage( | |
51 kDelayLessThanMinimum, | |
52 delay_or_period, | |
53 base::DoubleToString(delay_minimum)); | |
54 return false; | |
55 } | |
56 | |
57 return true; | |
58 } | |
59 | |
60 bool ValidateAlarmCreateInfo(const alarms::AlarmCreateInfo& create_info, | |
61 const Extension* extension, | 31 const Extension* extension, |
62 std::string* error) { | 32 std::string* error, |
| 33 std::vector<std::string>* warnings) { |
63 if (create_info.delay_in_minutes.get() && | 34 if (create_info.delay_in_minutes.get() && |
64 create_info.when.get()) { | 35 create_info.when.get()) { |
65 *error = kBothRelativeAndAbsoluteTime; | 36 *error = kBothRelativeAndAbsoluteTime; |
66 return false; | 37 return false; |
67 } | 38 } |
68 if (create_info.delay_in_minutes == NULL && | 39 if (create_info.delay_in_minutes == NULL && |
69 create_info.when == NULL && | 40 create_info.when == NULL && |
70 create_info.period_in_minutes == NULL) { | 41 create_info.period_in_minutes == NULL) { |
71 *error = kNoScheduledTime; | 42 *error = kNoScheduledTime; |
72 return false; | 43 return false; |
73 } | 44 } |
74 | 45 |
75 // Users can always use an absolute timeout to request an arbitrarily-short or | 46 // Users can always use an absolute timeout to request an arbitrarily-short or |
76 // negative delay. We won't honor the short timeout, but we can't check it | 47 // negative delay. We won't honor the short timeout, but we can't check it |
77 // and warn the user because it would introduce race conditions (say they | 48 // and warn the user because it would introduce race conditions (say they |
78 // compute a long-enough timeout, but then the call into the alarms interface | 49 // compute a long-enough timeout, but then the call into the alarms interface |
79 // gets delayed past the boundary). However, it's still worth warning about | 50 // gets delayed past the boundary). However, it's still worth warning about |
80 // relative delays that are shorter than we'll honor. | 51 // relative delays that are shorter than we'll honor. |
81 if (create_info.delay_in_minutes.get()) { | 52 if (create_info.delay_in_minutes.get()) { |
82 if (!ValidateDelay(*create_info.delay_in_minutes, | 53 if (*create_info.delay_in_minutes < kReleaseDelayMinimum) { |
83 extension, "Delay", error)) | 54 COMPILE_ASSERT(kReleaseDelayMinimum == 1, update_warning_message_below); |
84 return false; | 55 if (extension->location() == Extension::LOAD) |
| 56 warnings->push_back(ErrorUtils::FormatErrorMessage( |
| 57 "Alarm delay is less than minimum of 1 minutes." |
| 58 " In released .crx, alarm \"*\" will fire in approximately" |
| 59 " 1 minutes.", |
| 60 alarm_name)); |
| 61 else |
| 62 warnings->push_back(ErrorUtils::FormatErrorMessage( |
| 63 "Alarm delay is less than minimum of 1 minutes." |
| 64 " Alarm \"*\" will fire in approximately 1 minutes.", |
| 65 alarm_name)); |
| 66 } |
85 } | 67 } |
86 if (create_info.period_in_minutes.get()) { | 68 if (create_info.period_in_minutes.get()) { |
87 if (!ValidateDelay(*create_info.period_in_minutes, | 69 if (*create_info.period_in_minutes < kReleaseDelayMinimum) { |
88 extension, "Period", error)) | 70 COMPILE_ASSERT(kReleaseDelayMinimum == 1, update_warning_message_below); |
89 return false; | 71 if (extension->location() == Extension::LOAD) |
| 72 warnings->push_back(ErrorUtils::FormatErrorMessage( |
| 73 "Alarm period is less than minimum of 1 minutes." |
| 74 " In released .crx, alarm \"*\" will fire approximately" |
| 75 " every 1 minutes.", |
| 76 alarm_name)); |
| 77 else |
| 78 warnings->push_back(ErrorUtils::FormatErrorMessage( |
| 79 "Alarm period is less than minimum of 1 minutes." |
| 80 " Alarm \"*\" will fire approximately every 1 minutes.", |
| 81 alarm_name)); |
| 82 } |
90 } | 83 } |
91 | 84 |
92 return true; | 85 return true; |
93 } | 86 } |
94 | 87 |
95 } // namespace | 88 } // namespace |
96 | 89 |
97 AlarmsCreateFunction::AlarmsCreateFunction() | 90 AlarmsCreateFunction::AlarmsCreateFunction() |
98 : now_(&base::Time::Now) { | 91 : now_(&base::Time::Now) { |
99 } | 92 } |
100 | 93 |
101 bool AlarmsCreateFunction::RunImpl() { | 94 bool AlarmsCreateFunction::RunImpl() { |
102 scoped_ptr<alarms::Create::Params> params( | 95 scoped_ptr<alarms::Create::Params> params( |
103 alarms::Create::Params::Create(*args_)); | 96 alarms::Create::Params::Create(*args_)); |
104 EXTENSION_FUNCTION_VALIDATE(params.get()); | 97 EXTENSION_FUNCTION_VALIDATE(params.get()); |
| 98 const std::string& alarm_name = |
| 99 params->name.get() ? *params->name : kDefaultAlarmName; |
| 100 std::vector<std::string> warnings; |
105 if (!ValidateAlarmCreateInfo( | 101 if (!ValidateAlarmCreateInfo( |
106 params->alarm_info, GetExtension(), &error_)) | 102 alarm_name, params->alarm_info, GetExtension(), &error_, &warnings)) |
107 return false; | 103 return false; |
| 104 for (std::vector<std::string>::const_iterator it = warnings.begin(); |
| 105 it != warnings.end(); ++it) |
| 106 WriteToConsole(content::CONSOLE_MESSAGE_LEVEL_WARNING, *it); |
108 | 107 |
109 Alarm alarm(params->name.get() ? *params->name : kDefaultAlarmName, | 108 Alarm alarm(alarm_name, |
110 params->alarm_info, | 109 params->alarm_info, |
111 base::TimeDelta::FromMinutes( | 110 base::TimeDelta::FromMinutes( |
112 GetExtension()->location() == Extension::LOAD ? | 111 GetExtension()->location() == Extension::LOAD ? |
113 kDevDelayMinimum : kReleaseDelayMinimum), | 112 kDevDelayMinimum : kReleaseDelayMinimum), |
114 now_); | 113 now_); |
115 ExtensionSystem::Get(profile())->alarm_manager()->AddAlarm( | 114 ExtensionSystem::Get(profile())->alarm_manager()->AddAlarm( |
116 extension_id(), alarm); | 115 extension_id(), alarm); |
117 | 116 |
118 return true; | 117 return true; |
119 } | 118 } |
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
170 return true; | 169 return true; |
171 } | 170 } |
172 | 171 |
173 bool AlarmsClearAllFunction::RunImpl() { | 172 bool AlarmsClearAllFunction::RunImpl() { |
174 ExtensionSystem::Get(profile())->alarm_manager()->RemoveAllAlarms( | 173 ExtensionSystem::Get(profile())->alarm_manager()->RemoveAllAlarms( |
175 extension_id()); | 174 extension_id()); |
176 return true; | 175 return true; |
177 } | 176 } |
178 | 177 |
179 } // namespace extensions | 178 } // namespace extensions |
OLD | NEW |