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

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

Issue 148403007: Protect AppListItemList Add/Remove and fix sync bugs (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: . Created 6 years, 11 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
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 "chrome/browser/chrome_notification_types.h" 8 #include "chrome/browser/chrome_notification_types.h"
9 #include "chrome/browser/extensions/extension_service.h" 9 #include "chrome/browser/extensions/extension_service.h"
10 #include "chrome/browser/extensions/extension_system.h" 10 #include "chrome/browser/extensions/extension_system.h"
11 #include "chrome/browser/profiles/profile.h" 11 #include "chrome/browser/profiles/profile.h"
12 #include "chrome/browser/ui/app_list/app_list_service.h" 12 #include "chrome/browser/ui/app_list/app_list_service.h"
13 #include "chrome/browser/ui/app_list/extension_app_item.h" 13 #include "chrome/browser/ui/app_list/extension_app_item.h"
14 #include "chrome/browser/ui/app_list/extension_app_model_builder.h" 14 #include "chrome/browser/ui/app_list/extension_app_model_builder.h"
15 #include "chrome/browser/ui/host_desktop.h" 15 #include "chrome/browser/ui/host_desktop.h"
16 #include "chrome/common/chrome_switches.h" 16 #include "chrome/common/chrome_switches.h"
17 #include "content/public/browser/notification_source.h" 17 #include "content/public/browser/notification_source.h"
18 #include "extensions/browser/extension_prefs.h" 18 #include "extensions/browser/extension_prefs.h"
19 #include "sync/api/sync_change_processor.h" 19 #include "sync/api/sync_change_processor.h"
20 #include "sync/api/sync_data.h" 20 #include "sync/api/sync_data.h"
21 #include "sync/api/sync_merge_result.h" 21 #include "sync/api/sync_merge_result.h"
22 #include "sync/protocol/sync.pb.h" 22 #include "sync/protocol/sync.pb.h"
23 #include "ui/app_list/app_list_folder_item.h" 23 #include "ui/app_list/app_list_folder_item.h"
24 #include "ui/app_list/app_list_item.h" 24 #include "ui/app_list/app_list_item.h"
25 #include "ui/app_list/app_list_model.h" 25 #include "ui/app_list/app_list_model.h"
26 #include "ui/app_list/app_list_model_observer.h"
27 #include "ui/app_list/app_list_switches.h"
26 28
27 using syncer::SyncChange; 29 using syncer::SyncChange;
28 30
29 namespace app_list { 31 namespace app_list {
30 32
31 namespace { 33 namespace {
32 34
33 bool SyncAppListEnabled() { 35 bool SyncAppListEnabled() {
34 return CommandLine::ForCurrentProcess()->HasSwitch( 36 return CommandLine::ForCurrentProcess()->HasSwitch(
35 switches::kEnableSyncAppList); 37 ::switches::kEnableSyncAppList);
36 } 38 }
37 39
38 void UpdateSyncItemFromSync(const sync_pb::AppListSpecifics& specifics, 40 void UpdateSyncItemFromSync(const sync_pb::AppListSpecifics& specifics,
39 AppListSyncableService::SyncItem* item) { 41 AppListSyncableService::SyncItem* item) {
40 DCHECK_EQ(item->item_id, specifics.item_id()); 42 DCHECK_EQ(item->item_id, specifics.item_id());
41 item->item_type = specifics.item_type(); 43 item->item_type = specifics.item_type();
42 item->item_name = specifics.item_name(); 44 item->item_name = specifics.item_name();
43 item->parent_id = specifics.parent_id(); 45 item->parent_id = specifics.parent_id();
44 if (!specifics.page_ordinal().empty()) 46 if (!specifics.page_ordinal().empty())
45 item->page_ordinal = syncer::StringOrdinal(specifics.page_ordinal()); 47 item->page_ordinal = syncer::StringOrdinal(specifics.page_ordinal());
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
116 AppListSyncableService::SyncItem::SyncItem( 118 AppListSyncableService::SyncItem::SyncItem(
117 const std::string& id, 119 const std::string& id,
118 sync_pb::AppListSpecifics::AppListItemType type) 120 sync_pb::AppListSpecifics::AppListItemType type)
119 : item_id(id), 121 : item_id(id),
120 item_type(type) { 122 item_type(type) {
121 } 123 }
122 124
123 AppListSyncableService::SyncItem::~SyncItem() { 125 AppListSyncableService::SyncItem::~SyncItem() {
124 } 126 }
125 127
126 // AppListSyncableService::ItemListObserver 128 // AppListSyncableService::ModelObserver
127 129
128 class AppListSyncableService::ItemListObserver 130 class AppListSyncableService::ModelObserver : public AppListModelObserver {
129 : public AppListItemListObserver {
130 public: 131 public:
131 explicit ItemListObserver(AppListSyncableService* owner) : owner_(owner) { 132 explicit ModelObserver(AppListSyncableService* owner)
132 owner_->model()->item_list()->AddObserver(this); 133 : owner_(owner),
134 processing_sync_changes_(false) {
135 owner_->model()->AddObserver(this);
133 } 136 }
134 137
135 virtual ~ItemListObserver() { 138 virtual ~ModelObserver() {
136 owner_->model()->item_list()->RemoveObserver(this); 139 owner_->model()->RemoveObserver(this);
140 }
141
142 // Called by owner to indicate that incoming sync changes are being processed.
143 // Changes to the model will be ignored while this is true (since they
144 // originated from sync changes).
145 void set_processing_sync_changes(bool processing_sync_changes) {
146 processing_sync_changes_ = processing_sync_changes;
xiyuan 2014/01/28 05:58:29 Can we also Add/RemoveObserer here? If we can, we
stevenjb 2014/01/28 18:28:08 I didn't go that route for two reasons: 1) This ma
137 } 147 }
138 148
139 private: 149 private:
140 // AppListItemListObserver 150 // AppListModelObserver
141 virtual void OnListItemAdded(size_t index, AppListItem* item) OVERRIDE { 151 virtual void OnAppListItemAdded(AppListItem* item) OVERRIDE {
152 if (processing_sync_changes_)
153 return;
154 DVLOG(2) << owner_ << " OnAppListItemAdded: " << item->ToDebugString();
142 owner_->AddOrUpdateFromSyncItem(item); 155 owner_->AddOrUpdateFromSyncItem(item);
143 } 156 }
144 157
145 virtual void OnListItemRemoved(size_t index, AppListItem* item) OVERRIDE { 158 virtual void OnAppListItemWillBeDeleted(AppListItem* item) OVERRIDE {
159 if (processing_sync_changes_)
160 return;
161 DVLOG(2) << owner_ << " OnAppListItemDeleted: " << item->ToDebugString();
146 owner_->RemoveSyncItem(item->id()); 162 owner_->RemoveSyncItem(item->id());
147 } 163 }
148 164
149 virtual void OnListItemMoved(size_t from_index, 165 virtual void OnAppListItemUpdated(AppListItem* item) OVERRIDE {
150 size_t to_index, 166 if (processing_sync_changes_)
151 AppListItem* item) OVERRIDE { 167 return;
168 DVLOG(2) << owner_ << " OnAppListItemUpdated: " << item->ToDebugString();
152 owner_->UpdateSyncItem(item); 169 owner_->UpdateSyncItem(item);
153 } 170 }
154 171
155 AppListSyncableService* owner_; 172 AppListSyncableService* owner_;
173 bool processing_sync_changes_;
156 174
157 DISALLOW_COPY_AND_ASSIGN(ItemListObserver); 175 DISALLOW_COPY_AND_ASSIGN(ModelObserver);
158 }; 176 };
159 177
160 // AppListSyncableService 178 // AppListSyncableService
161 179
162 AppListSyncableService::AppListSyncableService( 180 AppListSyncableService::AppListSyncableService(
163 Profile* profile, 181 Profile* profile,
164 extensions::ExtensionSystem* extension_system) 182 extensions::ExtensionSystem* extension_system)
165 : profile_(profile), 183 : profile_(profile),
166 extension_system_(extension_system), 184 extension_system_(extension_system),
167 model_(new AppListModel) { 185 model_(new AppListModel) {
168 if (!extension_system || !extension_system->extension_service()) { 186 if (!extension_system || !extension_system->extension_service()) {
169 LOG(WARNING) << "AppListSyncableService created with no ExtensionService"; 187 LOG(WARNING) << "AppListSyncableService created with no ExtensionService";
170 return; 188 return;
171 } 189 }
172 190
173 if (SyncAppListEnabled()) 191 // Note: model_observer_ is constructed after the initial sync changes are
174 item_list_observer_.reset(new ItemListObserver(this)); 192 // received in MergeDataAndStartSyncing(). Changes to the model before that
175 193 // will be synced after the initial sync occurs.
176 if (extension_system->extension_service()->is_ready()) { 194 if (extension_system->extension_service()->is_ready()) {
177 BuildModel(); 195 BuildModel();
178 return; 196 return;
179 } 197 }
180 198
181 // The extensions for this profile have not yet all been loaded. 199 // The extensions for this profile have not yet all been loaded.
182 registrar_.Add(this, chrome::NOTIFICATION_EXTENSIONS_READY, 200 registrar_.Add(this, chrome::NOTIFICATION_EXTENSIONS_READY,
183 content::Source<Profile>(profile)); 201 content::Source<Profile>(profile));
184 } 202 }
185 203
186 AppListSyncableService::~AppListSyncableService() { 204 AppListSyncableService::~AppListSyncableService() {
187 // Remove observers. 205 // Remove observers.
188 item_list_observer_.reset(); 206 model_observer_.reset();
189 207
190 STLDeleteContainerPairSecondPointers(sync_items_.begin(), sync_items_.end()); 208 STLDeleteContainerPairSecondPointers(sync_items_.begin(), sync_items_.end());
191 } 209 }
192 210
193 void AppListSyncableService::BuildModel() { 211 void AppListSyncableService::BuildModel() {
194 // For now, use the AppListControllerDelegate associated with the native 212 // For now, use the AppListControllerDelegate associated with the native
195 // desktop. TODO(stevenjb): Remove ExtensionAppModelBuilder controller 213 // desktop. TODO(stevenjb): Remove ExtensionAppModelBuilder controller
196 // dependency and move the dependent methods from AppListControllerDelegate 214 // dependency and move the dependent methods from AppListControllerDelegate
197 // to an extension service delegate associated with this class. 215 // to an extension service delegate associated with this class.
198 AppListControllerDelegate* controller = NULL; 216 AppListControllerDelegate* controller = NULL;
(...skipping 26 matching lines...) Expand all
225 243
226 const AppListSyncableService::SyncItem* 244 const AppListSyncableService::SyncItem*
227 AppListSyncableService::GetSyncItem(const std::string& id) const { 245 AppListSyncableService::GetSyncItem(const std::string& id) const {
228 SyncItemMap::const_iterator iter = sync_items_.find(id); 246 SyncItemMap::const_iterator iter = sync_items_.find(id);
229 if (iter != sync_items_.end()) 247 if (iter != sync_items_.end())
230 return iter->second; 248 return iter->second;
231 return NULL; 249 return NULL;
232 } 250 }
233 251
234 void AppListSyncableService::AddItem(AppListItem* app_item) { 252 void AppListSyncableService::AddItem(AppListItem* app_item) {
235 SyncItem* sync_item = AddOrUpdateSyncItem(app_item); 253 SyncItem* sync_item = FindOrAddSyncItem(app_item);
236 if (!sync_item) 254 if (!sync_item)
237 return; // Item is not valid. 255 return; // Item is not valid.
238 256
239 DVLOG(1) << this << ": AddItem: " << sync_item->ToString(); 257 DVLOG(1) << this << ": AddItem: " << sync_item->ToString();
240 258 model_->AddItem(app_item);
241 // Add the item to the model if necessary.
242 if (!model_->item_list()->FindItem(app_item->id()))
243 model_->item_list()->AddItem(app_item);
244 else
245 model_->item_list()->SetItemPosition(app_item, sync_item->item_ordinal);
246 } 259 }
247 260
248 AppListSyncableService::SyncItem* AppListSyncableService::AddOrUpdateSyncItem( 261 AppListSyncableService::SyncItem* AppListSyncableService::FindOrAddSyncItem(
249 AppListItem* app_item) { 262 AppListItem* app_item) {
250 const std::string& item_id = app_item->id(); 263 const std::string& item_id = app_item->id();
251 if (item_id.empty()) { 264 if (item_id.empty()) {
252 LOG(ERROR) << "AppListItem item with empty ID"; 265 LOG(ERROR) << "AppListItem item with empty ID";
253 return NULL; 266 return NULL;
254 } 267 }
255 SyncItem* sync_item = FindSyncItem(item_id); 268 SyncItem* sync_item = FindSyncItem(item_id);
256 if (sync_item) { 269 if (sync_item) {
257 // If there is an existing, non-REMOVE_DEFAULT entry, update it. 270 // If there is an existing, non-REMOVE_DEFAULT entry, return it.
258 if (sync_item->item_type != 271 if (sync_item->item_type !=
259 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) { 272 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) {
260 DVLOG(2) << this << ": AddItem already exists: " << sync_item->ToString(); 273 DVLOG(2) << this << ": AddItem already exists: " << sync_item->ToString();
261 UpdateSyncItem(app_item);
262 return sync_item; 274 return sync_item;
263 } 275 }
264 276
265 if (RemoveDefaultApp(app_item, sync_item)) 277 if (RemoveDefaultApp(app_item, sync_item))
266 return NULL; 278 return NULL;
267 279
268 // Fall through. The REMOVE_DEFAULT_APP entry has been deleted, now a new 280 // Fall through. The REMOVE_DEFAULT_APP entry has been deleted, now a new
269 // App entry can be added. 281 // App entry can be added.
270 } 282 }
271 283
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
336 bool changed = UpdateSyncItemFromAppItem(app_item, sync_item); 348 bool changed = UpdateSyncItemFromAppItem(app_item, sync_item);
337 if (!changed) { 349 if (!changed) {
338 DVLOG(2) << this << " - Update: SYNC NO CHANGE: " << sync_item->ToString(); 350 DVLOG(2) << this << " - Update: SYNC NO CHANGE: " << sync_item->ToString();
339 return; 351 return;
340 } 352 }
341 SendSyncChange(sync_item, SyncChange::ACTION_UPDATE); 353 SendSyncChange(sync_item, SyncChange::ACTION_UPDATE);
342 } 354 }
343 355
344 void AppListSyncableService::RemoveItem(const std::string& id) { 356 void AppListSyncableService::RemoveItem(const std::string& id) {
345 RemoveSyncItem(id); 357 RemoveSyncItem(id);
346 model_->item_list()->DeleteItem(id); 358 model_->DeleteItem(id);
347 } 359 }
348 360
349 void AppListSyncableService::RemoveSyncItem(const std::string& id) { 361 void AppListSyncableService::RemoveSyncItem(const std::string& id) {
350 DVLOG(2) << this << ": RemoveSyncItem: " << id.substr(0, 8); 362 DVLOG(2) << this << ": RemoveSyncItem: " << id.substr(0, 8);
351 SyncItemMap::iterator iter = sync_items_.find(id); 363 SyncItemMap::iterator iter = sync_items_.find(id);
352 if (iter == sync_items_.end()) { 364 if (iter == sync_items_.end()) {
353 DVLOG(2) << this << " : RemoveSyncItem: No Item."; 365 DVLOG(2) << this << " : RemoveSyncItem: No Item.";
354 return; 366 return;
355 } 367 }
356 368
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after
428 syncer::SyncChangeList change_list; 440 syncer::SyncChangeList change_list;
429 for (std::set<std::string>::iterator iter = unsynced_items.begin(); 441 for (std::set<std::string>::iterator iter = unsynced_items.begin();
430 iter != unsynced_items.end(); ++iter) { 442 iter != unsynced_items.end(); ++iter) {
431 SyncItem* sync_item = FindSyncItem(*iter); 443 SyncItem* sync_item = FindSyncItem(*iter);
432 DVLOG(2) << this << " -> SYNC ADD: " << sync_item->ToString(); 444 DVLOG(2) << this << " -> SYNC ADD: " << sync_item->ToString();
433 change_list.push_back(SyncChange(FROM_HERE, SyncChange::ACTION_ADD, 445 change_list.push_back(SyncChange(FROM_HERE, SyncChange::ACTION_ADD,
434 GetSyncDataFromSyncItem(sync_item))); 446 GetSyncDataFromSyncItem(sync_item)));
435 } 447 }
436 sync_processor_->ProcessSyncChanges(FROM_HERE, change_list); 448 sync_processor_->ProcessSyncChanges(FROM_HERE, change_list);
437 449
450 // Start observing app list changes.
451 model_observer_.reset(new ModelObserver(this));
452
438 return result; 453 return result;
439 } 454 }
440 455
441 void AppListSyncableService::StopSyncing(syncer::ModelType type) { 456 void AppListSyncableService::StopSyncing(syncer::ModelType type) {
442 DCHECK_EQ(type, syncer::APP_LIST); 457 DCHECK_EQ(type, syncer::APP_LIST);
443 458
444 sync_processor_.reset(); 459 sync_processor_.reset();
445 sync_error_handler_.reset(); 460 sync_error_handler_.reset();
446 } 461 }
447 462
(...skipping 13 matching lines...) Expand all
461 476
462 syncer::SyncError AppListSyncableService::ProcessSyncChanges( 477 syncer::SyncError AppListSyncableService::ProcessSyncChanges(
463 const tracked_objects::Location& from_here, 478 const tracked_objects::Location& from_here,
464 const syncer::SyncChangeList& change_list) { 479 const syncer::SyncChangeList& change_list) {
465 if (!sync_processor_.get()) { 480 if (!sync_processor_.get()) {
466 return syncer::SyncError(FROM_HERE, 481 return syncer::SyncError(FROM_HERE,
467 syncer::SyncError::DATATYPE_ERROR, 482 syncer::SyncError::DATATYPE_ERROR,
468 "App List syncable service is not started.", 483 "App List syncable service is not started.",
469 syncer::APP_LIST); 484 syncer::APP_LIST);
470 } 485 }
471 486 model_observer_->set_processing_sync_changes(true);
tapted 2014/01/28 11:56:53 It's a common pattern in the /ui/app_list code to
stevenjb 2014/01/28 18:28:08 Xiyuan made a similar comment, I explained why I d
472 DVLOG(1) << this << ": ProcessSyncChanges: " << change_list.size(); 487 DVLOG(1) << this << ": ProcessSyncChanges: " << change_list.size();
473 for (syncer::SyncChangeList::const_iterator iter = change_list.begin(); 488 for (syncer::SyncChangeList::const_iterator iter = change_list.begin();
474 iter != change_list.end(); ++iter) { 489 iter != change_list.end(); ++iter) {
475 const SyncChange& change = *iter; 490 const SyncChange& change = *iter;
476 DVLOG(2) << this << " Change: " 491 DVLOG(2) << this << " Change: "
477 << change.sync_data().GetSpecifics().app_list().item_id() 492 << change.sync_data().GetSpecifics().app_list().item_id()
478 << " (" << change.change_type() << ")"; 493 << " (" << change.change_type() << ")";
479 if (change.change_type() == SyncChange::ACTION_ADD || 494 if (change.change_type() == SyncChange::ACTION_ADD ||
480 change.change_type() == SyncChange::ACTION_UPDATE) { 495 change.change_type() == SyncChange::ACTION_UPDATE) {
481 ProcessSyncItemSpecifics(change.sync_data().GetSpecifics().app_list()); 496 ProcessSyncItemSpecifics(change.sync_data().GetSpecifics().app_list());
482 } else if (change.change_type() == SyncChange::ACTION_DELETE) { 497 } else if (change.change_type() == SyncChange::ACTION_DELETE) {
483 DeleteSyncItemSpecifics(change.sync_data().GetSpecifics().app_list()); 498 DeleteSyncItemSpecifics(change.sync_data().GetSpecifics().app_list());
484 } else { 499 } else {
485 LOG(ERROR) << "Invalid sync change"; 500 LOG(ERROR) << "Invalid sync change";
486 } 501 }
487 } 502 }
503 model_observer_->set_processing_sync_changes(false);
488 return syncer::SyncError(); 504 return syncer::SyncError();
489 } 505 }
490 506
491 // AppListSyncableService private 507 // AppListSyncableService private
492 508
493 bool AppListSyncableService::ProcessSyncItemSpecifics( 509 bool AppListSyncableService::ProcessSyncItemSpecifics(
494 const sync_pb::AppListSpecifics& specifics) { 510 const sync_pb::AppListSpecifics& specifics) {
495 const std::string& item_id = specifics.item_id(); 511 const std::string& item_id = specifics.item_id();
496 if (item_id.empty()) { 512 if (item_id.empty()) {
497 LOG(ERROR) << "AppList item with empty ID"; 513 LOG(ERROR) << "AppList item with empty ID";
498 return false; 514 return false;
499 } 515 }
500 SyncItem* sync_item = FindSyncItem(item_id); 516 SyncItem* sync_item = FindSyncItem(item_id);
501 if (sync_item) { 517 if (sync_item) {
502 // If an item of the same type exists, update it. 518 // If an item of the same type exists, update it.
503 if (sync_item->item_type == specifics.item_type()) { 519 if (sync_item->item_type == specifics.item_type()) {
504 UpdateSyncItemFromSync(specifics, sync_item); 520 UpdateSyncItemFromSync(specifics, sync_item);
505 ProcessExistingSyncItem(sync_item); 521 ProcessExistingSyncItem(sync_item);
506 DVLOG(2) << this << " <- SYNC UPDATE: " << sync_item->ToString(); 522 DVLOG(2) << this << " <- SYNC UPDATE: " << sync_item->ToString();
507 return false; 523 return false;
508 } 524 }
509 // Otherwise, one of the entries should be TYPE_REMOVE_DEFAULT_APP. 525 // Otherwise, one of the entries should be TYPE_REMOVE_DEFAULT_APP.
510 if (sync_item->item_type != 526 if (sync_item->item_type !=
511 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP && 527 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP &&
512 specifics.item_type() != 528 specifics.item_type() !=
513 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) { 529 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) {
514 LOG(ERROR) << "Synced item type: " << specifics.item_type() 530 LOG(ERROR) << "Synced item type: " << specifics.item_type()
515 << " != existing sync item type: " << sync_item->item_type 531 << " != existing sync item type: " << sync_item->item_type
516 << " Deleting item from model!"; 532 << " Deleting item from model!";
517 model_->item_list()->DeleteItem(item_id); 533 model_->DeleteItem(item_id);
518 } 534 }
519 DVLOG(2) << this << " - ProcessSyncItem: Delete existing entry: " 535 DVLOG(2) << this << " - ProcessSyncItem: Delete existing entry: "
520 << sync_item->ToString(); 536 << sync_item->ToString();
521 delete sync_item; 537 delete sync_item;
522 sync_items_.erase(item_id); 538 sync_items_.erase(item_id);
523 } 539 }
524 540
525 sync_item = CreateSyncItem(item_id, specifics.item_type()); 541 sync_item = CreateSyncItem(item_id, specifics.item_type());
526 UpdateSyncItemFromSync(specifics, sync_item); 542 UpdateSyncItemFromSync(specifics, sync_item);
527 ProcessNewSyncItem(sync_item); 543 ProcessNewSyncItem(sync_item);
(...skipping 20 matching lines...) Expand all
548 // TODO(stevenjb): Implement 564 // TODO(stevenjb): Implement
549 LOG(WARNING) << "TYPE_FOLDER not supported"; 565 LOG(WARNING) << "TYPE_FOLDER not supported";
550 return; 566 return;
551 } 567 }
552 case sync_pb::AppListSpecifics::TYPE_URL: { 568 case sync_pb::AppListSpecifics::TYPE_URL: {
553 // TODO(stevenjb): Implement 569 // TODO(stevenjb): Implement
554 LOG(WARNING) << "TYPE_URL not supported"; 570 LOG(WARNING) << "TYPE_URL not supported";
555 return; 571 return;
556 } 572 }
557 } 573 }
558 NOTREACHED() << "Unrecoginized sync item type: " << sync_item->ToString(); 574 NOTREACHED() << "Unrecognized sync item type: " << sync_item->ToString();
559 } 575 }
560 576
561 void AppListSyncableService::ProcessExistingSyncItem(SyncItem* sync_item) { 577 void AppListSyncableService::ProcessExistingSyncItem(SyncItem* sync_item) {
562 if (sync_item->item_type == 578 if (sync_item->item_type ==
563 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) { 579 sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) {
564 return; 580 return;
565 } 581 }
566 DVLOG(2) << "ProcessExistingSyncItem: " << sync_item->ToString(); 582 DVLOG(2) << "ProcessExistingSyncItem: " << sync_item->ToString();
567 AppListItem* app_item = model_->item_list()->FindItem(sync_item->item_id); 583 AppListItem* app_item = model_->FindItem(sync_item->item_id);
584 DVLOG(2) << " AppItem: " << app_item->ToDebugString();
568 if (!app_item) { 585 if (!app_item) {
569 LOG(ERROR) << "Item not found in model: " << sync_item->ToString(); 586 LOG(ERROR) << "Item not found in model: " << sync_item->ToString();
570 return; 587 return;
571 } 588 }
572 UpdateAppItemFromSyncItem(sync_item, app_item); 589 UpdateAppItemFromSyncItem(sync_item, app_item);
573 } 590 }
574 591
575 void AppListSyncableService::UpdateAppItemFromSyncItem( 592 void AppListSyncableService::UpdateAppItemFromSyncItem(
576 const AppListSyncableService::SyncItem* sync_item, 593 const AppListSyncableService::SyncItem* sync_item,
577 AppListItem* app_item) { 594 AppListItem* app_item) {
578 if (!app_item->position().Equals(sync_item->item_ordinal)) 595 if (!app_item->position().Equals(sync_item->item_ordinal))
579 model_->item_list()->SetItemPosition(app_item, sync_item->item_ordinal); 596 model_->SetItemPosition(app_item, sync_item->item_ordinal);
580 } 597 }
581 598
582 bool AppListSyncableService::SyncStarted() { 599 bool AppListSyncableService::SyncStarted() {
583 if (sync_processor_.get()) 600 if (sync_processor_.get())
584 return true; 601 return true;
585 if (flare_.is_null()) { 602 if (flare_.is_null()) {
586 DVLOG(2) << this << ": SyncStarted: Flare."; 603 DVLOG(2) << this << ": SyncStarted: Flare.";
587 flare_ = sync_start_util::GetFlareForSyncableService(profile_->GetPath()); 604 flare_ = sync_start_util::GetFlareForSyncableService(profile_->GetPath());
588 flare_.Run(syncer::APP_LIST); 605 flare_.Run(syncer::APP_LIST);
589 } 606 }
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
636 DVLOG(2) << this << ": DeleteSyncItemSpecifics: " << item_id.substr(0, 8); 653 DVLOG(2) << this << ": DeleteSyncItemSpecifics: " << item_id.substr(0, 8);
637 SyncItemMap::iterator iter = sync_items_.find(item_id); 654 SyncItemMap::iterator iter = sync_items_.find(item_id);
638 if (iter == sync_items_.end()) 655 if (iter == sync_items_.end())
639 return; 656 return;
640 sync_pb::AppListSpecifics::AppListItemType item_type = 657 sync_pb::AppListSpecifics::AppListItemType item_type =
641 iter->second->item_type; 658 iter->second->item_type;
642 DVLOG(2) << this << " <- SYNC DELETE: " << iter->second->ToString(); 659 DVLOG(2) << this << " <- SYNC DELETE: " << iter->second->ToString();
643 delete iter->second; 660 delete iter->second;
644 sync_items_.erase(iter); 661 sync_items_.erase(iter);
645 if (item_type != sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) 662 if (item_type != sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP)
646 model_->item_list()->DeleteItem(item_id); 663 model_->DeleteItem(item_id);
647 } 664 }
648 665
649 std::string AppListSyncableService::SyncItem::ToString() const { 666 std::string AppListSyncableService::SyncItem::ToString() const {
650 std::string res = item_id.substr(0, 8); 667 std::string res = item_id.substr(0, 8);
651 if (item_type == sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) { 668 if (item_type == sync_pb::AppListSpecifics::TYPE_REMOVE_DEFAULT_APP) {
652 res += " { RemoveDefault }"; 669 res += " { RemoveDefault }";
653 } else { 670 } else {
654 res += " { " + item_name + " }"; 671 res += " { " + item_name + " }";
655 res += " [" + item_ordinal.ToDebugString() + "]"; 672 res += " [" + item_ordinal.ToDebugString() + "]";
673 if (!parent_id.empty())
674 res += " <" + parent_id.substr(0, 8) + ">";
656 } 675 }
657 return res; 676 return res;
658 } 677 }
659 678
660 } // namespace app_list 679 } // namespace app_list
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698