summaryrefslogtreecommitdiffstats
path: root/sync/engine/syncer.cc
diff options
context:
space:
mode:
Diffstat (limited to 'sync/engine/syncer.cc')
-rw-r--r--sync/engine/syncer.cc245
1 files changed, 103 insertions, 142 deletions
diff --git a/sync/engine/syncer.cc b/sync/engine/syncer.cc
index c4ef671..9b1adb3 100644
--- a/sync/engine/syncer.cc
+++ b/sync/engine/syncer.cc
@@ -15,13 +15,13 @@
#include "sync/engine/build_commit_command.h"
#include "sync/engine/commit.h"
#include "sync/engine/conflict_resolver.h"
-#include "sync/engine/download_updates_command.h"
+#include "sync/engine/download.h"
#include "sync/engine/net/server_connection_manager.h"
#include "sync/engine/process_commit_response_command.h"
-#include "sync/engine/process_updates_command.h"
-#include "sync/engine/store_timestamps_command.h"
#include "sync/engine/syncer_types.h"
#include "sync/internal_api/public/base/unique_position.h"
+#include "sync/internal_api/public/util/syncer_error.h"
+#include "sync/sessions/nudge_tracker.h"
#include "sync/syncable/mutable_entry.h"
#include "sync/syncable/syncable-inl.h"
@@ -31,35 +31,17 @@ using sync_pb::ClientCommand;
namespace syncer {
+// TODO(akalin): We may want to propagate this switch up
+// eventually.
+#if defined(OS_ANDROID) || defined(OS_IOS)
+static const bool kCreateMobileBookmarksFolder = true;
+#else
+static const bool kCreateMobileBookmarksFolder = false;
+#endif
+
using sessions::StatusController;
using sessions::SyncSession;
-using syncable::IS_UNAPPLIED_UPDATE;
-using syncable::SERVER_CTIME;
-using syncable::SERVER_IS_DEL;
-using syncable::SERVER_IS_DIR;
-using syncable::SERVER_MTIME;
-using syncable::SERVER_NON_UNIQUE_NAME;
-using syncable::SERVER_PARENT_ID;
-using syncable::SERVER_SPECIFICS;
-using syncable::SERVER_UNIQUE_POSITION;
-using syncable::SERVER_VERSION;
-
-#define ENUM_CASE(x) case x: return #x
-const char* SyncerStepToString(const SyncerStep step)
-{
- switch (step) {
- ENUM_CASE(SYNCER_BEGIN);
- ENUM_CASE(DOWNLOAD_UPDATES);
- ENUM_CASE(PROCESS_UPDATES);
- ENUM_CASE(STORE_TIMESTAMPS);
- ENUM_CASE(APPLY_UPDATES);
- ENUM_CASE(COMMIT);
- ENUM_CASE(SYNCER_END);
- }
- NOTREACHED();
- return "";
-}
-#undef ENUM_CASE
+using sessions::NudgeTracker;
Syncer::Syncer()
: early_exit_requested_(false) {
@@ -77,121 +59,100 @@ void Syncer::RequestEarlyExit() {
early_exit_requested_ = true;
}
-bool Syncer::SyncShare(sessions::SyncSession* session,
- SyncerStep first_step,
- SyncerStep last_step) {
+bool Syncer::NormalSyncShare(ModelTypeSet request_types,
+ const NudgeTracker& nudge_tracker,
+ SyncSession* session) {
+ HandleCycleBegin(session);
+ VLOG(1) << "Downloading types " << ModelTypeSetToString(request_types);
+ if (!DownloadAndApplyUpdates(
+ session,
+ base::Bind(&NormalDownloadUpdates,
+ session,
+ kCreateMobileBookmarksFolder,
+ request_types,
+ base::ConstRef(nudge_tracker)))) {
+ return HandleCycleEnd(session);
+ }
+
+ VLOG(1) << "Committing from types " << ModelTypeSetToString(request_types);
+ SyncerError commit_result = BuildAndPostCommits(request_types, this, session);
+ session->mutable_status_controller()->set_commit_result(commit_result);
+
+ return HandleCycleEnd(session);
+}
+
+bool Syncer::ConfigureSyncShare(ModelTypeSet request_types,
+ SyncSession* session) {
+ HandleCycleBegin(session);
+ VLOG(1) << "Configuring types " << ModelTypeSetToString(request_types);
+ DownloadAndApplyUpdates(
+ session,
+ base::Bind(&DownloadUpdatesForConfigure,
+ session,
+ kCreateMobileBookmarksFolder,
+ session->source(),
+ request_types));
+ return HandleCycleEnd(session);
+}
+
+bool Syncer::PollSyncShare(ModelTypeSet request_types,
+ SyncSession* session) {
+ HandleCycleBegin(session);
+ VLOG(1) << "Polling types " << ModelTypeSetToString(request_types);
+ DownloadAndApplyUpdates(
+ session,
+ base::Bind(&DownloadUpdatesForPoll,
+ session,
+ kCreateMobileBookmarksFolder,
+ request_types));
+ return HandleCycleEnd(session);
+}
+
+void Syncer::ApplyUpdates(SyncSession* session) {
+ TRACE_EVENT0("sync", "ApplyUpdates");
+
+ ApplyControlDataUpdates(session);
+
+ ApplyUpdatesAndResolveConflictsCommand apply_updates;
+ apply_updates.Execute(session);
+
+ session->context()->set_hierarchy_conflict_detected(
+ session->status_controller().num_hierarchy_conflicts() > 0);
+
+ session->SendEventNotification(SyncEngineEvent::STATUS_CHANGED);
+}
+
+bool Syncer::DownloadAndApplyUpdates(
+ SyncSession* session,
+ base::Callback<SyncerError(void)> download_fn) {
+ while (!session->status_controller().ServerSaysNothingMoreToDownload()) {
+ SyncerError download_result = download_fn.Run();
+ session->mutable_status_controller()->set_last_download_updates_result(
+ download_result);
+ if (download_result != SYNCER_OK) {
+ return false;
+ }
+ }
+ if (ExitRequested())
+ return false;
+ ApplyUpdates(session);
+ if (ExitRequested())
+ return false;
+ return true;
+}
+
+void Syncer::HandleCycleBegin(SyncSession* session) {
session->mutable_status_controller()->UpdateStartTime();
- SyncerStep current_step = first_step;
-
- SyncerStep next_step = current_step;
- while (!ExitRequested()) {
- TRACE_EVENT1("sync", "SyncerStateMachine",
- "state", SyncerStepToString(current_step));
- DVLOG(1) << "Syncer step:" << SyncerStepToString(current_step);
-
- switch (current_step) {
- case SYNCER_BEGIN:
- session->SendEventNotification(SyncEngineEvent::SYNC_CYCLE_BEGIN);
-
- next_step = DOWNLOAD_UPDATES;
- break;
- case DOWNLOAD_UPDATES: {
- // TODO(akalin): We may want to propagate this switch up
- // eventually.
-#if defined(OS_ANDROID) || defined(OS_IOS)
- const bool kCreateMobileBookmarksFolder = true;
-#else
- const bool kCreateMobileBookmarksFolder = false;
-#endif
- DownloadUpdatesCommand download_updates(kCreateMobileBookmarksFolder);
- session->mutable_status_controller()->set_last_download_updates_result(
- download_updates.Execute(session));
- next_step = PROCESS_UPDATES;
- break;
- }
- case PROCESS_UPDATES: {
- ProcessUpdatesCommand process_updates;
- process_updates.Execute(session);
- next_step = STORE_TIMESTAMPS;
- break;
- }
- case STORE_TIMESTAMPS: {
- StoreTimestampsCommand store_timestamps;
- store_timestamps.Execute(session);
- session->SendEventNotification(SyncEngineEvent::STATUS_CHANGED);
- // We download all of the updates before attempting to apply them.
- if (!session->status_controller().download_updates_succeeded()) {
- // We may have downloaded some updates, but if the latest download
- // attempt failed then we don't have all the updates. We'll leave
- // it to a retry job to pick up where we left off.
- last_step = SYNCER_END; // Necessary for CONFIGURATION mode.
- next_step = SYNCER_END;
- DVLOG(1) << "Aborting sync cycle due to download updates failure";
- } else if (!session->status_controller()
- .ServerSaysNothingMoreToDownload()) {
- next_step = DOWNLOAD_UPDATES;
- } else {
- next_step = APPLY_UPDATES;
- }
- break;
- }
- case APPLY_UPDATES: {
- // These include encryption updates that should be applied early.
- ApplyControlDataUpdates(session);
-
- ApplyUpdatesAndResolveConflictsCommand apply_updates;
- apply_updates.Execute(session);
-
- session->context()->set_hierarchy_conflict_detected(
- session->status_controller().num_hierarchy_conflicts() > 0);
-
- session->SendEventNotification(SyncEngineEvent::STATUS_CHANGED);
- if (last_step == APPLY_UPDATES) {
- // We're in configuration mode, but we still need to run the
- // SYNCER_END step.
- last_step = SYNCER_END;
- next_step = SYNCER_END;
- } else {
- next_step = COMMIT;
- }
- break;
- }
- case COMMIT: {
- session->mutable_status_controller()->set_commit_result(
- BuildAndPostCommits(this, session));
- next_step = SYNCER_END;
- break;
- }
- case SYNCER_END: {
- session->SendEventNotification(SyncEngineEvent::SYNC_CYCLE_ENDED);
- next_step = SYNCER_END;
- break;
- }
- default:
- LOG(ERROR) << "Unknown command: " << current_step;
- } // switch
- DVLOG(2) << "last step: " << SyncerStepToString(last_step) << ", "
- << "current step: " << SyncerStepToString(current_step) << ", "
- << "next step: " << SyncerStepToString(next_step) << ", "
- << "snapshot: " << session->TakeSnapshot().ToString();
- if (last_step == current_step)
- return true;
- current_step = next_step;
- } // while
- return false;
+ session->SendEventNotification(SyncEngineEvent::SYNC_CYCLE_BEGIN);
}
-void CopyServerFields(syncable::Entry* src, syncable::MutableEntry* dest) {
- dest->Put(SERVER_NON_UNIQUE_NAME, src->Get(SERVER_NON_UNIQUE_NAME));
- dest->Put(SERVER_PARENT_ID, src->Get(SERVER_PARENT_ID));
- dest->Put(SERVER_MTIME, src->Get(SERVER_MTIME));
- dest->Put(SERVER_CTIME, src->Get(SERVER_CTIME));
- dest->Put(SERVER_VERSION, src->Get(SERVER_VERSION));
- dest->Put(SERVER_IS_DIR, src->Get(SERVER_IS_DIR));
- dest->Put(SERVER_IS_DEL, src->Get(SERVER_IS_DEL));
- dest->Put(IS_UNAPPLIED_UPDATE, src->Get(IS_UNAPPLIED_UPDATE));
- dest->Put(SERVER_SPECIFICS, src->Get(SERVER_SPECIFICS));
- dest->Put(SERVER_UNIQUE_POSITION, src->Get(SERVER_UNIQUE_POSITION));
+bool Syncer::HandleCycleEnd(SyncSession* session) {
+ if (!ExitRequested()) {
+ session->SendEventNotification(SyncEngineEvent::SYNC_CYCLE_ENDED);
+ return true;
+ } else {
+ return false;
+ }
}
} // namespace syncer