| OLD | NEW |
| (Empty) |
| 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 #ifndef COMPONENTS_SYNC_DRIVER_GLUE_SYNC_BACKEND_HOST_IMPL_H_ | |
| 6 #define COMPONENTS_SYNC_DRIVER_GLUE_SYNC_BACKEND_HOST_IMPL_H_ | |
| 7 | |
| 8 #include <stdint.h> | |
| 9 | |
| 10 #include <map> | |
| 11 #include <memory> | |
| 12 #include <string> | |
| 13 #include <vector> | |
| 14 | |
| 15 #include "base/callback.h" | |
| 16 #include "base/compiler_specific.h" | |
| 17 #include "base/macros.h" | |
| 18 #include "base/memory/ref_counted.h" | |
| 19 #include "base/memory/weak_ptr.h" | |
| 20 #include "base/single_thread_task_runner.h" | |
| 21 #include "base/threading/thread.h" | |
| 22 #include "components/invalidation/public/invalidation_handler.h" | |
| 23 #include "components/sync/base/extensions_activity.h" | |
| 24 #include "components/sync/base/model_type.h" | |
| 25 #include "components/sync/base/weak_handle.h" | |
| 26 #include "components/sync/core/configure_reason.h" | |
| 27 #include "components/sync/core/sync_manager.h" | |
| 28 #include "components/sync/protocol/encryption.pb.h" | |
| 29 #include "components/sync/protocol/sync_protocol_error.h" | |
| 30 #include "components/sync/sessions/sync_session_snapshot.h" | |
| 31 #include "components/sync/sessions/type_debug_info_observer.h" | |
| 32 #include "components/sync_driver/backend_data_type_configurer.h" | |
| 33 #include "components/sync_driver/glue/sync_backend_host.h" | |
| 34 | |
| 35 class GURL; | |
| 36 | |
| 37 namespace base { | |
| 38 class MessageLoop; | |
| 39 } | |
| 40 | |
| 41 namespace invalidation { | |
| 42 class InvalidationService; | |
| 43 } | |
| 44 | |
| 45 namespace syncer { | |
| 46 class SyncManagerFactory; | |
| 47 class UnrecoverableErrorHandler; | |
| 48 } | |
| 49 | |
| 50 namespace sync_driver { | |
| 51 class SyncClient; | |
| 52 class SyncPrefs; | |
| 53 } | |
| 54 | |
| 55 namespace browser_sync { | |
| 56 | |
| 57 class ChangeProcessor; | |
| 58 class SyncBackendHostCore; | |
| 59 class SyncBackendRegistrar; | |
| 60 struct DoInitializeOptions; | |
| 61 | |
| 62 // The only real implementation of the SyncBackendHost. See that interface's | |
| 63 // definition for documentation of public methods. | |
| 64 class SyncBackendHostImpl | |
| 65 : public SyncBackendHost, | |
| 66 public syncer::InvalidationHandler { | |
| 67 public: | |
| 68 typedef syncer::SyncStatus Status; | |
| 69 | |
| 70 // Create a SyncBackendHost with a reference to the |frontend| that | |
| 71 // it serves and communicates to via the SyncFrontend interface (on | |
| 72 // the same thread it used to call the constructor). Must outlive | |
| 73 // |sync_prefs|. | |
| 74 SyncBackendHostImpl( | |
| 75 const std::string& name, | |
| 76 sync_driver::SyncClient* sync_client, | |
| 77 const scoped_refptr<base::SingleThreadTaskRunner>& ui_thread, | |
| 78 invalidation::InvalidationService* invalidator, | |
| 79 const base::WeakPtr<sync_driver::SyncPrefs>& sync_prefs, | |
| 80 const base::FilePath& sync_folder); | |
| 81 ~SyncBackendHostImpl() override; | |
| 82 | |
| 83 // SyncBackendHost implementation. | |
| 84 void Initialize( | |
| 85 sync_driver::SyncFrontend* frontend, | |
| 86 std::unique_ptr<base::Thread> sync_thread, | |
| 87 const scoped_refptr<base::SingleThreadTaskRunner>& db_thread, | |
| 88 const scoped_refptr<base::SingleThreadTaskRunner>& file_thread, | |
| 89 const syncer::WeakHandle<syncer::JsEventHandler>& event_handler, | |
| 90 const GURL& service_url, | |
| 91 const std::string& sync_user_agent, | |
| 92 const syncer::SyncCredentials& credentials, | |
| 93 bool delete_sync_data_folder, | |
| 94 std::unique_ptr<syncer::SyncManagerFactory> sync_manager_factory, | |
| 95 const syncer::WeakHandle<syncer::UnrecoverableErrorHandler>& | |
| 96 unrecoverable_error_handler, | |
| 97 const base::Closure& report_unrecoverable_error_function, | |
| 98 const HttpPostProviderFactoryGetter& http_post_provider_factory_getter, | |
| 99 std::unique_ptr<syncer::SyncEncryptionHandler::NigoriState> | |
| 100 saved_nigori_state) override; | |
| 101 void TriggerRefresh(const syncer::ModelTypeSet& types) override; | |
| 102 void UpdateCredentials(const syncer::SyncCredentials& credentials) override; | |
| 103 void StartSyncingWithServer() override; | |
| 104 void SetEncryptionPassphrase(const std::string& passphrase, | |
| 105 bool is_explicit) override; | |
| 106 bool SetDecryptionPassphrase(const std::string& passphrase) override | |
| 107 WARN_UNUSED_RESULT; | |
| 108 void StopSyncingForShutdown() override; | |
| 109 std::unique_ptr<base::Thread> Shutdown( | |
| 110 syncer::ShutdownReason reason) override; | |
| 111 void UnregisterInvalidationIds() override; | |
| 112 syncer::ModelTypeSet ConfigureDataTypes( | |
| 113 syncer::ConfigureReason reason, | |
| 114 const DataTypeConfigStateMap& config_state_map, | |
| 115 const base::Callback<void(syncer::ModelTypeSet, syncer::ModelTypeSet)>& | |
| 116 ready_task, | |
| 117 const base::Callback<void()>& retry_callback) override; | |
| 118 void ActivateDirectoryDataType( | |
| 119 syncer::ModelType type, | |
| 120 syncer::ModelSafeGroup group, | |
| 121 sync_driver::ChangeProcessor* change_processor) override; | |
| 122 void DeactivateDirectoryDataType(syncer::ModelType type) override; | |
| 123 void ActivateNonBlockingDataType( | |
| 124 syncer::ModelType type, | |
| 125 std::unique_ptr<syncer_v2::ActivationContext>) override; | |
| 126 void DeactivateNonBlockingDataType(syncer::ModelType type) override; | |
| 127 void EnableEncryptEverything() override; | |
| 128 syncer::UserShare* GetUserShare() const override; | |
| 129 Status GetDetailedStatus() override; | |
| 130 syncer::sessions::SyncSessionSnapshot GetLastSessionSnapshot() const override; | |
| 131 bool HasUnsyncedItems() const override; | |
| 132 bool IsNigoriEnabled() const override; | |
| 133 syncer::PassphraseType GetPassphraseType() const override; | |
| 134 base::Time GetExplicitPassphraseTime() const override; | |
| 135 bool IsCryptographerReady( | |
| 136 const syncer::BaseTransaction* trans) const override; | |
| 137 void GetModelSafeRoutingInfo( | |
| 138 syncer::ModelSafeRoutingInfo* out) const override; | |
| 139 void FlushDirectory() const override; | |
| 140 void RequestBufferedProtocolEventsAndEnableForwarding() override; | |
| 141 void DisableProtocolEventForwarding() override; | |
| 142 void EnableDirectoryTypeDebugInfoForwarding() override; | |
| 143 void DisableDirectoryTypeDebugInfoForwarding() override; | |
| 144 void GetAllNodesForTypes( | |
| 145 syncer::ModelTypeSet types, | |
| 146 base::Callback<void(const std::vector<syncer::ModelType>&, | |
| 147 ScopedVector<base::ListValue>)> type) override; | |
| 148 base::MessageLoop* GetSyncLoopForTesting() override; | |
| 149 void RefreshTypesForTest(syncer::ModelTypeSet types) override; | |
| 150 void ClearServerData( | |
| 151 const syncer::SyncManager::ClearServerDataCallback& callback) override; | |
| 152 void OnCookieJarChanged(bool account_mismatch, bool empty_jar) override; | |
| 153 | |
| 154 // InvalidationHandler implementation. | |
| 155 void OnInvalidatorStateChange(syncer::InvalidatorState state) override; | |
| 156 void OnIncomingInvalidation( | |
| 157 const syncer::ObjectIdInvalidationMap& invalidation_map) override; | |
| 158 std::string GetOwnerName() const override; | |
| 159 | |
| 160 protected: | |
| 161 // The types and functions below are protected so that test | |
| 162 // subclasses can use them. | |
| 163 | |
| 164 // Allows tests to perform alternate core initialization work. | |
| 165 virtual void InitCore(std::unique_ptr<DoInitializeOptions> options); | |
| 166 | |
| 167 // Request the syncer to reconfigure with the specfied params. | |
| 168 // Virtual for testing. | |
| 169 virtual void RequestConfigureSyncer( | |
| 170 syncer::ConfigureReason reason, | |
| 171 syncer::ModelTypeSet to_download, | |
| 172 syncer::ModelTypeSet to_purge, | |
| 173 syncer::ModelTypeSet to_journal, | |
| 174 syncer::ModelTypeSet to_unapply, | |
| 175 syncer::ModelTypeSet to_ignore, | |
| 176 const syncer::ModelSafeRoutingInfo& routing_info, | |
| 177 const base::Callback<void(syncer::ModelTypeSet, | |
| 178 syncer::ModelTypeSet)>& ready_task, | |
| 179 const base::Closure& retry_callback); | |
| 180 | |
| 181 // Called when the syncer has finished performing a configuration. | |
| 182 void FinishConfigureDataTypesOnFrontendLoop( | |
| 183 const syncer::ModelTypeSet enabled_types, | |
| 184 const syncer::ModelTypeSet succeeded_configuration_types, | |
| 185 const syncer::ModelTypeSet failed_configuration_types, | |
| 186 const base::Callback<void(syncer::ModelTypeSet, | |
| 187 syncer::ModelTypeSet)>& ready_task); | |
| 188 | |
| 189 // Reports backend initialization success. Includes some objects from sync | |
| 190 // manager initialization to be passed back to the UI thread. | |
| 191 // | |
| 192 // |model_type_connector| is our ModelTypeConnector, which is owned because in | |
| 193 // production it is a proxy object to the real ModelTypeConnector. | |
| 194 virtual void HandleInitializationSuccessOnFrontendLoop( | |
| 195 const syncer::WeakHandle<syncer::JsBackend> js_backend, | |
| 196 const syncer::WeakHandle<syncer::DataTypeDebugInfoListener> | |
| 197 debug_info_listener, | |
| 198 std::unique_ptr<syncer_v2::ModelTypeConnector> model_type_connector, | |
| 199 const std::string& cache_guid); | |
| 200 | |
| 201 // Forwards a ProtocolEvent to the frontend. Will not be called unless a | |
| 202 // call to SetForwardProtocolEvents() explicitly requested that we start | |
| 203 // forwarding these events. | |
| 204 void HandleProtocolEventOnFrontendLoop(syncer::ProtocolEvent* event); | |
| 205 | |
| 206 // Forwards a directory commit counter update to the frontend loop. Will not | |
| 207 // be called unless a call to EnableDirectoryTypeDebugInfoForwarding() | |
| 208 // explicitly requested that we start forwarding these events. | |
| 209 void HandleDirectoryCommitCountersUpdatedOnFrontendLoop( | |
| 210 syncer::ModelType type, | |
| 211 const syncer::CommitCounters& counters); | |
| 212 | |
| 213 // Forwards a directory update counter update to the frontend loop. Will not | |
| 214 // be called unless a call to EnableDirectoryTypeDebugInfoForwarding() | |
| 215 // explicitly requested that we start forwarding these events. | |
| 216 void HandleDirectoryUpdateCountersUpdatedOnFrontendLoop( | |
| 217 syncer::ModelType type, | |
| 218 const syncer::UpdateCounters& counters); | |
| 219 | |
| 220 // Forwards a directory status counter update to the frontend loop. Will not | |
| 221 // be called unless a call to EnableDirectoryTypeDebugInfoForwarding() | |
| 222 // explicitly requested that we start forwarding these events. | |
| 223 void HandleDirectoryStatusCountersUpdatedOnFrontendLoop( | |
| 224 syncer::ModelType type, | |
| 225 const syncer::StatusCounters& counters); | |
| 226 | |
| 227 // Overwrites the kSyncInvalidationVersions preference with the most recent | |
| 228 // set of invalidation versions for each type. | |
| 229 void UpdateInvalidationVersions( | |
| 230 const std::map<syncer::ModelType, int64_t>& invalidation_versions); | |
| 231 | |
| 232 sync_driver::SyncFrontend* frontend() { | |
| 233 return frontend_; | |
| 234 } | |
| 235 | |
| 236 private: | |
| 237 friend class SyncBackendHostCore; | |
| 238 | |
| 239 // Checks if we have received a notice to turn on experimental datatypes | |
| 240 // (via the nigori node) and informs the frontend if that is the case. | |
| 241 // Note: it is illegal to call this before the backend is initialized. | |
| 242 void AddExperimentalTypes(); | |
| 243 | |
| 244 // Handles backend initialization failure. | |
| 245 void HandleInitializationFailureOnFrontendLoop(); | |
| 246 | |
| 247 // Called from Core::OnSyncCycleCompleted to handle updating frontend | |
| 248 // thread components. | |
| 249 void HandleSyncCycleCompletedOnFrontendLoop( | |
| 250 const syncer::sessions::SyncSessionSnapshot& snapshot); | |
| 251 | |
| 252 // Called when the syncer failed to perform a configuration and will | |
| 253 // eventually retry. FinishingConfigurationOnFrontendLoop(..) will be called | |
| 254 // on successful completion. | |
| 255 void RetryConfigurationOnFrontendLoop(const base::Closure& retry_callback); | |
| 256 | |
| 257 // Helpers to persist a token that can be used to bootstrap sync encryption | |
| 258 // across browser restart to avoid requiring the user to re-enter their | |
| 259 // passphrase. |token| must be valid UTF-8 as we use the PrefService for | |
| 260 // storage. | |
| 261 void PersistEncryptionBootstrapToken( | |
| 262 const std::string& token, | |
| 263 syncer::BootstrapTokenType token_type); | |
| 264 | |
| 265 // For convenience, checks if initialization state is INITIALIZED. | |
| 266 bool initialized() const { return initialized_; } | |
| 267 | |
| 268 // Let the front end handle the actionable error event. | |
| 269 void HandleActionableErrorEventOnFrontendLoop( | |
| 270 const syncer::SyncProtocolError& sync_error); | |
| 271 | |
| 272 // Handle a migration request. | |
| 273 void HandleMigrationRequestedOnFrontendLoop(const syncer::ModelTypeSet types); | |
| 274 | |
| 275 // Checks if |passphrase| can be used to decrypt the cryptographer's pending | |
| 276 // keys that were cached during NotifyPassphraseRequired. Returns true if | |
| 277 // decryption was successful. Returns false otherwise. Must be called with a | |
| 278 // non-empty pending keys cache. | |
| 279 bool CheckPassphraseAgainstCachedPendingKeys( | |
| 280 const std::string& passphrase) const; | |
| 281 | |
| 282 // Invoked when a passphrase is required to decrypt a set of Nigori keys, | |
| 283 // or for encrypting. |reason| denotes why the passphrase was required. | |
| 284 // |pending_keys| is a copy of the cryptographer's pending keys, that are | |
| 285 // cached by the frontend. If there are no pending keys, or if the passphrase | |
| 286 // required reason is REASON_ENCRYPTION, an empty EncryptedData object is | |
| 287 // passed. | |
| 288 void NotifyPassphraseRequired(syncer::PassphraseRequiredReason reason, | |
| 289 sync_pb::EncryptedData pending_keys); | |
| 290 | |
| 291 // Invoked when the passphrase provided by the user has been accepted. | |
| 292 void NotifyPassphraseAccepted(); | |
| 293 | |
| 294 // Invoked when the set of encrypted types or the encrypt | |
| 295 // everything flag changes. | |
| 296 void NotifyEncryptedTypesChanged( | |
| 297 syncer::ModelTypeSet encrypted_types, | |
| 298 bool encrypt_everything); | |
| 299 | |
| 300 // Invoked when sync finishes encrypting new datatypes. | |
| 301 void NotifyEncryptionComplete(); | |
| 302 | |
| 303 // Invoked when the passphrase state has changed. Caches the passphrase state | |
| 304 // for later use on the UI thread. | |
| 305 // If |type| is FROZEN_IMPLICIT_PASSPHRASE or CUSTOM_PASSPHRASE, | |
| 306 // |explicit_passphrase_time| is the time at which that passphrase was set | |
| 307 // (if available). | |
| 308 void HandlePassphraseTypeChangedOnFrontendLoop( | |
| 309 syncer::PassphraseType type, | |
| 310 base::Time explicit_passphrase_time); | |
| 311 | |
| 312 void HandleLocalSetPassphraseEncryptionOnFrontendLoop( | |
| 313 const syncer::SyncEncryptionHandler::NigoriState& nigori_state); | |
| 314 | |
| 315 // Dispatched to from OnConnectionStatusChange to handle updating | |
| 316 // frontend UI components. | |
| 317 void HandleConnectionStatusChangeOnFrontendLoop( | |
| 318 syncer::ConnectionStatus status); | |
| 319 | |
| 320 void ClearServerDataDoneOnFrontendLoop( | |
| 321 const syncer::SyncManager::ClearServerDataCallback& frontend_callback); | |
| 322 | |
| 323 // A reference to the TaskRUnner used to construct |this|, so we know how to | |
| 324 // safely talk back to the SyncFrontend. | |
| 325 scoped_refptr<base::SingleThreadTaskRunner> const frontend_task_runner_; | |
| 326 | |
| 327 sync_driver::SyncClient* const sync_client_; | |
| 328 | |
| 329 // The UI thread's task runner. | |
| 330 const scoped_refptr<base::SingleThreadTaskRunner> ui_thread_; | |
| 331 | |
| 332 // Name used for debugging (set from profile_->GetDebugName()). | |
| 333 const std::string name_; | |
| 334 | |
| 335 // Our core, which communicates directly to the syncapi. Use refptr instead | |
| 336 // of WeakHandle because |core_| is created on UI loop but released on | |
| 337 // sync loop. | |
| 338 scoped_refptr<SyncBackendHostCore> core_; | |
| 339 | |
| 340 // A handle referencing the main interface for non-blocking sync types. This | |
| 341 // object is owned because in production code it is a proxy object. | |
| 342 std::unique_ptr<syncer_v2::ModelTypeConnector> model_type_connector_; | |
| 343 | |
| 344 bool initialized_; | |
| 345 | |
| 346 const base::WeakPtr<sync_driver::SyncPrefs> sync_prefs_; | |
| 347 | |
| 348 std::unique_ptr<SyncBackendRegistrar> registrar_; | |
| 349 | |
| 350 // The frontend which we serve (and are owned by). | |
| 351 sync_driver::SyncFrontend* frontend_; | |
| 352 | |
| 353 // We cache the cryptographer's pending keys whenever NotifyPassphraseRequired | |
| 354 // is called. This way, before the UI calls SetDecryptionPassphrase on the | |
| 355 // syncer, it can avoid the overhead of an asynchronous decryption call and | |
| 356 // give the user immediate feedback about the passphrase entered by first | |
| 357 // trying to decrypt the cached pending keys on the UI thread. Note that | |
| 358 // SetDecryptionPassphrase can still fail after the cached pending keys are | |
| 359 // successfully decrypted if the pending keys have changed since the time they | |
| 360 // were cached. | |
| 361 sync_pb::EncryptedData cached_pending_keys_; | |
| 362 | |
| 363 // The state of the passphrase required to decrypt the bag of encryption keys | |
| 364 // in the nigori node. Updated whenever a new nigori node arrives or the user | |
| 365 // manually changes their passphrase state. Cached so we can synchronously | |
| 366 // check it from the UI thread. | |
| 367 syncer::PassphraseType cached_passphrase_type_; | |
| 368 | |
| 369 // If an explicit passphrase is in use, the time at which the passphrase was | |
| 370 // first set (if available). | |
| 371 base::Time cached_explicit_passphrase_time_; | |
| 372 | |
| 373 // UI-thread cache of the last SyncSessionSnapshot received from syncapi. | |
| 374 syncer::sessions::SyncSessionSnapshot last_snapshot_; | |
| 375 | |
| 376 invalidation::InvalidationService* invalidator_; | |
| 377 bool invalidation_handler_registered_; | |
| 378 | |
| 379 base::WeakPtrFactory<SyncBackendHostImpl> weak_ptr_factory_; | |
| 380 | |
| 381 DISALLOW_COPY_AND_ASSIGN(SyncBackendHostImpl); | |
| 382 }; | |
| 383 | |
| 384 } // namespace browser_sync | |
| 385 | |
| 386 #endif // COMPONENTS_SYNC_DRIVER_GLUE_SYNC_BACKEND_HOST_IMPL_H_ | |
| OLD | NEW |