Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(179)

Side by Side Diff: chrome/browser/extensions/external_install_error.cc

Issue 300853008: Refactor external_install_ui (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: back to EXTENSION_REMOVED notification Created 6 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright 2014 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.
4
5 #include "chrome/browser/extensions/external_install_error.h"
6
7 #include "base/bind.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "chrome/app/chrome_command_ids.h"
10 #include "chrome/browser/extensions/extension_install_ui.h"
11 #include "chrome/browser/extensions/extension_service.h"
12 #include "chrome/browser/extensions/external_install_manager.h"
13 #include "chrome/browser/extensions/webstore_data_fetcher.h"
14 #include "chrome/browser/profiles/profile.h"
15 #include "chrome/browser/ui/browser.h"
16 #include "chrome/browser/ui/browser_finder.h"
17 #include "chrome/browser/ui/global_error/global_error.h"
18 #include "chrome/browser/ui/global_error/global_error_service.h"
19 #include "chrome/browser/ui/global_error/global_error_service_factory.h"
20 #include "extensions/browser/extension_registry.h"
21 #include "extensions/browser/extension_system.h"
22 #include "extensions/common/constants.h"
23 #include "extensions/common/extension.h"
24 #include "grit/generated_resources.h"
25 #include "ui/base/l10n/l10n_util.h"
26 #include "ui/gfx/image/image.h"
27 #include "ui/gfx/image/image_skia_operations.h"
28
29 namespace extensions {
30
31 namespace {
32
33 // Return the menu label for a global error.
34 base::string16 GetMenuItemLabel(const Extension* extension) {
35 if (!extension)
36 return base::string16();
37
38 int id = -1;
39 if (extension->is_app())
40 id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_APP;
41 else if (extension->is_theme())
42 id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_THEME;
43 else
44 id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_EXTENSION;
45
46 return l10n_util::GetStringFUTF16(id, base::UTF8ToUTF16(extension->name()));
47 }
48
49 // A global error that spawns a dialog when the menu item is clicked.
50 class ExternalInstallMenuAlert : public GlobalError {
51 public:
52 explicit ExternalInstallMenuAlert(ExternalInstallError* error);
53 virtual ~ExternalInstallMenuAlert();
54
55 private:
56 // GlobalError implementation.
57 virtual Severity GetSeverity() OVERRIDE;
58 virtual bool HasMenuItem() OVERRIDE;
59 virtual int MenuItemCommandID() OVERRIDE;
60 virtual base::string16 MenuItemLabel() OVERRIDE;
61 virtual void ExecuteMenuItem(Browser* browser) OVERRIDE;
62 virtual bool HasBubbleView() OVERRIDE;
63 virtual bool HasShownBubbleView() OVERRIDE;
64 virtual void ShowBubbleView(Browser* browser) OVERRIDE;
65 virtual GlobalErrorBubbleViewBase* GetBubbleView() OVERRIDE;
66
67 // The owning ExternalInstallError.
68 ExternalInstallError* error_;
69
70 DISALLOW_COPY_AND_ASSIGN(ExternalInstallMenuAlert);
71 };
72
73 // A global error that spawns a bubble when the menu item is clicked.
74 class ExternalInstallBubbleAlert : public GlobalErrorWithStandardBubble {
75 public:
76 explicit ExternalInstallBubbleAlert(ExternalInstallError* error,
77 ExtensionInstallPrompt::Prompt* prompt);
78 virtual ~ExternalInstallBubbleAlert();
79
80 private:
81 // GlobalError implementation.
82 virtual Severity GetSeverity() OVERRIDE;
83 virtual bool HasMenuItem() OVERRIDE;
84 virtual int MenuItemCommandID() OVERRIDE;
85 virtual base::string16 MenuItemLabel() OVERRIDE;
86 virtual void ExecuteMenuItem(Browser* browser) OVERRIDE;
87
88 // GlobalErrorWithStandardBubble implementation.
89 virtual gfx::Image GetBubbleViewIcon() OVERRIDE;
90 virtual base::string16 GetBubbleViewTitle() OVERRIDE;
91 virtual std::vector<base::string16> GetBubbleViewMessages() OVERRIDE;
92 virtual base::string16 GetBubbleViewAcceptButtonLabel() OVERRIDE;
93 virtual base::string16 GetBubbleViewCancelButtonLabel() OVERRIDE;
94 virtual void OnBubbleViewDidClose(Browser* browser) OVERRIDE;
95 virtual void BubbleViewAcceptButtonPressed(Browser* browser) OVERRIDE;
96 virtual void BubbleViewCancelButtonPressed(Browser* browser) OVERRIDE;
97
98 // The owning ExternalInstallError.
99 ExternalInstallError* error_;
100
101 // The Prompt with all information, which we then use to populate the bubble.
102 ExtensionInstallPrompt::Prompt* prompt_;
103
104 DISALLOW_COPY_AND_ASSIGN(ExternalInstallBubbleAlert);
105 };
106
107 ////////////////////////////////////////////////////////////////////////////////
108 // ExternalInstallMenuAlert
109
110 ExternalInstallMenuAlert::ExternalInstallMenuAlert(ExternalInstallError* error)
111 : error_(error) {
112 }
113
114 ExternalInstallMenuAlert::~ExternalInstallMenuAlert() {
115 }
116
117 GlobalError::Severity ExternalInstallMenuAlert::GetSeverity() {
118 return SEVERITY_LOW;
119 }
120
121 bool ExternalInstallMenuAlert::HasMenuItem() {
122 return true;
123 }
124
125 int ExternalInstallMenuAlert::MenuItemCommandID() {
126 return IDC_EXTERNAL_EXTENSION_ALERT;
127 }
128
129 base::string16 ExternalInstallMenuAlert::MenuItemLabel() {
130 return GetMenuItemLabel(error_->GetExtension());
131 }
132
133 void ExternalInstallMenuAlert::ExecuteMenuItem(Browser* browser) {
134 error_->ShowDialog();
135 }
136
137 bool ExternalInstallMenuAlert::HasBubbleView() {
138 return false;
139 }
140
141 bool ExternalInstallMenuAlert::HasShownBubbleView() {
142 NOTREACHED();
143 return true;
144 }
145
146 void ExternalInstallMenuAlert::ShowBubbleView(Browser* browser) {
147 NOTREACHED();
148 }
149
150 GlobalErrorBubbleViewBase* ExternalInstallMenuAlert::GetBubbleView() {
151 return NULL;
152 }
153
154 ////////////////////////////////////////////////////////////////////////////////
155 // ExternalInstallBubbleAlert
156
157 ExternalInstallBubbleAlert::ExternalInstallBubbleAlert(
158 ExternalInstallError* error,
159 ExtensionInstallPrompt::Prompt* prompt)
160 : error_(error),
161 prompt_(prompt) {
162 DCHECK(error_);
163 DCHECK(prompt_);
164 }
165
166 ExternalInstallBubbleAlert::~ExternalInstallBubbleAlert() {
167 }
168
169 GlobalError::Severity ExternalInstallBubbleAlert::GetSeverity() {
170 return SEVERITY_LOW;
171 }
172
173 bool ExternalInstallBubbleAlert::HasMenuItem() {
174 return true;
175 }
176
177 int ExternalInstallBubbleAlert::MenuItemCommandID() {
178 return IDC_EXTERNAL_EXTENSION_ALERT;
179 }
180
181 base::string16 ExternalInstallBubbleAlert::MenuItemLabel() {
182 return GetMenuItemLabel(error_->GetExtension());
183 }
184
185 void ExternalInstallBubbleAlert::ExecuteMenuItem(Browser* browser) {
186 ShowBubbleView(browser);
187 }
188
189 gfx::Image ExternalInstallBubbleAlert::GetBubbleViewIcon() {
190 if (prompt_->icon().IsEmpty())
191 return GlobalErrorWithStandardBubble::GetBubbleViewIcon();
192 // Scale icon to a reasonable size.
193 return gfx::Image(gfx::ImageSkiaOperations::CreateResizedImage(
194 *prompt_->icon().ToImageSkia(),
195 skia::ImageOperations::RESIZE_BEST,
196 gfx::Size(extension_misc::EXTENSION_ICON_SMALL,
197 extension_misc::EXTENSION_ICON_SMALL)));
198 }
199
200 base::string16 ExternalInstallBubbleAlert::GetBubbleViewTitle() {
201 return prompt_->GetDialogTitle();
202 }
203
204 std::vector<base::string16>
205 ExternalInstallBubbleAlert::GetBubbleViewMessages() {
206 std::vector<base::string16> messages;
207 messages.push_back(prompt_->GetHeading());
208 if (prompt_->GetPermissionCount()) {
209 messages.push_back(prompt_->GetPermissionsHeading());
210 for (size_t i = 0; i < prompt_->GetPermissionCount(); ++i) {
211 messages.push_back(l10n_util::GetStringFUTF16(
212 IDS_EXTENSION_PERMISSION_LINE, prompt_->GetPermission(i)));
213 }
214 }
215 // TODO(yoz): OAuth issue advice?
216 return messages;
217 }
218
219 base::string16 ExternalInstallBubbleAlert::GetBubbleViewAcceptButtonLabel() {
220 return prompt_->GetAcceptButtonLabel();
221 }
222
223 base::string16 ExternalInstallBubbleAlert::GetBubbleViewCancelButtonLabel() {
224 return prompt_->GetAbortButtonLabel();
225 }
226
227 void ExternalInstallBubbleAlert::OnBubbleViewDidClose(Browser* browser) {
228 }
229
230 void ExternalInstallBubbleAlert::BubbleViewAcceptButtonPressed(
231 Browser* browser) {
232 error_->InstallUIProceed();
233 }
234
235 void ExternalInstallBubbleAlert::BubbleViewCancelButtonPressed(
236 Browser* browser) {
237 error_->InstallUIAbort(true);
238 }
239
240 } // namespace
241
242 ////////////////////////////////////////////////////////////////////////////////
243 // ExternalInstallError
244
245 ExternalInstallError::ExternalInstallError(
246 content::BrowserContext* browser_context,
247 const std::string& extension_id,
248 AlertType alert_type,
249 ExternalInstallManager* manager)
250 : browser_context_(browser_context),
251 extension_id_(extension_id),
252 alert_type_(alert_type),
253 manager_(manager),
254 error_service_(GlobalErrorServiceFactory::GetForProfile(
255 Profile::FromBrowserContext(browser_context_))),
256 browser_(NULL),
257 weak_factory_(this) {
258 #if !defined(OS_ANDROID)
259 browser_ =
260 chrome::FindTabbedBrowser(Profile::FromBrowserContext(browser_context_),
261 true,
262 chrome::GetActiveDesktop());
263 #endif
264
265 prompt_.reset(new ExtensionInstallPrompt::Prompt(
266 ExtensionInstallPrompt::EXTERNAL_INSTALL_PROMPT));
267
268 webstore_data_fetcher_.reset(new WebstoreDataFetcher(
269 this, browser_context_->GetRequestContext(), GURL(), extension_id_));
270 webstore_data_fetcher_->Start();
271 }
272
273 ExternalInstallError::~ExternalInstallError() {
274 if (global_error_.get())
275 error_service_->RemoveGlobalError(global_error_.get());
276 }
277
278 void ExternalInstallError::InstallUIProceed() {
279 const Extension* extension = GetExtension();
280 if (extension) {
281 ExtensionSystem::Get(browser_context_)
282 ->extension_service()
283 ->GrantPermissionsAndEnableExtension(extension);
284 }
285 manager_->RemoveExternalInstallError();
286 }
287
288 void ExternalInstallError::InstallUIAbort(bool user_initiated) {
289 if (user_initiated && GetExtension()) {
290 ExtensionSystem::Get(browser_context_)
291 ->extension_service()
292 ->UninstallExtension(extension_id_,
293 false, // Not externally uninstalled.
294 NULL); // Ignore error.
295 }
296 manager_->RemoveExternalInstallError();
297 }
298
299 void ExternalInstallError::AcknowledgeExtension() {
300 const Extension* extension = GetExtension();
301 if (extension) {
302 ExtensionSystem::Get(browser_context_)
303 ->extension_service()
304 ->AcknowledgeExternalExtension(extension->id());
305 }
306 }
307
308 void ExternalInstallError::ShowDialog() {
309 DCHECK(install_ui_.get());
310 DCHECK(prompt_.get());
311 DCHECK(show_params_.get());
312 ExtensionInstallPrompt::GetDefaultShowDialogCallback().Run(
313 *show_params_, this, *prompt_);
314 }
315
316 const Extension* ExternalInstallError::GetExtension() const {
317 return ExtensionRegistry::Get(browser_context_)
318 ->GetExtensionById(extension_id_, ExtensionRegistry::EVERYTHING);
319 }
320
321 void ExternalInstallError::OnWebstoreRequestFailure() {
322 OnFetchComplete();
323 }
324
325 void ExternalInstallError::OnWebstoreResponseParseSuccess(
326 scoped_ptr<base::DictionaryValue> webstore_data) {
327 std::string localized_user_count;
328 double average_rating;
329 int rating_count;
330 if (!webstore_data->GetString(kUsersKey, &localized_user_count) ||
331 !webstore_data->GetDouble(kAverageRatingKey, &average_rating) ||
332 !webstore_data->GetInteger(kRatingCountKey, &rating_count)) {
333 // If we don't get a valid webstore response, short circuit, and continue
334 // to show a prompt without webstore data.
335 OnFetchComplete();
336 return;
337 }
338
339 bool show_user_count = true;
340 webstore_data->GetBoolean(kShowUserCountKey, &show_user_count);
341
342 prompt_->SetWebstoreData(
343 localized_user_count, show_user_count, average_rating, rating_count);
344 OnFetchComplete();
345 }
346
347 void ExternalInstallError::OnWebstoreResponseParseFailure(
348 const std::string& error) {
349 OnFetchComplete();
350 }
351
352 void ExternalInstallError::OnFetchComplete() {
353 install_ui_.reset(
354 ExtensionInstallUI::CreateInstallPromptWithBrowser(browser_));
355
356 install_ui_->ConfirmExternalInstall(
357 this,
358 GetExtension(),
359 base::Bind(&ExternalInstallError::OnDialogReady,
360 weak_factory_.GetWeakPtr()),
361 *prompt_);
362 }
363
364 void ExternalInstallError::OnDialogReady(
365 const ExtensionInstallPrompt::ShowParams& show_params,
366 ExtensionInstallPrompt::Delegate* prompt_delegate,
367 const ExtensionInstallPrompt::Prompt& prompt) {
368 DCHECK_EQ(this, prompt_delegate);
369 show_params_.reset(new ExtensionInstallPrompt::ShowParams(show_params));
370 prompt_.reset(new ExtensionInstallPrompt::Prompt(prompt));
371
372 if (alert_type_ == BUBBLE_ALERT) {
373 global_error_.reset(new ExternalInstallBubbleAlert(this, prompt_.get()));
374 error_service_->AddGlobalError(global_error_.get());
375 if (browser_)
376 global_error_->ShowBubbleView(browser_);
377 } else {
378 DCHECK(alert_type_ == MENU_ALERT);
379 global_error_.reset(new ExternalInstallMenuAlert(this));
380 error_service_->AddGlobalError(global_error_.get());
381 }
382 }
383
384 } // namespace extensions
OLDNEW
« no previous file with comments | « chrome/browser/extensions/external_install_error.h ('k') | chrome/browser/extensions/external_install_manager.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698