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

Side by Side Diff: chrome/browser/ui/app_list/app_list_syncable_service.cc

Issue 981893002: Lazily build the app list model. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@fix_set_enabled
Patch Set: revert ALSL Created 5 years, 8 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
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/ui/app_list/app_list_syncable_service.h" 5 #include "chrome/browser/ui/app_list/app_list_syncable_service.h"
6 6
7 #include "base/command_line.h" 7 #include "base/command_line.h"
8 #include "base/strings/string_util.h" 8 #include "base/strings/string_util.h"
9 #include "chrome/browser/apps/drive/drive_app_provider.h" 9 #include "chrome/browser/apps/drive/drive_app_provider.h"
10 #include "chrome/browser/chrome_notification_types.h"
11 #include "chrome/browser/extensions/extension_service.h" 10 #include "chrome/browser/extensions/extension_service.h"
12 #include "chrome/browser/profiles/profile.h" 11 #include "chrome/browser/profiles/profile.h"
13 #include "chrome/browser/ui/app_list/app_list_prefs.h" 12 #include "chrome/browser/ui/app_list/app_list_prefs.h"
14 #include "chrome/browser/ui/app_list/app_list_service.h" 13 #include "chrome/browser/ui/app_list/app_list_service.h"
15 #include "chrome/browser/ui/app_list/extension_app_item.h" 14 #include "chrome/browser/ui/app_list/extension_app_item.h"
16 #include "chrome/browser/ui/app_list/extension_app_model_builder.h" 15 #include "chrome/browser/ui/app_list/extension_app_model_builder.h"
17 #include "chrome/browser/ui/app_list/model_pref_updater.h" 16 #include "chrome/browser/ui/app_list/model_pref_updater.h"
18 #include "chrome/browser/ui/host_desktop.h" 17 #include "chrome/browser/ui/host_desktop.h"
19 #include "chrome/common/chrome_switches.h" 18 #include "chrome/common/chrome_switches.h"
20 #include "chrome/common/extensions/extension_constants.h" 19 #include "chrome/common/extensions/extension_constants.h"
21 #include "chrome/grit/generated_resources.h" 20 #include "chrome/grit/generated_resources.h"
22 #include "content/public/browser/notification_source.h"
23 #include "extensions/browser/extension_prefs.h" 21 #include "extensions/browser/extension_prefs.h"
24 #include "extensions/browser/extension_system.h" 22 #include "extensions/browser/extension_system.h"
25 #include "extensions/browser/uninstall_reason.h" 23 #include "extensions/browser/uninstall_reason.h"
26 #include "extensions/common/constants.h" 24 #include "extensions/common/constants.h"
27 #include "sync/api/sync_change_processor.h" 25 #include "sync/api/sync_change_processor.h"
28 #include "sync/api/sync_data.h" 26 #include "sync/api/sync_data.h"
29 #include "sync/api/sync_merge_result.h" 27 #include "sync/api/sync_merge_result.h"
30 #include "sync/protocol/sync.pb.h" 28 #include "sync/protocol/sync.pb.h"
31 #include "ui/app_list/app_list_folder_item.h" 29 #include "ui/app_list/app_list_folder_item.h"
32 #include "ui/app_list/app_list_item.h" 30 #include "ui/app_list/app_list_item.h"
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after
174 } 172 }
175 173
176 // AppListSyncableService::ModelObserver 174 // AppListSyncableService::ModelObserver
177 175
178 class AppListSyncableService::ModelObserver : public AppListModelObserver { 176 class AppListSyncableService::ModelObserver : public AppListModelObserver {
179 public: 177 public:
180 explicit ModelObserver(AppListSyncableService* owner) 178 explicit ModelObserver(AppListSyncableService* owner)
181 : owner_(owner), 179 : owner_(owner),
182 adding_item_(NULL) { 180 adding_item_(NULL) {
183 DVLOG(2) << owner_ << ": ModelObserver Added"; 181 DVLOG(2) << owner_ << ": ModelObserver Added";
184 owner_->model()->AddObserver(this); 182 owner_->GetModel()->AddObserver(this);
185 } 183 }
186 184
187 ~ModelObserver() override { 185 ~ModelObserver() override {
188 owner_->model()->RemoveObserver(this); 186 owner_->GetModel()->RemoveObserver(this);
189 DVLOG(2) << owner_ << ": ModelObserver Removed"; 187 DVLOG(2) << owner_ << ": ModelObserver Removed";
190 } 188 }
191 189
192 private: 190 private:
193 // AppListModelObserver 191 // AppListModelObserver
194 void OnAppListItemAdded(AppListItem* item) override { 192 void OnAppListItemAdded(AppListItem* item) override {
195 DCHECK(!adding_item_); 193 DCHECK(!adding_item_);
196 adding_item_ = item; // Ignore updates while adding an item. 194 adding_item_ = item; // Ignore updates while adding an item.
197 VLOG(2) << owner_ << " OnAppListItemAdded: " << item->ToDebugString(); 195 VLOG(2) << owner_ << " OnAppListItemAdded: " << item->ToDebugString();
198 owner_->AddOrUpdateFromSyncItem(item); 196 owner_->AddOrUpdateFromSyncItem(item);
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
237 model_(new AppListModel), 235 model_(new AppListModel),
238 initial_sync_data_processed_(false), 236 initial_sync_data_processed_(false),
239 first_app_list_sync_(true) { 237 first_app_list_sync_(true) {
240 if (!extension_system) { 238 if (!extension_system) {
241 LOG(ERROR) << "AppListSyncableService created with no ExtensionSystem"; 239 LOG(ERROR) << "AppListSyncableService created with no ExtensionSystem";
242 return; 240 return;
243 } 241 }
244 242
245 oem_folder_name_ = 243 oem_folder_name_ =
246 l10n_util::GetStringUTF8(IDS_APP_LIST_OEM_DEFAULT_FOLDER_NAME); 244 l10n_util::GetStringUTF8(IDS_APP_LIST_OEM_DEFAULT_FOLDER_NAME);
247
248 // Note: model_observer_ is constructed after the initial sync changes are
249 // received in MergeDataAndStartSyncing(). Changes to the model before that
250 // will be synced after the initial sync occurs.
251 if (extension_system->extension_service() &&
252 extension_system->extension_service()->is_ready()) {
253 BuildModel();
254 return;
255 }
256
257 // The extensions for this profile have not yet all been loaded.
258 registrar_.Add(this,
259 extensions::NOTIFICATION_EXTENSIONS_READY_DEPRECATED,
260 content::Source<Profile>(profile));
261 } 245 }
262 246
263 AppListSyncableService::~AppListSyncableService() { 247 AppListSyncableService::~AppListSyncableService() {
264 // Remove observers. 248 // Remove observers.
265 model_observer_.reset(); 249 model_observer_.reset();
266 model_pref_updater_.reset(); 250 model_pref_updater_.reset();
267 251
268 STLDeleteContainerPairSecondPointers(sync_items_.begin(), sync_items_.end()); 252 STLDeleteContainerPairSecondPointers(sync_items_.begin(), sync_items_.end());
269 } 253 }
270 254
271 void AppListSyncableService::BuildModel() { 255 void AppListSyncableService::BuildModel() {
256 // TODO(calamity): make this a DCHECK after a dev channel release.
257 CHECK(extension_system_->extension_service() &&
258 extension_system_->extension_service()->is_ready());
272 // For now, use the AppListControllerDelegate associated with the native 259 // For now, use the AppListControllerDelegate associated with the native
273 // desktop. TODO(stevenjb): Remove ExtensionAppModelBuilder controller 260 // desktop. TODO(stevenjb): Remove ExtensionAppModelBuilder controller
274 // dependency and move the dependent methods from AppListControllerDelegate 261 // dependency and move the dependent methods from AppListControllerDelegate
275 // to an extension service delegate associated with this class. 262 // to an extension service delegate associated with this class.
276 AppListControllerDelegate* controller = NULL; 263 AppListControllerDelegate* controller = NULL;
277 AppListService* service = 264 AppListService* service =
278 AppListService::Get(chrome::HOST_DESKTOP_TYPE_NATIVE); 265 AppListService::Get(chrome::HOST_DESKTOP_TYPE_NATIVE);
279 if (service) 266 if (service)
280 controller = service->GetControllerDelegate(); 267 controller = service->GetControllerDelegate();
281 apps_builder_.reset(new ExtensionAppModelBuilder(controller)); 268 apps_builder_.reset(new ExtensionAppModelBuilder(controller));
282 DCHECK(profile_); 269 DCHECK(profile_);
283 if (app_list::switches::IsAppListSyncEnabled()) { 270 if (app_list::switches::IsAppListSyncEnabled()) {
284 VLOG(1) << this << ": AppListSyncableService: InitializeWithService."; 271 VLOG(1) << this << ": AppListSyncableService: InitializeWithService.";
285 SyncStarted(); 272 SyncStarted();
286 apps_builder_->InitializeWithService(this); 273 apps_builder_->InitializeWithService(this, model_.get());
287 } else { 274 } else {
288 VLOG(1) << this << ": AppListSyncableService: InitializeWithProfile."; 275 VLOG(1) << this << ": AppListSyncableService: InitializeWithProfile.";
289 apps_builder_->InitializeWithProfile(profile_, model_.get()); 276 apps_builder_->InitializeWithProfile(profile_, model_.get());
290 } 277 }
291 278
292 model_pref_updater_.reset( 279 model_pref_updater_.reset(
293 new ModelPrefUpdater(AppListPrefs::Get(profile_), model_.get())); 280 new ModelPrefUpdater(AppListPrefs::Get(profile_), model_.get()));
294 281
295 if (app_list::switches::IsDriveAppsInAppListEnabled()) 282 if (app_list::switches::IsDriveAppsInAppListEnabled())
296 drive_app_provider_.reset(new DriveAppProvider(profile_, this)); 283 drive_app_provider_.reset(new DriveAppProvider(profile_, this));
297 } 284 }
298 285
286 size_t AppListSyncableService::GetNumSyncItemsForTest() {
287 // If the model isn't built yet, there will be no sync items.
288 GetModel();
289
290 return sync_items_.size();
291 }
292
299 void AppListSyncableService::ResetDriveAppProviderForTest() { 293 void AppListSyncableService::ResetDriveAppProviderForTest() {
300 drive_app_provider_.reset(); 294 drive_app_provider_.reset();
301 } 295 }
302 296
303 void AppListSyncableService::Shutdown() { 297 void AppListSyncableService::Shutdown() {
304 // DriveAppProvider touches other KeyedServices in its dtor and needs be 298 // DriveAppProvider touches other KeyedServices in its dtor and needs be
305 // released in shutdown stage. 299 // released in shutdown stage.
306 drive_app_provider_.reset(); 300 drive_app_provider_.reset();
307 } 301 }
308 302
(...skipping 17 matching lines...) Expand all
326 const std::string sync_id = GetDriveAppSyncId(drive_app_id); 320 const std::string sync_id = GetDriveAppSyncId(drive_app_id);
327 SyncItem* sync_item = FindSyncItem(sync_id); 321 SyncItem* sync_item = FindSyncItem(sync_id);
328 if (!sync_item) 322 if (!sync_item)
329 return; 323 return;
330 324
331 DCHECK_EQ(sync_item->item_type, 325 DCHECK_EQ(sync_item->item_type,
332 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP); 326 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP);
333 DeleteSyncItem(sync_item); 327 DeleteSyncItem(sync_item);
334 } 328 }
335 329
336 void AppListSyncableService::Observe(
337 int type,
338 const content::NotificationSource& source,
339 const content::NotificationDetails& details) {
340 DCHECK_EQ(extensions::NOTIFICATION_EXTENSIONS_READY_DEPRECATED, type);
341 DCHECK_EQ(profile_, content::Source<Profile>(source).ptr());
342 registrar_.RemoveAll();
343 BuildModel();
344 }
345
346 const AppListSyncableService::SyncItem* 330 const AppListSyncableService::SyncItem*
347 AppListSyncableService::GetSyncItem(const std::string& id) const { 331 AppListSyncableService::GetSyncItem(const std::string& id) const {
348 SyncItemMap::const_iterator iter = sync_items_.find(id); 332 SyncItemMap::const_iterator iter = sync_items_.find(id);
349 if (iter != sync_items_.end()) 333 if (iter != sync_items_.end())
350 return iter->second; 334 return iter->second;
351 return NULL; 335 return NULL;
352 } 336 }
353 337
354 void AppListSyncableService::SetOemFolderName(const std::string& name) { 338 void AppListSyncableService::SetOemFolderName(const std::string& name) {
355 oem_folder_name_ = name; 339 oem_folder_name_ = name;
356 AppListFolderItem* oem_folder = model_->FindFolderItem(kOemFolderId); 340 AppListFolderItem* oem_folder = model_->FindFolderItem(kOemFolderId);
357 if (oem_folder) 341 if (oem_folder)
358 model_->SetItemName(oem_folder, oem_folder_name_); 342 model_->SetItemName(oem_folder, oem_folder_name_);
359 } 343 }
360 344
345 AppListModel* AppListSyncableService::GetModel() {
346 if (!apps_builder_)
347 BuildModel();
348
349 return model_.get();
350 }
351
361 void AppListSyncableService::AddItem(scoped_ptr<AppListItem> app_item) { 352 void AppListSyncableService::AddItem(scoped_ptr<AppListItem> app_item) {
362 SyncItem* sync_item = FindOrAddSyncItem(app_item.get()); 353 SyncItem* sync_item = FindOrAddSyncItem(app_item.get());
363 if (!sync_item) 354 if (!sync_item)
364 return; // Item is not valid. 355 return; // Item is not valid.
365 356
366 std::string folder_id; 357 std::string folder_id;
367 if (app_list::switches::IsFolderUIEnabled()) { 358 if (app_list::switches::IsFolderUIEnabled()) {
368 if (AppIsOem(app_item->id())) { 359 if (AppIsOem(app_item->id())) {
369 folder_id = FindOrCreateOemFolder(); 360 folder_id = FindOrCreateOemFolder();
370 VLOG_IF(2, !folder_id.empty()) 361 VLOG_IF(2, !folder_id.empty())
(...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after
576 567
577 syncer::SyncMergeResult AppListSyncableService::MergeDataAndStartSyncing( 568 syncer::SyncMergeResult AppListSyncableService::MergeDataAndStartSyncing(
578 syncer::ModelType type, 569 syncer::ModelType type,
579 const syncer::SyncDataList& initial_sync_data, 570 const syncer::SyncDataList& initial_sync_data,
580 scoped_ptr<syncer::SyncChangeProcessor> sync_processor, 571 scoped_ptr<syncer::SyncChangeProcessor> sync_processor,
581 scoped_ptr<syncer::SyncErrorFactory> error_handler) { 572 scoped_ptr<syncer::SyncErrorFactory> error_handler) {
582 DCHECK(!sync_processor_.get()); 573 DCHECK(!sync_processor_.get());
583 DCHECK(sync_processor.get()); 574 DCHECK(sync_processor.get());
584 DCHECK(error_handler.get()); 575 DCHECK(error_handler.get());
585 576
577 // Ensure the model is built.
578 GetModel();
579
586 sync_processor_ = sync_processor.Pass(); 580 sync_processor_ = sync_processor.Pass();
587 sync_error_handler_ = error_handler.Pass(); 581 sync_error_handler_ = error_handler.Pass();
588 if (switches::IsFolderUIEnabled()) 582 if (switches::IsFolderUIEnabled())
589 model_->SetFoldersEnabled(true); 583 model_->SetFoldersEnabled(true);
590 584
591 syncer::SyncMergeResult result = syncer::SyncMergeResult(type); 585 syncer::SyncMergeResult result = syncer::SyncMergeResult(type);
592 result.set_num_items_before_association(sync_items_.size()); 586 result.set_num_items_before_association(sync_items_.size());
593 VLOG(1) << this << ": MergeDataAndStartSyncing: " 587 VLOG(1) << this << ": MergeDataAndStartSyncing: "
594 << initial_sync_data.size(); 588 << initial_sync_data.size();
595 589
(...skipping 400 matching lines...) Expand 10 before | Expand all | Expand 10 after
996 } else { 990 } else {
997 res += " { " + item_name + " }"; 991 res += " { " + item_name + " }";
998 res += " [" + item_ordinal.ToDebugString() + "]"; 992 res += " [" + item_ordinal.ToDebugString() + "]";
999 if (!parent_id.empty()) 993 if (!parent_id.empty())
1000 res += " <" + parent_id.substr(0, 8) + ">"; 994 res += " <" + parent_id.substr(0, 8) + ">";
1001 } 995 }
1002 return res; 996 return res;
1003 } 997 }
1004 998
1005 } // namespace app_list 999 } // namespace app_list
OLDNEW
« no previous file with comments | « chrome/browser/ui/app_list/app_list_syncable_service.h ('k') | chrome/browser/ui/app_list/app_list_view_delegate.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698