Popular sites on the NTP: check that experiment group StartsWith (rather than IS...
[chromium-blink-merge.git] / chrome / browser / ui / webui / options / chromeos / internet_options_handler.cc
blob55d66cd645de8cc103fd8879b459cc7d720f00a6
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
3 // found in the LICENSE file.
5 #include "chrome/browser/ui/webui/options/chromeos/internet_options_handler.h"
7 #include <ctype.h>
9 #include <map>
10 #include <string>
11 #include <vector>
13 #include "base/basictypes.h"
14 #include "base/bind.h"
15 #include "base/bind_helpers.h"
16 #include "base/memory/scoped_ptr.h"
17 #include "base/values.h"
18 #include "chrome/browser/chromeos/enrollment_dialog_view.h"
19 #include "chrome/browser/chromeos/mobile_config.h"
20 #include "chrome/browser/chromeos/options/network_config_view.h"
21 #include "chrome/browser/chromeos/profiles/profile_helper.h"
22 #include "chrome/browser/chromeos/settings/cros_settings.h"
23 #include "chrome/browser/chromeos/sim_dialog_delegate.h"
24 #include "chrome/browser/chromeos/ui/choose_mobile_network_dialog.h"
25 #include "chrome/browser/chromeos/ui/mobile_config_ui.h"
26 #include "chrome/browser/chromeos/ui_proxy_config_service.h"
27 #include "chrome/browser/profiles/profile.h"
28 #include "chrome/browser/ui/webui/chromeos/mobile_setup_dialog.h"
29 #include "chrome/browser/ui/webui/options/chromeos/internet_options_handler_strings.h"
30 #include "chromeos/login/login_state.h"
31 #include "chromeos/network/network_state.h"
32 #include "chromeos/network/network_state_handler.h"
33 #include "components/onc/onc_constants.h"
34 #include "components/user_manager/user_manager.h"
35 #include "content/public/browser/web_contents.h"
36 #include "content/public/browser/web_ui.h"
37 #include "extensions/browser/api/vpn_provider/vpn_service.h"
38 #include "extensions/browser/api/vpn_provider/vpn_service_factory.h"
39 #include "extensions/browser/extension_registry.h"
40 #include "extensions/common/extension.h"
41 #include "extensions/common/extension_set.h"
42 #include "extensions/common/permissions/api_permission.h"
43 #include "extensions/common/permissions/permissions_data.h"
44 #include "third_party/cros_system_api/dbus/service_constants.h"
45 #include "ui/base/l10n/l10n_util.h"
46 #include "ui/base/webui/web_ui_util.h"
47 #include "ui/chromeos/network/network_connect.h"
48 #include "ui/chromeos/strings/grit/ui_chromeos_strings.h"
50 namespace chromeos {
51 namespace options {
53 namespace {
55 // Keys for the initial "localized" dictionary values.
56 const char kLoggedInAsOwnerKey[] = "loggedInAsOwner";
58 // Functions we call in JavaScript.
59 const char kSetVPNProvidersFunction[] = "options.VPNProviders.setProviders";
61 // JS methods to show additional UI.
62 const char kShowMorePlanInfoMessage[] = "showMorePlanInfo";
63 const char kSimOperationMessage[] = "simOperation";
65 // TODO(stevenjb): Deprecate these and integrate with settings Web UI.
66 const char kAddVPNConnectionMessage[] = "addVPNConnection";
67 const char kAddNonVPNConnectionMessage[] = "addNonVPNConnection";
68 const char kConfigureNetworkMessage[] = "configureNetwork";
70 const char kLoadVPNProviders[] = "loadVPNProviders";
72 // These are strings used to communicate with JavaScript.
73 const char kTagSimOpChangePin[] = "changePin";
74 const char kTagSimOpConfigure[] = "configure";
75 const char kTagSimOpSetLocked[] = "setLocked";
76 const char kTagSimOpSetUnlocked[] = "setUnlocked";
77 const char kTagSimOpUnlock[] = "unlock";
78 const char kTagVPNProviderName[] = "name";
79 const char kTagVPNProviderExtensionID[] = "extensionID";
81 const NetworkState* GetNetworkState(const std::string& service_path) {
82 return NetworkHandler::Get()->network_state_handler()->
83 GetNetworkState(service_path);
86 std::string ServicePathFromGuid(const std::string& guid) {
87 const NetworkState* network =
88 NetworkHandler::Get()->network_state_handler()->GetNetworkStateFromGuid(
89 guid);
90 return network ? network->path() : "";
93 bool IsVPNProvider(const extensions::Extension* extension) {
94 return extension->permissions_data()->HasAPIPermission(
95 extensions::APIPermission::kVpnProvider);
98 Profile* GetProfileForPrimaryUser() {
99 return chromeos::ProfileHelper::Get()->GetProfileByUser(
100 user_manager::UserManager::Get()->GetPrimaryUser());
103 extensions::ExtensionRegistry* GetExtensionRegistryForPrimaryUser() {
104 return extensions::ExtensionRegistry::Get(GetProfileForPrimaryUser());
107 scoped_ptr<base::DictionaryValue> BuildVPNProviderDictionary(
108 const std::string& name,
109 const std::string& third_party_provider_extension_id) {
110 scoped_ptr<base::DictionaryValue> dict(new base::DictionaryValue);
111 dict->SetString(kTagVPNProviderName, name);
112 if (!third_party_provider_extension_id.empty()) {
113 dict->SetString(kTagVPNProviderExtensionID,
114 third_party_provider_extension_id);
116 return dict.Pass();
119 } // namespace
121 InternetOptionsHandler::InternetOptionsHandler()
122 : weak_factory_(this) {
123 GetExtensionRegistryForPrimaryUser()->AddObserver(this);
126 InternetOptionsHandler::~InternetOptionsHandler() {
127 GetExtensionRegistryForPrimaryUser()->RemoveObserver(this);
130 void InternetOptionsHandler::GetLocalizedValues(
131 base::DictionaryValue* localized_strings) {
132 DCHECK(localized_strings);
133 internet_options_strings::RegisterLocalizedStrings(localized_strings);
135 // TODO(stevenjb): Find a better way to populate initial data before
136 // InitializePage() gets called.
137 std::string owner;
138 chromeos::CrosSettings::Get()->GetString(chromeos::kDeviceOwner, &owner);
139 bool logged_in_as_owner = LoginState::Get()->GetLoggedInUserType() ==
140 LoginState::LOGGED_IN_USER_OWNER;
141 localized_strings->SetBoolean(kLoggedInAsOwnerKey, logged_in_as_owner);
144 void InternetOptionsHandler::InitializePage() {
145 UpdateVPNProviders();
148 void InternetOptionsHandler::RegisterMessages() {
149 web_ui()->RegisterMessageCallback(kAddVPNConnectionMessage,
150 base::Bind(&InternetOptionsHandler::AddVPNConnection,
151 base::Unretained(this)));
152 web_ui()->RegisterMessageCallback(kAddNonVPNConnectionMessage,
153 base::Bind(&InternetOptionsHandler::AddNonVPNConnection,
154 base::Unretained(this)));
155 web_ui()->RegisterMessageCallback(kConfigureNetworkMessage,
156 base::Bind(&InternetOptionsHandler::ConfigureNetwork,
157 base::Unretained(this)));
158 web_ui()->RegisterMessageCallback(kShowMorePlanInfoMessage,
159 base::Bind(&InternetOptionsHandler::ShowMorePlanInfoCallback,
160 base::Unretained(this)));
161 web_ui()->RegisterMessageCallback(kSimOperationMessage,
162 base::Bind(&InternetOptionsHandler::SimOperationCallback,
163 base::Unretained(this)));
164 web_ui()->RegisterMessageCallback(
165 kLoadVPNProviders,
166 base::Bind(&InternetOptionsHandler::LoadVPNProvidersCallback,
167 base::Unretained(this)));
170 void InternetOptionsHandler::OnExtensionLoaded(
171 content::BrowserContext* browser_context,
172 const extensions::Extension* extension) {
173 if (IsVPNProvider(extension))
174 UpdateVPNProviders();
177 void InternetOptionsHandler::OnExtensionUnloaded(
178 content::BrowserContext* browser_context,
179 const extensions::Extension* extension,
180 extensions::UnloadedExtensionInfo::Reason reason) {
181 if (IsVPNProvider(extension))
182 UpdateVPNProviders();
185 void InternetOptionsHandler::OnShutdown(
186 extensions::ExtensionRegistry* registry) {
187 registry->RemoveObserver(this);
190 void InternetOptionsHandler::ShowMorePlanInfoCallback(
191 const base::ListValue* args) {
192 if (!web_ui())
193 return;
194 std::string guid;
195 if (args->GetSize() != 1 || !args->GetString(0, &guid)) {
196 NOTREACHED();
197 return;
199 std::string service_path = ServicePathFromGuid(guid);
200 if (!service_path.empty())
201 ui::NetworkConnect::Get()->ShowMobileSetup(service_path);
204 void InternetOptionsHandler::SimOperationCallback(const base::ListValue* args) {
205 std::string operation;
206 if (args->GetSize() != 1 || !args->GetString(0, &operation)) {
207 NOTREACHED();
208 return;
210 if (operation == kTagSimOpConfigure) {
211 mobile_config_ui::DisplayConfigDialog();
212 return;
214 // 1. Bring up SIM unlock dialog, pass new RequirePin setting in URL.
215 // 2. Dialog will ask for current PIN in any case.
216 // 3. If card is locked it will first call PIN unlock operation
217 // 4. Then it will call Set RequirePin, passing the same PIN.
218 // 5. The dialog may change device properties, in which case
219 // DevicePropertiesUpdated() will get called which will update the UI.
220 SimDialogDelegate::SimDialogMode mode;
221 if (operation == kTagSimOpSetLocked) {
222 mode = SimDialogDelegate::SIM_DIALOG_SET_LOCK_ON;
223 } else if (operation == kTagSimOpSetUnlocked) {
224 mode = SimDialogDelegate::SIM_DIALOG_SET_LOCK_OFF;
225 } else if (operation == kTagSimOpUnlock) {
226 mode = SimDialogDelegate::SIM_DIALOG_UNLOCK;
227 } else if (operation == kTagSimOpChangePin) {
228 mode = SimDialogDelegate::SIM_DIALOG_CHANGE_PIN;
229 } else {
230 NOTREACHED();
231 return;
233 SimDialogDelegate::ShowDialog(GetNativeWindow(), mode);
236 ////////////////////////////////////////////////////////////////////////////////
238 void InternetOptionsHandler::UpdateVPNProviders() {
239 extensions::ExtensionRegistry* const registry =
240 GetExtensionRegistryForPrimaryUser();
242 base::ListValue vpn_providers;
243 const extensions::ExtensionSet& extensions = registry->enabled_extensions();
244 for (const auto& extension : extensions) {
245 if (IsVPNProvider(extension.get())) {
246 vpn_providers.Append(BuildVPNProviderDictionary(
247 extension->name(), extension->id()).release());
250 // Add the built-in OpenVPN/L2TP provider.
251 vpn_providers.Append(
252 BuildVPNProviderDictionary(
253 l10n_util::GetStringUTF8(IDS_NETWORK_VPN_BUILT_IN_PROVIDER),
254 std::string() /* third_party_provider_extension_id */).release());
255 web_ui()->CallJavascriptFunction(kSetVPNProvidersFunction, vpn_providers);
258 gfx::NativeWindow InternetOptionsHandler::GetNativeWindow() const {
259 return web_ui()->GetWebContents()->GetTopLevelNativeWindow();
262 const PrefService* InternetOptionsHandler::GetPrefs() const {
263 return Profile::FromWebUI(web_ui())->GetPrefs();
267 void InternetOptionsHandler::AddVPNConnection(const base::ListValue* args) {
268 if (args->empty()) {
269 // Show the "add network" dialog for the built-in OpenVPN/L2TP provider.
270 NetworkConfigView::ShowForType(shill::kTypeVPN, GetNativeWindow());
271 return;
274 std::string extension_id;
275 if (args->GetSize() != 1 || !args->GetString(0, &extension_id)) {
276 NOTREACHED();
277 return;
280 // Request that the third-party VPN provider identified by |provider_id|
281 // show its "add network" dialog.
282 chromeos::VpnServiceFactory::GetForBrowserContext(
283 GetProfileForPrimaryUser())->SendShowAddDialogToExtension(extension_id);
286 void InternetOptionsHandler::AddNonVPNConnection(const base::ListValue* args) {
287 std::string onc_type;
288 if (args->GetSize() != 1 || !args->GetString(0, &onc_type)) {
289 NOTREACHED();
290 return;
292 if (onc_type == ::onc::network_type::kWiFi) {
293 NetworkConfigView::ShowForType(shill::kTypeWifi, GetNativeWindow());
294 } else if (onc_type == ::onc::network_type::kCellular) {
295 ChooseMobileNetworkDialog::ShowDialog(GetNativeWindow());
296 } else {
297 LOG(ERROR) << "Unsupported type for AddConnection";
301 void InternetOptionsHandler::ConfigureNetwork(const base::ListValue* args) {
302 std::string guid;
303 if (args->GetSize() < 1 || !args->GetString(0, &guid)) {
304 NOTREACHED();
305 return;
307 bool force_show = false;
308 if (args->GetSize() >= 2)
309 args->GetBoolean(1, &force_show);
311 const std::string service_path = ServicePathFromGuid(guid);
312 if (service_path.empty())
313 return;
315 const NetworkState* network = GetNetworkState(service_path);
316 if (!network)
317 return;
319 if (network->type() == shill::kTypeVPN &&
320 network->vpn_provider_type() == shill::kProviderThirdPartyVpn) {
321 // Request that the third-party VPN provider used by the |network| show a
322 // configuration dialog for it.
323 VpnServiceFactory::GetForBrowserContext(GetProfileForPrimaryUser())
324 ->SendShowConfigureDialogToExtension(
325 network->third_party_vpn_provider_extension_id(), network->name());
326 return;
329 // If a network is not connectable, show the enrollment dialog if available.
330 if (!force_show && !network->connectable() &&
331 enrollment::CreateDialog(service_path, GetNativeWindow())) {
332 return;
335 NetworkConfigView::Show(service_path, GetNativeWindow());
338 void InternetOptionsHandler::LoadVPNProvidersCallback(
339 const base::ListValue* args) {
340 UpdateVPNProviders();
343 } // namespace options
344 } // namespace chromeos