• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2013 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/install_tracker.h"
6 
7 #include "base/bind.h"
8 #include "chrome/browser/chrome_notification_types.h"
9 #include "chrome/browser/extensions/install_tracker_factory.h"
10 #include "content/public/browser/notification_service.h"
11 #include "extensions/browser/extension_prefs.h"
12 #include "extensions/browser/extension_registry.h"
13 #include "extensions/browser/pref_names.h"
14 
15 namespace extensions {
16 
InstallTracker(content::BrowserContext * browser_context,extensions::ExtensionPrefs * prefs)17 InstallTracker::InstallTracker(content::BrowserContext* browser_context,
18                                extensions::ExtensionPrefs* prefs)
19     : extension_registry_observer_(this) {
20   registrar_.Add(this,
21                  extensions::NOTIFICATION_EXTENSION_UPDATE_DISABLED,
22                  content::Source<content::BrowserContext>(browser_context));
23   registrar_.Add(this,
24                  chrome::NOTIFICATION_APP_INSTALLED_TO_APPLIST,
25                  content::Source<content::BrowserContext>(browser_context));
26   extension_registry_observer_.Add(ExtensionRegistry::Get(browser_context));
27 
28   // Prefs may be null in tests.
29   if (prefs) {
30     AppSorting* sorting = prefs->app_sorting();
31     registrar_.Add(this,
32                    chrome::NOTIFICATION_APP_LAUNCHER_REORDERED,
33                    content::Source<AppSorting>(sorting));
34     pref_change_registrar_.Init(prefs->pref_service());
35     pref_change_registrar_.Add(
36         pref_names::kExtensions,
37         base::Bind(&InstallTracker::OnAppsReordered, base::Unretained(this)));
38   }
39 }
40 
~InstallTracker()41 InstallTracker::~InstallTracker() {
42 }
43 
44 // static
Get(content::BrowserContext * context)45 InstallTracker* InstallTracker::Get(content::BrowserContext* context) {
46   return InstallTrackerFactory::GetForBrowserContext(context);
47 }
48 
AddObserver(InstallObserver * observer)49 void InstallTracker::AddObserver(InstallObserver* observer) {
50   observers_.AddObserver(observer);
51 }
52 
RemoveObserver(InstallObserver * observer)53 void InstallTracker::RemoveObserver(InstallObserver* observer) {
54   observers_.RemoveObserver(observer);
55 }
56 
GetActiveInstall(const std::string & extension_id) const57 const ActiveInstallData* InstallTracker::GetActiveInstall(
58     const std::string& extension_id) const {
59   ActiveInstallsMap::const_iterator install_data =
60       active_installs_.find(extension_id);
61   if (install_data == active_installs_.end())
62     return NULL;
63   else
64     return &(install_data->second);
65 }
66 
AddActiveInstall(const ActiveInstallData & install_data)67 void InstallTracker::AddActiveInstall(const ActiveInstallData& install_data) {
68   DCHECK(!install_data.extension_id.empty());
69   DCHECK(active_installs_.find(install_data.extension_id) ==
70          active_installs_.end());
71   active_installs_.insert(
72       std::make_pair(install_data.extension_id, install_data));
73 }
74 
RemoveActiveInstall(const std::string & extension_id)75 void InstallTracker::RemoveActiveInstall(const std::string& extension_id) {
76   active_installs_.erase(extension_id);
77 }
78 
OnBeginExtensionInstall(const InstallObserver::ExtensionInstallParams & params)79 void InstallTracker::OnBeginExtensionInstall(
80     const InstallObserver::ExtensionInstallParams& params) {
81   ActiveInstallsMap::iterator install_data =
82       active_installs_.find(params.extension_id);
83   if (install_data == active_installs_.end()) {
84     ActiveInstallData install_data(params.extension_id);
85     install_data.is_ephemeral = params.is_ephemeral;
86     active_installs_.insert(std::make_pair(params.extension_id, install_data));
87   }
88 
89   FOR_EACH_OBSERVER(InstallObserver, observers_,
90                     OnBeginExtensionInstall(params));
91 }
92 
OnBeginExtensionDownload(const std::string & extension_id)93 void InstallTracker::OnBeginExtensionDownload(const std::string& extension_id) {
94   FOR_EACH_OBSERVER(
95       InstallObserver, observers_, OnBeginExtensionDownload(extension_id));
96 }
97 
OnDownloadProgress(const std::string & extension_id,int percent_downloaded)98 void InstallTracker::OnDownloadProgress(const std::string& extension_id,
99                                         int percent_downloaded) {
100   ActiveInstallsMap::iterator install_data =
101       active_installs_.find(extension_id);
102   if (install_data != active_installs_.end()) {
103     install_data->second.percent_downloaded = percent_downloaded;
104   } else {
105     NOTREACHED();
106   }
107 
108   FOR_EACH_OBSERVER(InstallObserver, observers_,
109                     OnDownloadProgress(extension_id, percent_downloaded));
110 }
111 
OnBeginCrxInstall(const std::string & extension_id)112 void InstallTracker::OnBeginCrxInstall(const std::string& extension_id) {
113   FOR_EACH_OBSERVER(
114       InstallObserver, observers_, OnBeginCrxInstall(extension_id));
115 }
116 
OnFinishCrxInstall(const std::string & extension_id,bool success)117 void InstallTracker::OnFinishCrxInstall(const std::string& extension_id,
118                                         bool success) {
119   FOR_EACH_OBSERVER(
120       InstallObserver, observers_, OnFinishCrxInstall(extension_id, success));
121 }
122 
OnInstallFailure(const std::string & extension_id)123 void InstallTracker::OnInstallFailure(
124     const std::string& extension_id) {
125   RemoveActiveInstall(extension_id);
126   FOR_EACH_OBSERVER(InstallObserver, observers_,
127                     OnInstallFailure(extension_id));
128 }
129 
Shutdown()130 void InstallTracker::Shutdown() {
131   FOR_EACH_OBSERVER(InstallObserver, observers_, OnShutdown());
132 }
133 
Observe(int type,const content::NotificationSource & source,const content::NotificationDetails & details)134 void InstallTracker::Observe(int type,
135                              const content::NotificationSource& source,
136                              const content::NotificationDetails& details) {
137   switch (type) {
138     case extensions::NOTIFICATION_EXTENSION_UPDATE_DISABLED: {
139       const Extension* extension =
140           content::Details<const Extension>(details).ptr();
141       FOR_EACH_OBSERVER(
142           InstallObserver, observers_, OnDisabledExtensionUpdated(extension));
143       break;
144     }
145     case chrome::NOTIFICATION_APP_LAUNCHER_REORDERED: {
146       FOR_EACH_OBSERVER(InstallObserver, observers_, OnAppsReordered());
147       break;
148     }
149     case chrome::NOTIFICATION_APP_INSTALLED_TO_APPLIST: {
150       const std::string& extension_id(
151           *content::Details<const std::string>(details).ptr());
152       FOR_EACH_OBSERVER(InstallObserver, observers_,
153                         OnAppInstalledToAppList(extension_id));
154       break;
155     }
156     default:
157       NOTREACHED();
158   }
159 }
160 
OnExtensionInstalled(content::BrowserContext * browser_context,const Extension * extension,bool is_update)161 void InstallTracker::OnExtensionInstalled(
162     content::BrowserContext* browser_context,
163     const Extension* extension,
164     bool is_update) {
165   RemoveActiveInstall(extension->id());
166 }
167 
OnAppsReordered()168 void InstallTracker::OnAppsReordered() {
169   FOR_EACH_OBSERVER(InstallObserver, observers_, OnAppsReordered());
170 }
171 
172 }  // namespace extensions
173