cygprofile: increase timeouts to allow showing web contents
[chromium-blink-merge.git] / chrome / browser / extensions / api / settings_private / prefs_util.cc
blob12c3f8fc06ffb94f26d91fe6c2ddb9d99739abeb
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.
5 #include "base/prefs/pref_service.h"
6 #include "chrome/browser/browser_process.h"
7 #include "chrome/browser/extensions/api/settings_private/prefs_util.h"
8 #include "chrome/browser/extensions/chrome_extension_function.h"
9 #include "chrome/browser/profiles/profile.h"
10 #include "chrome/common/pref_names.h"
11 #include "components/proxy_config/proxy_config_pref_names.h"
12 #include "components/url_formatter/url_fixer.h"
14 #if defined(OS_CHROMEOS)
15 #include "chrome/browser/chromeos/ownership/owner_settings_service_chromeos.h"
16 #include "chrome/browser/chromeos/ownership/owner_settings_service_chromeos_factory.h"
17 #include "chrome/browser/chromeos/settings/cros_settings.h"
18 #endif
20 namespace extensions {
22 namespace settings_private = api::settings_private;
24 PrefsUtil::PrefsUtil(Profile* profile) : profile_(profile) {
27 PrefsUtil::~PrefsUtil() {
30 #if defined(OS_CHROMEOS)
31 using CrosSettings = chromeos::CrosSettings;
32 #endif
34 const PrefsUtil::TypedPrefMap& PrefsUtil::GetWhitelistedKeys() {
35 static PrefsUtil::TypedPrefMap* s_whitelist = nullptr;
36 if (s_whitelist)
37 return *s_whitelist;
38 s_whitelist = new PrefsUtil::TypedPrefMap();
39 (*s_whitelist)["alternate_error_pages.enabled"] =
40 settings_private::PrefType::PREF_TYPE_BOOLEAN;
41 (*s_whitelist)["bookmark_bar.show_on_all_tabs"] =
42 settings_private::PrefType::PREF_TYPE_BOOLEAN;
43 (*s_whitelist)["browser.show_home_button"] =
44 settings_private::PrefType::PREF_TYPE_BOOLEAN;
45 (*s_whitelist)["download.default_directory"] =
46 settings_private::PrefType::PREF_TYPE_STRING;
47 (*s_whitelist)["download.prompt_for_download"] =
48 settings_private::PrefType::PREF_TYPE_BOOLEAN;
49 (*s_whitelist)["enable_do_not_track"] =
50 settings_private::PrefType::PREF_TYPE_BOOLEAN;
51 (*s_whitelist)["homepage"] = settings_private::PrefType::PREF_TYPE_URL;
52 (*s_whitelist)["net.network_prediction_options"] =
53 settings_private::PrefType::PREF_TYPE_NUMBER;
54 (*s_whitelist)["safebrowsing.enabled"] =
55 settings_private::PrefType::PREF_TYPE_BOOLEAN;
56 (*s_whitelist)["safebrowsing.extended_reporting_enabled"] =
57 settings_private::PrefType::PREF_TYPE_BOOLEAN;
58 (*s_whitelist)["search.suggest_enabled"] =
59 settings_private::PrefType::PREF_TYPE_BOOLEAN;
60 (*s_whitelist)["spellcheck.use_spelling_service"] =
61 settings_private::PrefType::PREF_TYPE_BOOLEAN;
62 (*s_whitelist)["session.restore_on_startup"] =
63 settings_private::PrefType::PREF_TYPE_NUMBER;
64 (*s_whitelist)["session.startup_urls"] =
65 settings_private::PrefType::PREF_TYPE_LIST;
67 #if defined(OS_CHROMEOS)
68 (*s_whitelist)["cros.accounts.allowBWSI"] =
69 settings_private::PrefType::PREF_TYPE_BOOLEAN;
70 (*s_whitelist)["cros.accounts.supervisedUsersEnabled"] =
71 settings_private::PrefType::PREF_TYPE_BOOLEAN;
72 (*s_whitelist)["cros.accounts.showUserNamesOnSignIn"] =
73 settings_private::PrefType::PREF_TYPE_BOOLEAN;
74 (*s_whitelist)["cros.accounts.allowGuest"] =
75 settings_private::PrefType::PREF_TYPE_BOOLEAN;
76 (*s_whitelist)["cros.accounts.users"] =
77 settings_private::PrefType::PREF_TYPE_LIST;
78 (*s_whitelist)["settings.accessibility"] =
79 settings_private::PrefType::PREF_TYPE_BOOLEAN;
80 (*s_whitelist)["settings.a11y.autoclick"] =
81 settings_private::PrefType::PREF_TYPE_BOOLEAN;
82 (*s_whitelist)["settings.a11y.autoclick_delay_ms"] =
83 settings_private::PrefType::PREF_TYPE_BOOLEAN;
84 (*s_whitelist)["settings.a11y.enable_menu"] =
85 settings_private::PrefType::PREF_TYPE_BOOLEAN;
86 (*s_whitelist)["settings.a11y.high_contrast_enabled"] =
87 settings_private::PrefType::PREF_TYPE_BOOLEAN;
88 (*s_whitelist)["settings.a11y.large_cursor_enabled"] =
89 settings_private::PrefType::PREF_TYPE_BOOLEAN;
90 (*s_whitelist)["settings.a11y.screen_magnifier"] =
91 settings_private::PrefType::PREF_TYPE_BOOLEAN;
92 (*s_whitelist)["settings.a11y.sticky_keys_enabled"] =
93 settings_private::PrefType::PREF_TYPE_BOOLEAN;
94 (*s_whitelist)["settings.a11y.virtual_keyboard"] =
95 settings_private::PrefType::PREF_TYPE_BOOLEAN;
96 (*s_whitelist)["settings.clock.use_24hour_clock"] =
97 settings_private::PrefType::PREF_TYPE_BOOLEAN;
98 (*s_whitelist)["settings.touchpad.enable_tap_dragging"] =
99 settings_private::PrefType::PREF_TYPE_BOOLEAN;
100 (*s_whitelist)["cros.metrics.reportingEnabled"] =
101 settings_private::PrefType::PREF_TYPE_BOOLEAN;
102 (*s_whitelist)["cros.device.attestation_for_content_protection_enabled"] =
103 settings_private::PrefType::PREF_TYPE_BOOLEAN;
104 (*s_whitelist)["settings.internet.wake_on_wifi_ssid"] =
105 settings_private::PrefType::PREF_TYPE_BOOLEAN;
106 #endif
108 return *s_whitelist;
111 api::settings_private::PrefType PrefsUtil::GetType(const std::string& name,
112 base::Value::Type type) {
113 switch (type) {
114 case base::Value::Type::TYPE_BOOLEAN:
115 return api::settings_private::PrefType::PREF_TYPE_BOOLEAN;
116 case base::Value::Type::TYPE_INTEGER:
117 case base::Value::Type::TYPE_DOUBLE:
118 return api::settings_private::PrefType::PREF_TYPE_NUMBER;
119 case base::Value::Type::TYPE_STRING:
120 return IsPrefTypeURL(name)
121 ? api::settings_private::PrefType::PREF_TYPE_URL
122 : api::settings_private::PrefType::PREF_TYPE_STRING;
123 case base::Value::Type::TYPE_LIST:
124 return api::settings_private::PrefType::PREF_TYPE_LIST;
125 default:
126 return api::settings_private::PrefType::PREF_TYPE_NONE;
130 scoped_ptr<api::settings_private::PrefObject> PrefsUtil::GetCrosSettingsPref(
131 const std::string& name) {
132 scoped_ptr<api::settings_private::PrefObject> pref_object(
133 new api::settings_private::PrefObject());
135 #if defined(OS_CHROMEOS)
136 const base::Value* value = CrosSettings::Get()->GetPref(name);
137 pref_object->key = name;
138 pref_object->type = GetType(name, value->GetType());
139 pref_object->value.reset(value->DeepCopy());
140 #endif
142 return pref_object.Pass();
145 scoped_ptr<api::settings_private::PrefObject> PrefsUtil::GetPref(
146 const std::string& name) {
147 if (IsCrosSetting(name))
148 return GetCrosSettingsPref(name);
150 PrefService* pref_service = FindServiceForPref(name);
151 const PrefService::Preference* pref = pref_service->FindPreference(name);
152 if (!pref)
153 return nullptr;
155 scoped_ptr<api::settings_private::PrefObject> pref_object(
156 new api::settings_private::PrefObject());
157 pref_object->key = pref->name();
158 pref_object->type = GetType(name, pref->GetType());
159 pref_object->value.reset(pref->GetValue()->DeepCopy());
161 if (pref->IsManaged()) {
162 if (pref->IsManagedByCustodian()) {
163 pref_object->policy_source =
164 api::settings_private::PolicySource::POLICY_SOURCE_DEVICE;
165 } else {
166 pref_object->policy_source =
167 api::settings_private::PolicySource::POLICY_SOURCE_USER;
169 pref_object->policy_enforcement =
170 pref->IsRecommended() ? api::settings_private::PolicyEnforcement::
171 POLICY_ENFORCEMENT_RECOMMENDED
172 : api::settings_private::PolicyEnforcement::
173 POLICY_ENFORCEMENT_ENFORCED;
174 } else if (!IsPrefUserModifiable(name)) {
175 pref_object->policy_source =
176 api::settings_private::PolicySource::POLICY_SOURCE_USER;
177 pref_object->policy_enforcement =
178 api::settings_private::PolicyEnforcement::POLICY_ENFORCEMENT_ENFORCED;
181 return pref_object.Pass();
184 PrefsUtil::SetPrefResult PrefsUtil::SetPref(const std::string& pref_name,
185 const base::Value* value) {
186 if (IsCrosSetting(pref_name))
187 return SetCrosSettingsPref(pref_name, value);
189 PrefService* pref_service = FindServiceForPref(pref_name);
191 if (!IsPrefUserModifiable(pref_name))
192 return PREF_NOT_MODIFIABLE;
194 const PrefService::Preference* pref =
195 pref_service->FindPreference(pref_name);
196 if (!pref)
197 return PREF_NOT_FOUND;
199 DCHECK_EQ(pref->GetType(), value->GetType());
201 switch (pref->GetType()) {
202 case base::Value::TYPE_BOOLEAN:
203 case base::Value::TYPE_DOUBLE:
204 case base::Value::TYPE_LIST:
205 pref_service->Set(pref_name, *value);
206 break;
207 case base::Value::TYPE_INTEGER: {
208 // In JS all numbers are doubles.
209 double double_value;
210 if (!value->GetAsDouble(&double_value))
211 return PREF_TYPE_MISMATCH;
213 pref_service->SetInteger(pref_name, static_cast<int>(double_value));
214 break;
216 case base::Value::TYPE_STRING: {
217 std::string string_value;
218 if (!value->GetAsString(&string_value))
219 return PREF_TYPE_MISMATCH;
221 if (IsPrefTypeURL(pref_name)) {
222 GURL fixed = url_formatter::FixupURL(string_value, std::string());
223 string_value = fixed.spec();
226 pref_service->SetString(pref_name, string_value);
227 break;
229 default:
230 return PREF_TYPE_UNSUPPORTED;
233 // TODO(orenb): Process setting metrics here and in the CrOS setting method
234 // too (like "ProcessUserMetric" in CoreOptionsHandler).
235 return SUCCESS;
238 PrefsUtil::SetPrefResult PrefsUtil::SetCrosSettingsPref(
239 const std::string& pref_name, const base::Value* value) {
240 #if defined(OS_CHROMEOS)
241 chromeos::OwnerSettingsServiceChromeOS* service =
242 chromeos::OwnerSettingsServiceChromeOSFactory::GetForBrowserContext(
243 profile_);
245 // Check if setting requires owner.
246 if (service && service->HandlesSetting(pref_name)) {
247 if (service->Set(pref_name, *value))
248 return SUCCESS;
249 return PREF_NOT_MODIFIABLE;
252 chromeos::CrosSettings::Get()->Set(pref_name, *value);
253 return SUCCESS;
254 #else
255 return PREF_NOT_FOUND;
256 #endif
259 bool PrefsUtil::AppendToListCrosSetting(const std::string& pref_name,
260 const base::Value& value) {
261 #if defined(OS_CHROMEOS)
262 chromeos::OwnerSettingsServiceChromeOS* service =
263 chromeos::OwnerSettingsServiceChromeOSFactory::GetForBrowserContext(
264 profile_);
266 // Returns false if not the owner, for settings requiring owner.
267 if (service && service->HandlesSetting(pref_name)) {
268 return service->AppendToList(pref_name, value);
271 chromeos::CrosSettings::Get()->AppendToList(pref_name, &value);
272 return true;
273 #else
274 return false;
275 #endif
278 bool PrefsUtil::RemoveFromListCrosSetting(const std::string& pref_name,
279 const base::Value& value) {
280 #if defined(OS_CHROMEOS)
281 chromeos::OwnerSettingsServiceChromeOS* service =
282 chromeos::OwnerSettingsServiceChromeOSFactory::GetForBrowserContext(
283 profile_);
285 // Returns false if not the owner, for settings requiring owner.
286 if (service && service->HandlesSetting(pref_name)) {
287 return service->RemoveFromList(pref_name, value);
290 chromeos::CrosSettings::Get()->RemoveFromList(pref_name, &value);
291 return true;
292 #else
293 return false;
294 #endif
297 bool PrefsUtil::IsPrefTypeURL(const std::string& pref_name) {
298 settings_private::PrefType pref_type =
299 settings_private::PrefType::PREF_TYPE_NONE;
301 const TypedPrefMap keys = GetWhitelistedKeys();
302 const auto& iter = keys.find(pref_name);
303 if (iter != keys.end())
304 pref_type = iter->second;
306 return pref_type == settings_private::PrefType::PREF_TYPE_URL;
309 bool PrefsUtil::IsPrefUserModifiable(const std::string& pref_name) {
310 if (pref_name != prefs::kBrowserGuestModeEnabled &&
311 pref_name != prefs::kBrowserAddPersonEnabled) {
312 return true;
315 PrefService* pref_service = profile_->GetPrefs();
316 const PrefService::Preference* pref =
317 pref_service->FindPreference(pref_name.c_str());
318 if (!pref || !pref->IsUserModifiable() || profile_->IsSupervised())
319 return false;
321 return true;
324 PrefService* PrefsUtil::FindServiceForPref(const std::string& pref_name) {
325 PrefService* user_prefs = profile_->GetPrefs();
327 // Proxy is a peculiar case: on ChromeOS, settings exist in both user
328 // prefs and local state, but chrome://settings should affect only user prefs.
329 // Elsewhere the proxy settings are stored in local state.
330 // See http://crbug.com/157147
332 if (pref_name == proxy_config::prefs::kProxy) {
333 #if defined(OS_CHROMEOS)
334 return user_prefs;
335 #else
336 return g_browser_process->local_state();
337 #endif
340 // Find which PrefService contains the given pref. Pref names should not
341 // be duplicated across services, however if they are, prefer the user's
342 // prefs.
343 if (user_prefs->FindPreference(pref_name))
344 return user_prefs;
346 if (g_browser_process->local_state()->FindPreference(pref_name))
347 return g_browser_process->local_state();
349 return user_prefs;
352 bool PrefsUtil::IsCrosSetting(const std::string& pref_name) {
353 #if defined(OS_CHROMEOS)
354 return CrosSettings::Get()->IsCrosSettings(pref_name);
355 #else
356 return false;
357 #endif
360 } // namespace extensions