Index: chrome/browser/extensions/external_install_ui.cc |
diff --git a/chrome/browser/extensions/external_install_ui.cc b/chrome/browser/extensions/external_install_ui.cc |
deleted file mode 100644 |
index 0f786468a00ff39f21e2df01a73b1824128013be..0000000000000000000000000000000000000000 |
--- a/chrome/browser/extensions/external_install_ui.cc |
+++ /dev/null |
@@ -1,590 +0,0 @@ |
-// Copyright (c) 2012 The Chromium Authors. All rights reserved. |
-// Use of this source code is governed by a BSD-style license that can be |
-// found in the LICENSE file. |
- |
-#include "chrome/browser/extensions/external_install_ui.h" |
- |
-#include <string> |
- |
-#include "base/bind.h" |
-#include "base/lazy_instance.h" |
-#include "base/memory/ref_counted.h" |
-#include "base/memory/scoped_ptr.h" |
-#include "base/message_loop/message_loop.h" |
-#include "base/metrics/histogram.h" |
-#include "base/scoped_observer.h" |
-#include "base/strings/utf_string_conversions.h" |
-#include "chrome/app/chrome_command_ids.h" |
-#include "chrome/browser/chrome_notification_types.h" |
-#include "chrome/browser/extensions/extension_install_prompt.h" |
-#include "chrome/browser/extensions/extension_install_ui.h" |
-#include "chrome/browser/extensions/extension_service.h" |
-#include "chrome/browser/extensions/extension_uninstall_dialog.h" |
-#include "chrome/browser/extensions/webstore_data_fetcher.h" |
-#include "chrome/browser/extensions/webstore_data_fetcher_delegate.h" |
-#include "chrome/browser/profiles/profile.h" |
-#include "chrome/browser/ui/browser.h" |
-#include "chrome/browser/ui/browser_finder.h" |
-#include "chrome/browser/ui/global_error/global_error.h" |
-#include "chrome/browser/ui/global_error/global_error_service.h" |
-#include "chrome/browser/ui/global_error/global_error_service_factory.h" |
-#include "chrome/common/extensions/manifest_url_handler.h" |
-#include "content/public/browser/notification_details.h" |
-#include "content/public/browser/notification_observer.h" |
-#include "content/public/browser/notification_registrar.h" |
-#include "content/public/browser/notification_source.h" |
-#include "extensions/browser/extension_registry.h" |
-#include "extensions/browser/extension_registry_observer.h" |
-#include "extensions/common/constants.h" |
-#include "grit/generated_resources.h" |
-#include "ui/base/l10n/l10n_util.h" |
-#include "ui/gfx/image/image.h" |
-#include "ui/gfx/image/image_skia_operations.h" |
- |
-namespace extensions { |
- |
-namespace { |
- |
-// Whether the external extension can use the streamlined bubble install flow. |
-bool UseBubbleInstall(const Extension* extension, bool is_new_profile) { |
- return ManifestURL::UpdatesFromGallery(extension) && !is_new_profile; |
-} |
- |
-} // namespace |
- |
-static const int kMenuCommandId = IDC_EXTERNAL_EXTENSION_ALERT; |
- |
-class ExternalInstallGlobalError; |
- |
-namespace extensions { |
-class ExtensionRegistry; |
-} |
- |
-// This class is refcounted to stay alive while we try and pull webstore data. |
-class ExternalInstallDialogDelegate |
- : public ExtensionInstallPrompt::Delegate, |
- public WebstoreDataFetcherDelegate, |
- public content::NotificationObserver, |
- public base::RefCountedThreadSafe<ExternalInstallDialogDelegate> { |
- public: |
- ExternalInstallDialogDelegate(Browser* browser, |
- ExtensionService* service, |
- const Extension* extension, |
- bool use_global_error); |
- |
- Browser* browser() { return browser_; } |
- |
- private: |
- friend class base::RefCountedThreadSafe<ExternalInstallDialogDelegate>; |
- friend class ExternalInstallGlobalError; |
- |
- virtual ~ExternalInstallDialogDelegate(); |
- |
- // ExtensionInstallPrompt::Delegate: |
- virtual void InstallUIProceed() OVERRIDE; |
- virtual void InstallUIAbort(bool user_initiated) OVERRIDE; |
- |
- // WebstoreDataFetcherDelegate: |
- virtual void OnWebstoreRequestFailure() OVERRIDE; |
- virtual void OnWebstoreResponseParseSuccess( |
- scoped_ptr<base::DictionaryValue> webstore_data) OVERRIDE; |
- virtual void OnWebstoreResponseParseFailure( |
- const std::string& error) OVERRIDE; |
- |
- // content::NotificationObserver: |
- virtual void Observe(int type, |
- const content::NotificationSource& source, |
- const content::NotificationDetails& details) OVERRIDE; |
- |
- // Show the install dialog to the user. |
- void ShowInstallUI(); |
- |
- // The UI for showing the install dialog when enabling. |
- scoped_ptr<ExtensionInstallPrompt> install_ui_; |
- scoped_ptr<ExtensionInstallPrompt::Prompt> prompt_; |
- |
- Browser* browser_; |
- base::WeakPtr<ExtensionService> service_weak_; |
- scoped_ptr<WebstoreDataFetcher> webstore_data_fetcher_; |
- content::NotificationRegistrar registrar_; |
- std::string extension_id_; |
- bool use_global_error_; |
- |
- DISALLOW_COPY_AND_ASSIGN(ExternalInstallDialogDelegate); |
-}; |
- |
-// Only shows a menu item, no bubble. Clicking the menu item shows |
-// an external install dialog. |
-class ExternalInstallMenuAlert : public GlobalErrorWithStandardBubble, |
- public content::NotificationObserver, |
- public ExtensionRegistryObserver { |
- public: |
- ExternalInstallMenuAlert(ExtensionService* service, |
- const Extension* extension); |
- virtual ~ExternalInstallMenuAlert(); |
- |
- // GlobalError implementation. |
- virtual Severity GetSeverity() OVERRIDE; |
- virtual bool HasMenuItem() OVERRIDE; |
- virtual int MenuItemCommandID() OVERRIDE; |
- virtual base::string16 MenuItemLabel() OVERRIDE; |
- virtual void ExecuteMenuItem(Browser* browser) OVERRIDE; |
- virtual bool HasBubbleView() OVERRIDE; |
- virtual base::string16 GetBubbleViewTitle() OVERRIDE; |
- virtual std::vector<base::string16> GetBubbleViewMessages() OVERRIDE; |
- virtual base::string16 GetBubbleViewAcceptButtonLabel() OVERRIDE; |
- virtual base::string16 GetBubbleViewCancelButtonLabel() OVERRIDE; |
- virtual void OnBubbleViewDidClose(Browser* browser) OVERRIDE; |
- virtual void BubbleViewAcceptButtonPressed(Browser* browser) OVERRIDE; |
- virtual void BubbleViewCancelButtonPressed(Browser* browser) OVERRIDE; |
- |
- protected: |
- ExtensionService* service_; |
- const Extension* extension_; |
- |
- private: |
- // Delete this instance after cleaning jobs. |
- void Clean(); |
- |
- // content::NotificationObserver implementation. |
- virtual void Observe(int type, |
- const content::NotificationSource& source, |
- const content::NotificationDetails& details) OVERRIDE; |
- |
- // ExtensionRegistryObserver implementation. |
- virtual void OnExtensionLoaded(content::BrowserContext* browser_context, |
- const Extension* extension) OVERRIDE; |
- |
- content::NotificationRegistrar registrar_; |
- |
- // Listen to extension load notifications. |
- ScopedObserver<ExtensionRegistry, ExtensionRegistryObserver> |
- extension_registry_observer_; |
- |
- DISALLOW_COPY_AND_ASSIGN(ExternalInstallMenuAlert); |
-}; |
- |
-// Shows a menu item and a global error bubble, replacing the install dialog. |
-class ExternalInstallGlobalError : public ExternalInstallMenuAlert { |
- public: |
- ExternalInstallGlobalError(ExtensionService* service, |
- const Extension* extension, |
- ExternalInstallDialogDelegate* delegate, |
- const ExtensionInstallPrompt::Prompt& prompt); |
- virtual ~ExternalInstallGlobalError(); |
- |
- virtual void ExecuteMenuItem(Browser* browser) OVERRIDE; |
- virtual bool HasBubbleView() OVERRIDE; |
- virtual gfx::Image GetBubbleViewIcon() OVERRIDE; |
- virtual base::string16 GetBubbleViewTitle() OVERRIDE; |
- virtual std::vector<base::string16> GetBubbleViewMessages() OVERRIDE; |
- virtual base::string16 GetBubbleViewAcceptButtonLabel() OVERRIDE; |
- virtual base::string16 GetBubbleViewCancelButtonLabel() OVERRIDE; |
- virtual void OnBubbleViewDidClose(Browser* browser) OVERRIDE; |
- virtual void BubbleViewAcceptButtonPressed(Browser* browser) OVERRIDE; |
- virtual void BubbleViewCancelButtonPressed(Browser* browser) OVERRIDE; |
- |
- protected: |
- // Ref-counted, but needs to be disposed of if we are dismissed without |
- // having been clicked (perhaps because the user enabled the extension |
- // manually). |
- ExternalInstallDialogDelegate* delegate_; |
- const ExtensionInstallPrompt::Prompt* prompt_; |
- |
- private: |
- DISALLOW_COPY_AND_ASSIGN(ExternalInstallGlobalError); |
-}; |
- |
-static void CreateExternalInstallGlobalError( |
- base::WeakPtr<ExtensionService> service, |
- const std::string& extension_id, |
- const ExtensionInstallPrompt::ShowParams& show_params, |
- ExtensionInstallPrompt::Delegate* prompt_delegate, |
- const ExtensionInstallPrompt::Prompt& prompt) { |
- if (!service.get()) |
- return; |
- const Extension* extension = service->GetInstalledExtension(extension_id); |
- if (!extension) |
- return; |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service->profile()); |
- if (error_service->GetGlobalErrorByMenuItemCommandID(kMenuCommandId)) |
- return; |
- |
- ExternalInstallDialogDelegate* delegate = |
- static_cast<ExternalInstallDialogDelegate*>(prompt_delegate); |
- ExternalInstallGlobalError* error_bubble = new ExternalInstallGlobalError( |
- service.get(), extension, delegate, prompt); |
- error_service->AddGlobalError(error_bubble); |
- // Show bubble immediately if possible. |
- if (delegate->browser()) |
- error_bubble->ShowBubbleView(delegate->browser()); |
-} |
- |
-static void ShowExternalInstallDialog( |
- ExtensionService* service, |
- Browser* browser, |
- const Extension* extension) { |
- // This object manages its own lifetime. |
- new ExternalInstallDialogDelegate(browser, service, extension, false); |
-} |
- |
-// ExternalInstallDialogDelegate -------------------------------------------- |
- |
-ExternalInstallDialogDelegate::ExternalInstallDialogDelegate( |
- Browser* browser, |
- ExtensionService* service, |
- const Extension* extension, |
- bool use_global_error) |
- : browser_(browser), |
- service_weak_(service->AsWeakPtr()), |
- extension_id_(extension->id()), |
- use_global_error_(use_global_error) { |
- AddRef(); // Balanced in Proceed or Abort. |
- |
- prompt_.reset(new ExtensionInstallPrompt::Prompt( |
- ExtensionInstallPrompt::EXTERNAL_INSTALL_PROMPT)); |
- |
- // If we don't have a browser, we can't go to the webstore to fetch data. |
- // This should only happen in tests. |
- if (!browser) { |
- ShowInstallUI(); |
- return; |
- } |
- |
- // Make sure to be notified if the owning profile is destroyed. |
- registrar_.Add(this, |
- chrome::NOTIFICATION_PROFILE_DESTROYED, |
- content::Source<Profile>(browser->profile())); |
- |
- webstore_data_fetcher_.reset(new WebstoreDataFetcher( |
- this, |
- browser->profile()->GetRequestContext(), |
- GURL::EmptyGURL(), |
- extension->id())); |
- webstore_data_fetcher_->Start(); |
-} |
- |
-void ExternalInstallDialogDelegate::OnWebstoreRequestFailure() { |
- ShowInstallUI(); |
-} |
- |
-void ExternalInstallDialogDelegate::OnWebstoreResponseParseSuccess( |
- scoped_ptr<base::DictionaryValue> webstore_data) { |
- std::string localized_user_count; |
- double average_rating; |
- int rating_count; |
- if (!webstore_data->GetString(kUsersKey, &localized_user_count) || |
- !webstore_data->GetDouble(kAverageRatingKey, &average_rating) || |
- !webstore_data->GetInteger(kRatingCountKey, &rating_count)) { |
- // If we don't get a valid webstore response, short circuit, and continue |
- // to show a prompt without webstore data. |
- ShowInstallUI(); |
- return; |
- } |
- |
- bool show_user_count = true; |
- webstore_data->GetBoolean(kShowUserCountKey, &show_user_count); |
- |
- prompt_->SetWebstoreData(localized_user_count, |
- show_user_count, |
- average_rating, |
- rating_count); |
- |
- ShowInstallUI(); |
-} |
- |
-void ExternalInstallDialogDelegate::OnWebstoreResponseParseFailure( |
- const std::string& error) { |
- ShowInstallUI(); |
-} |
- |
-void ExternalInstallDialogDelegate::Observe( |
- int type, |
- const content::NotificationSource& source, |
- const content::NotificationDetails& details) { |
- DCHECK_EQ(type, chrome::NOTIFICATION_PROFILE_DESTROYED); |
- // If the owning profile is destroyed, we need to abort so that we don't leak. |
- InstallUIAbort(false); // Not user initiated. |
-} |
- |
-void ExternalInstallDialogDelegate::ShowInstallUI() { |
- const Extension* extension = NULL; |
- if (!service_weak_.get() || |
- !(extension = service_weak_->GetInstalledExtension(extension_id_))) { |
- return; |
- } |
- install_ui_.reset( |
- ExtensionInstallUI::CreateInstallPromptWithBrowser(browser_)); |
- |
- const ExtensionInstallPrompt::ShowDialogCallback callback = |
- use_global_error_ ? |
- base::Bind(&CreateExternalInstallGlobalError, |
- service_weak_, |
- extension_id_) : |
- ExtensionInstallPrompt::GetDefaultShowDialogCallback(); |
- |
- install_ui_->ConfirmExternalInstall(this, extension, callback, *prompt_); |
-} |
- |
-ExternalInstallDialogDelegate::~ExternalInstallDialogDelegate() { |
-} |
- |
-void ExternalInstallDialogDelegate::InstallUIProceed() { |
- const Extension* extension = NULL; |
- if (service_weak_.get() && |
- (extension = service_weak_->GetInstalledExtension(extension_id_))) { |
- service_weak_->GrantPermissionsAndEnableExtension(extension); |
- } |
- Release(); |
-} |
- |
-void ExternalInstallDialogDelegate::InstallUIAbort(bool user_initiated) { |
- const Extension* extension = NULL; |
- |
- // Uninstall the extension if the abort was user initiated (and not, e.g., the |
- // result of the window closing). |
- // Otherwise, the extension will remain installed, but unacknowledged, so it |
- // will be prompted again. |
- if (user_initiated && |
- service_weak_.get() && |
- (extension = service_weak_->GetInstalledExtension(extension_id_))) { |
- service_weak_->UninstallExtension(extension_id_, false, NULL); |
- } |
- Release(); |
-} |
- |
-// ExternalInstallMenuAlert ------------------------------------------------- |
- |
-ExternalInstallMenuAlert::ExternalInstallMenuAlert(ExtensionService* service, |
- const Extension* extension) |
- : service_(service), |
- extension_(extension), |
- extension_registry_observer_(this) { |
- extension_registry_observer_.Add(ExtensionRegistry::Get(service->profile())); |
- registrar_.Add(this, chrome::NOTIFICATION_EXTENSION_REMOVED, |
- content::Source<Profile>(service->profile())); |
-} |
- |
-ExternalInstallMenuAlert::~ExternalInstallMenuAlert() { |
-} |
- |
-GlobalError::Severity ExternalInstallMenuAlert::GetSeverity() { |
- return SEVERITY_LOW; |
-} |
- |
-bool ExternalInstallMenuAlert::HasMenuItem() { |
- return true; |
-} |
- |
-int ExternalInstallMenuAlert::MenuItemCommandID() { |
- return kMenuCommandId; |
-} |
- |
-base::string16 ExternalInstallMenuAlert::MenuItemLabel() { |
- int id = -1; |
- if (extension_->is_app()) |
- id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_APP; |
- else if (extension_->is_theme()) |
- id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_THEME; |
- else |
- id = IDS_EXTENSION_EXTERNAL_INSTALL_ALERT_EXTENSION; |
- return l10n_util::GetStringFUTF16(id, base::UTF8ToUTF16(extension_->name())); |
-} |
- |
-void ExternalInstallMenuAlert::ExecuteMenuItem(Browser* browser) { |
- ShowExternalInstallDialog(service_, browser, extension_); |
-} |
- |
-bool ExternalInstallMenuAlert::HasBubbleView() { |
- return false; |
-} |
-base::string16 ExternalInstallMenuAlert::GetBubbleViewTitle() { |
- return base::string16(); |
-} |
- |
-std::vector<base::string16> ExternalInstallMenuAlert::GetBubbleViewMessages() { |
- return std::vector<base::string16>(); |
-} |
- |
-base::string16 ExternalInstallMenuAlert::GetBubbleViewAcceptButtonLabel() { |
- return base::string16(); |
-} |
- |
-base::string16 ExternalInstallMenuAlert::GetBubbleViewCancelButtonLabel() { |
- return base::string16(); |
-} |
- |
-void ExternalInstallMenuAlert::OnBubbleViewDidClose(Browser* browser) { |
- NOTREACHED(); |
-} |
- |
-void ExternalInstallMenuAlert::BubbleViewAcceptButtonPressed( |
- Browser* browser) { |
- NOTREACHED(); |
-} |
- |
-void ExternalInstallMenuAlert::BubbleViewCancelButtonPressed( |
- Browser* browser) { |
- NOTREACHED(); |
-} |
- |
-void ExternalInstallMenuAlert::OnExtensionLoaded( |
- content::BrowserContext* browser_context, |
- const Extension* extension) { |
- if (extension == extension_) |
- Clean(); |
-} |
- |
-void ExternalInstallMenuAlert::Observe( |
- int type, |
- const content::NotificationSource& source, |
- const content::NotificationDetails& details) { |
- // The error is invalidated if the extension has been loaded or removed. |
- DCHECK_EQ(type, chrome::NOTIFICATION_EXTENSION_REMOVED); |
- const Extension* extension = content::Details<const Extension>(details).ptr(); |
- if (extension == extension_) |
- Clean(); |
-} |
- |
-void ExternalInstallMenuAlert::Clean() { |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service_->profile()); |
- error_service->RemoveGlobalError(this); |
- service_->AcknowledgeExternalExtension(extension_->id()); |
- delete this; |
-} |
- |
-// ExternalInstallGlobalError ----------------------------------------------- |
- |
-ExternalInstallGlobalError::ExternalInstallGlobalError( |
- ExtensionService* service, |
- const Extension* extension, |
- ExternalInstallDialogDelegate* delegate, |
- const ExtensionInstallPrompt::Prompt& prompt) |
- : ExternalInstallMenuAlert(service, extension), |
- delegate_(delegate), |
- prompt_(&prompt) { |
-} |
- |
-ExternalInstallGlobalError::~ExternalInstallGlobalError() { |
- if (delegate_) |
- delegate_->Release(); |
-} |
- |
-void ExternalInstallGlobalError::ExecuteMenuItem(Browser* browser) { |
- ShowBubbleView(browser); |
-} |
- |
-bool ExternalInstallGlobalError::HasBubbleView() { |
- return true; |
-} |
- |
-gfx::Image ExternalInstallGlobalError::GetBubbleViewIcon() { |
- if (prompt_->icon().IsEmpty()) |
- return GlobalErrorWithStandardBubble::GetBubbleViewIcon(); |
- // Scale icon to a reasonable size. |
- return gfx::Image(gfx::ImageSkiaOperations::CreateResizedImage( |
- *prompt_->icon().ToImageSkia(), |
- skia::ImageOperations::RESIZE_BEST, |
- gfx::Size(extension_misc::EXTENSION_ICON_SMALL, |
- extension_misc::EXTENSION_ICON_SMALL))); |
-} |
- |
-base::string16 ExternalInstallGlobalError::GetBubbleViewTitle() { |
- return prompt_->GetDialogTitle(); |
-} |
- |
-std::vector<base::string16> |
-ExternalInstallGlobalError::GetBubbleViewMessages() { |
- std::vector<base::string16> messages; |
- messages.push_back(prompt_->GetHeading()); |
- if (prompt_->GetPermissionCount()) { |
- messages.push_back(prompt_->GetPermissionsHeading()); |
- for (size_t i = 0; i < prompt_->GetPermissionCount(); ++i) { |
- messages.push_back(l10n_util::GetStringFUTF16( |
- IDS_EXTENSION_PERMISSION_LINE, |
- prompt_->GetPermission(i))); |
- } |
- } |
- // TODO(yoz): OAuth issue advice? |
- return messages; |
-} |
- |
-base::string16 ExternalInstallGlobalError::GetBubbleViewAcceptButtonLabel() { |
- return prompt_->GetAcceptButtonLabel(); |
-} |
- |
-base::string16 ExternalInstallGlobalError::GetBubbleViewCancelButtonLabel() { |
- return prompt_->GetAbortButtonLabel(); |
-} |
- |
-void ExternalInstallGlobalError::OnBubbleViewDidClose(Browser* browser) { |
-} |
- |
-void ExternalInstallGlobalError::BubbleViewAcceptButtonPressed( |
- Browser* browser) { |
- ExternalInstallDialogDelegate* delegate = delegate_; |
- delegate_ = NULL; |
- delegate->InstallUIProceed(); |
-} |
- |
-void ExternalInstallGlobalError::BubbleViewCancelButtonPressed( |
- Browser* browser) { |
- ExternalInstallDialogDelegate* delegate = delegate_; |
- delegate_ = NULL; |
- delegate->InstallUIAbort(true); |
-} |
- |
-// Public interface --------------------------------------------------------- |
- |
-void AddExternalInstallError(ExtensionService* service, |
- const Extension* extension, |
- bool is_new_profile) { |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service->profile()); |
- if (error_service->GetGlobalErrorByMenuItemCommandID(kMenuCommandId)) |
- return; |
- |
- if (UseBubbleInstall(extension, is_new_profile)) { |
- Browser* browser = NULL; |
-#if !defined(OS_ANDROID) |
- browser = chrome::FindTabbedBrowser(service->profile(), |
- true, |
- chrome::GetActiveDesktop()); |
-#endif |
- new ExternalInstallDialogDelegate(browser, service, extension, true); |
- } else { |
- error_service->AddGlobalError( |
- new ExternalInstallMenuAlert(service, extension)); |
- } |
-} |
- |
-void RemoveExternalInstallError(ExtensionService* service) { |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service->profile()); |
- GlobalError* error = error_service->GetGlobalErrorByMenuItemCommandID( |
- kMenuCommandId); |
- if (error) { |
- error_service->RemoveGlobalError(error); |
- delete error; |
- } |
-} |
- |
-bool HasExternalInstallError(ExtensionService* service) { |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service->profile()); |
- GlobalError* error = error_service->GetGlobalErrorByMenuItemCommandID( |
- kMenuCommandId); |
- return !!error; |
-} |
- |
-bool HasExternalInstallBubble(ExtensionService* service) { |
- GlobalErrorService* error_service = |
- GlobalErrorServiceFactory::GetForProfile(service->profile()); |
- GlobalError* error = error_service->GetGlobalErrorByMenuItemCommandID( |
- kMenuCommandId); |
- return error && error->HasBubbleView(); |
-} |
- |
-} // namespace extensions |