1 // Copyright (c) 2012 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 #ifndef CHROME_BROWSER_SYNC_GLUE_TYPED_URL_CHANGE_PROCESSOR_H_ 6 #define CHROME_BROWSER_SYNC_GLUE_TYPED_URL_CHANGE_PROCESSOR_H_ 7 8 #include "components/sync_driver/change_processor.h" 9 10 #include "base/basictypes.h" 11 #include "base/compiler_specific.h" 12 #include "base/memory/scoped_ptr.h" 13 #include "chrome/browser/sync/glue/sync_backend_host.h" 14 #include "chrome/browser/sync/glue/typed_url_model_associator.h" 15 #include "components/sync_driver/data_type_error_handler.h" 16 #include "content/public/browser/notification_observer.h" 17 #include "content/public/browser/notification_registrar.h" 18 #include "content/public/browser/notification_types.h" 19 20 class Profile; 21 22 namespace base { 23 class MessageLoop; 24 } 25 26 namespace content { 27 class NotificationService; 28 } 29 30 namespace history { 31 class HistoryBackend; 32 struct URLsDeletedDetails; 33 struct URLsModifiedDetails; 34 struct URLVisitedDetails; 35 class URLRow; 36 }; 37 38 namespace browser_sync { 39 40 class DataTypeErrorHandler; 41 42 // This class is responsible for taking changes from the history backend and 43 // applying them to the sync API 'syncable' model, and vice versa. All 44 // operations and use of this class are from the UI thread. 45 class TypedUrlChangeProcessor : public sync_driver::ChangeProcessor, 46 public content::NotificationObserver { 47 public: 48 TypedUrlChangeProcessor(Profile* profile, 49 TypedUrlModelAssociator* model_associator, 50 history::HistoryBackend* history_backend, 51 sync_driver::DataTypeErrorHandler* error_handler); 52 virtual ~TypedUrlChangeProcessor(); 53 54 // content::NotificationObserver implementation. 55 // History -> sync API change application. 56 virtual void Observe(int type, 57 const content::NotificationSource& source, 58 const content::NotificationDetails& details) OVERRIDE; 59 60 // sync API model -> WebDataService change application. 61 virtual void ApplyChangesFromSyncModel( 62 const syncer::BaseTransaction* trans, 63 int64 model_version, 64 const syncer::ImmutableChangeRecordList& changes) OVERRIDE; 65 66 // Commit changes here, after we've released the transaction lock to avoid 67 // jank. 68 virtual void CommitChangesFromSyncModel() OVERRIDE; 69 70 // Stop processing changes and wait for being destroyed. 71 void Disconnect(); 72 73 protected: 74 virtual void StartImpl() OVERRIDE; 75 76 private: 77 friend class ScopedStopObserving<TypedUrlChangeProcessor>; 78 void StartObserving(); 79 void StopObserving(); 80 81 void HandleURLsModified(history::URLsModifiedDetails* details); 82 void HandleURLsDeleted(history::URLsDeletedDetails* details); 83 void HandleURLsVisited(history::URLVisitedDetails* details); 84 85 // Returns true if the caller should sync as a result of the passed visit 86 // notification. We use this to throttle the number of sync changes we send 87 // to the server so we don't hit the server for every 88 // single typed URL visit. 89 bool ShouldSyncVisit(history::URLVisitedDetails* details); 90 91 // Utility routine that either updates an existing sync node or creates a 92 // new one for the passed |typed_url| if one does not already exist. Returns 93 // false and sets an unrecoverable error if the operation failed. 94 bool CreateOrUpdateSyncNode(history::URLRow typed_url, 95 syncer::WriteTransaction* transaction); 96 97 // The profile with which we are associated. 98 Profile* profile_; 99 100 // The two models should be associated according to this ModelAssociator. 101 TypedUrlModelAssociator* model_associator_; 102 103 // The model we are processing changes from. This is owned by the 104 // WebDataService which is kept alive by our data type controller 105 // holding a reference. 106 history::HistoryBackend* history_backend_; 107 base::MessageLoop* backend_loop_; 108 109 content::NotificationRegistrar notification_registrar_; 110 111 scoped_ptr<content::NotificationService> notification_service_; 112 113 // The set of pending changes that will be written out on the next 114 // CommitChangesFromSyncModel() call. 115 history::URLRows pending_new_urls_; 116 history::URLRows pending_updated_urls_; 117 std::vector<GURL> pending_deleted_urls_; 118 TypedUrlModelAssociator::TypedUrlVisitVector pending_new_visits_; 119 history::VisitVector pending_deleted_visits_; 120 121 bool disconnected_; 122 base::Lock disconnect_lock_; 123 124 DISALLOW_COPY_AND_ASSIGN(TypedUrlChangeProcessor); 125 }; 126 127 } // namespace browser_sync 128 129 #endif // CHROME_BROWSER_SYNC_GLUE_TYPED_URL_CHANGE_PROCESSOR_H_ 130