// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "components/sync_driver/model_association_manager.h"

#include <algorithm>
#include <functional>

#include "base/debug/trace_event.h"
#include "base/logging.h"
#include "base/message_loop/message_loop.h"
#include "base/metrics/histogram.h"
#include "sync/internal_api/public/base/model_type.h"

using syncer::ModelTypeSet;

namespace browser_sync {

namespace {

static const syncer::ModelType kStartOrder[] = {
  syncer::NIGORI,               //  Listed for completeness.
  syncer::DEVICE_INFO,          //  Listed for completeness.
  syncer::EXPERIMENTS,          //  Listed for completeness.
  syncer::PROXY_TABS,           //  Listed for completeness.

  // Kick off the association of the non-UI types first so they can associate
  // in parallel with the UI types.
  syncer::PASSWORDS,
  syncer::AUTOFILL,
  syncer::AUTOFILL_PROFILE,
  syncer::EXTENSION_SETTINGS,
  syncer::APP_SETTINGS,
  syncer::TYPED_URLS,
  syncer::HISTORY_DELETE_DIRECTIVES,
  syncer::SYNCED_NOTIFICATIONS,
  syncer::SYNCED_NOTIFICATION_APP_INFO,

  // UI thread data types.
  syncer::BOOKMARKS,
  syncer::SUPERVISED_USERS,     //  Syncing supervised users on initial login
                                //  might block creating a new supervised user,
                                //  so we want to do it early.
  syncer::PREFERENCES,
  syncer::PRIORITY_PREFERENCES,
  syncer::EXTENSIONS,
  syncer::APPS,
  syncer::APP_LIST,
  syncer::THEMES,
  syncer::SEARCH_ENGINES,
  syncer::SESSIONS,
  syncer::APP_NOTIFICATIONS,
  syncer::DICTIONARY,
  syncer::FAVICON_IMAGES,
  syncer::FAVICON_TRACKING,
  syncer::SUPERVISED_USER_SETTINGS,
  syncer::SUPERVISED_USER_SHARED_SETTINGS,
  syncer::ARTICLES,
};

COMPILE_ASSERT(arraysize(kStartOrder) ==
               syncer::MODEL_TYPE_COUNT - syncer::FIRST_REAL_MODEL_TYPE,
               kStartOrder_IncorrectSize);

// The amount of time we wait for association to finish. If some types haven't
// finished association by the time, configuration result will be
// PARTIAL_SUCCESS and DataTypeManager is notified of the unfinished types.
const int64 kAssociationTimeOutInSeconds = 600;

syncer::DataTypeAssociationStats BuildAssociationStatsFromMergeResults(
    const syncer::SyncMergeResult& local_merge_result,
    const syncer::SyncMergeResult& syncer_merge_result,
    const base::TimeDelta& association_wait_time,
    const base::TimeDelta& association_time) {
  DCHECK_EQ(local_merge_result.model_type(), syncer_merge_result.model_type());
  syncer::DataTypeAssociationStats stats;
  stats.had_error = local_merge_result.error().IsSet() ||
                    syncer_merge_result.error().IsSet();
  stats.num_local_items_before_association =
      local_merge_result.num_items_before_association();
  stats.num_sync_items_before_association =
      syncer_merge_result.num_items_before_association();
  stats.num_local_items_after_association =
      local_merge_result.num_items_after_association();
  stats.num_sync_items_after_association =
      syncer_merge_result.num_items_after_association();
  stats.num_local_items_added =
      local_merge_result.num_items_added();
  stats.num_local_items_deleted =
      local_merge_result.num_items_deleted();
  stats.num_local_items_modified =
      local_merge_result.num_items_modified();
  stats.local_version_pre_association =
      local_merge_result.pre_association_version();
  stats.num_sync_items_added =
      syncer_merge_result.num_items_added();
  stats.num_sync_items_deleted =
      syncer_merge_result.num_items_deleted();
  stats.num_sync_items_modified =
      syncer_merge_result.num_items_modified();
  stats.sync_version_pre_association =
      syncer_merge_result.pre_association_version();
  stats.association_wait_time = association_wait_time;
  stats.association_time = association_time;
  return stats;
}

}  // namespace

ModelAssociationManager::ModelAssociationManager(
    const DataTypeController::TypeMap* controllers,
    ModelAssociationManagerDelegate* processor)
    : state_(IDLE),
      controllers_(controllers),
      delegate_(processor),
      weak_ptr_factory_(this),
      configure_status_(DataTypeManager::UNKNOWN) {
  // Ensure all data type controllers are stopped.
  for (DataTypeController::TypeMap::const_iterator it = controllers_->begin();
       it != controllers_->end(); ++it) {
    DCHECK_EQ(DataTypeController::NOT_RUNNING, (*it).second->state());
  }
}

ModelAssociationManager::~ModelAssociationManager() {
}

void ModelAssociationManager::Initialize(syncer::ModelTypeSet desired_types) {
  // state_ can be INITIALIZED_TO_CONFIGURE if types are reconfigured when
  // data is being downloaded, so StartAssociationAsync() is never called for
  // the first configuration.
  DCHECK_NE(CONFIGURING, state_);

  // Only keep types that have controllers.
  desired_types_.Clear();
  slow_types_.Clear();
  for (syncer::ModelTypeSet::Iterator it = desired_types.First();
      it.Good(); it.Inc()) {
    if (controllers_->find(it.Get()) != controllers_->end())
      desired_types_.Put(it.Get());
  }

  DVLOG(1) << "ModelAssociationManager: Initializing for "
           << syncer::ModelTypeSetToString(desired_types_);

  state_ = INITIALIZED_TO_CONFIGURE;

  StopDisabledTypes();
  LoadEnabledTypes();
}

void ModelAssociationManager::StopDatatype(DataTypeController* dtc) {
  // First tell the sync backend that we no longer want to listen to
  // changes for this type.
  delegate_->OnSingleDataTypeWillStop(dtc->type());

  // Then tell all data type specific logic to shut down.
  dtc->Stop();
}

void ModelAssociationManager::StopDisabledTypes() {
  DVLOG(1) << "ModelAssociationManager: Stopping disabled types.";
  for (DataTypeController::TypeMap::const_iterator it = controllers_->begin();
       it != controllers_->end(); ++it) {
    DataTypeController* dtc = (*it).second.get();
    if (dtc->state() != DataTypeController::NOT_RUNNING &&
        (!desired_types_.Has(dtc->type()) ||
            failed_data_types_info_.count(dtc->type()) > 0)) {
      DVLOG(1) << "ModelTypeToString: stop " << dtc->name();
      StopDatatype(dtc);
      loaded_types_.Remove(dtc->type());
      associated_types_.Remove(dtc->type());
    }
  }
}

void ModelAssociationManager::LoadEnabledTypes() {
  // Load in kStartOrder.
  for (size_t i = 0; i < arraysize(kStartOrder); i++) {
    syncer::ModelType type = kStartOrder[i];
    if (!desired_types_.Has(type))
      continue;

    DCHECK(controllers_->find(type) != controllers_->end());
    DataTypeController* dtc = controllers_->find(type)->second.get();
    if (dtc->state() == DataTypeController::NOT_RUNNING) {
      DCHECK(!loaded_types_.Has(dtc->type()));
      DCHECK(!associated_types_.Has(dtc->type()));
      dtc->LoadModels(base::Bind(&ModelAssociationManager::ModelLoadCallback,
                                 weak_ptr_factory_.GetWeakPtr()));
    }
  }
}

void ModelAssociationManager::StartAssociationAsync(
    const syncer::ModelTypeSet& types_to_associate) {
  DCHECK_NE(CONFIGURING, state_);
  state_ = CONFIGURING;

  association_start_time_ = base::TimeTicks::Now();

  requested_types_ = types_to_associate;

  associating_types_ = types_to_associate;
  associating_types_.RetainAll(desired_types_);
  associating_types_.RemoveAll(associated_types_);

  // Assume success.
  configure_status_ = DataTypeManager::OK;

  // Remove types that already failed.
  for (std::map<syncer::ModelType, syncer::SyncError>::const_iterator it =
          failed_data_types_info_.begin();
      it != failed_data_types_info_.end(); ++it) {
    associating_types_.Remove(it->first);
  }

  // Done if no types to associate.
  if (associating_types_.Empty()) {
    ModelAssociationDone();
    return;
  }

  timer_.Start(FROM_HERE,
               base::TimeDelta::FromSeconds(kAssociationTimeOutInSeconds),
               this,
               &ModelAssociationManager::ModelAssociationDone);

  // Start association of types that are loaded in specified order.
  for (size_t i = 0; i < arraysize(kStartOrder); i++) {
    syncer::ModelType type = kStartOrder[i];
    if (!associating_types_.Has(type) || !loaded_types_.Has(type))
      continue;

    DataTypeController* dtc = controllers_->find(type)->second.get();
    DCHECK(DataTypeController::MODEL_LOADED == dtc->state() ||
           DataTypeController::ASSOCIATING == dtc->state());
    if (dtc->state() == DataTypeController::MODEL_LOADED) {
      TRACE_EVENT_ASYNC_BEGIN1("sync", "ModelAssociation",
                               dtc,
                               "DataType",
                               ModelTypeToString(type));

      dtc->StartAssociating(
          base::Bind(&ModelAssociationManager::TypeStartCallback,
                     weak_ptr_factory_.GetWeakPtr(),
                     type, base::TimeTicks::Now()));
    }
  }
}

void ModelAssociationManager::ResetForNextAssociation() {
  DVLOG(1) << "ModelAssociationManager: Reseting for next configuration";
  // |loaded_types_| and |associated_types_| are not cleared. So
  // reconfiguration won't restart types that are already started.
  requested_types_.Clear();
  failed_data_types_info_.clear();
  associating_types_.Clear();
  needs_crypto_types_.Clear();
}

void ModelAssociationManager::Stop() {
  // Ignore callbacks from controllers.
  weak_ptr_factory_.InvalidateWeakPtrs();

  // Stop started data types.
  for (DataTypeController::TypeMap::const_iterator it = controllers_->begin();
       it != controllers_->end(); ++it) {
    DataTypeController* dtc = (*it).second.get();
    if (dtc->state() != DataTypeController::NOT_RUNNING) {
      StopDatatype(dtc);
      DVLOG(1) << "ModelAssociationManager: Stopped " << dtc->name();
    }
  }

  desired_types_.Clear();
  loaded_types_.Clear();
  associated_types_.Clear();
  slow_types_.Clear();

  if (state_ == CONFIGURING) {
    if (configure_status_ == DataTypeManager::OK)
      configure_status_ = DataTypeManager::ABORTED;
    DVLOG(1) << "ModelAssociationManager: Calling OnModelAssociationDone";
    ModelAssociationDone();
  }

  ResetForNextAssociation();

  state_ = IDLE;
}

void ModelAssociationManager::AppendToFailedDatatypesAndLogError(
    const syncer::SyncError& error) {
  failed_data_types_info_[error.model_type()] = error;
  LOG(ERROR) << "Failed to associate models for "
             << syncer::ModelTypeToString(error.model_type());
  UMA_HISTOGRAM_ENUMERATION("Sync.ConfigureFailed",
                            ModelTypeToHistogramInt(error.model_type()),
                            syncer::MODEL_TYPE_COUNT);
}

void ModelAssociationManager::ModelLoadCallback(syncer::ModelType type,
                                                syncer::SyncError error) {
  DVLOG(1) << "ModelAssociationManager: ModelLoadCallback for "
      << syncer::ModelTypeToString(type);

  // TODO(haitaol): temporary fix for 335606.
  if (slow_types_.Has(type))
    return;

  // This happens when slow loading type is disabled by new configuration.
  if (!desired_types_.Has(type))
    return;

  DCHECK(!loaded_types_.Has(type));
  if (error.IsSet()) {
    syncer::SyncMergeResult local_merge_result(type);
    local_merge_result.set_error(error);
    TypeStartCallback(type,
                      base::TimeTicks::Now(),
                      DataTypeController::ASSOCIATION_FAILED,
                      local_merge_result,
                      syncer::SyncMergeResult(type));
    return;
  }

  loaded_types_.Put(type);
  if (associating_types_.Has(type) || slow_types_.Has(type)) {
    DataTypeController* dtc = controllers_->find(type)->second.get();
    dtc->StartAssociating(
        base::Bind(&ModelAssociationManager::TypeStartCallback,
                   weak_ptr_factory_.GetWeakPtr(),
                   type, base::TimeTicks::Now()));
  }
}

void ModelAssociationManager::TypeStartCallback(
    syncer::ModelType type,
    base::TimeTicks type_start_time,
    DataTypeController::StartResult start_result,
    const syncer::SyncMergeResult& local_merge_result,
    const syncer::SyncMergeResult& syncer_merge_result) {
  // TODO(haitaol): temporary fix for 335606.
  if (slow_types_.Has(type))
    return;

  // This happens when slow associating type is disabled by new configuration.
  if (!desired_types_.Has(type))
    return;

  slow_types_.Remove(type);

  DCHECK(!associated_types_.Has(type));
  if (DataTypeController::IsSuccessfulResult(start_result)) {
    associated_types_.Put(type);
  } else if (state_ == IDLE) {
    // For type that failed in IDLE mode, simply stop the controller. Next
    // configuration will try to restart from scratch if the type is still
    // enabled.
    DataTypeController* dtc = controllers_->find(type)->second.get();
    if (dtc->state() != DataTypeController::NOT_RUNNING)
      StopDatatype(dtc);
    loaded_types_.Remove(type);
  } else {
    // Record error in CONFIGURING or INITIALIZED_TO_CONFIGURE mode. The error
    // will be reported when data types association finishes.
    if (start_result == DataTypeController::NEEDS_CRYPTO) {
      DVLOG(1) << "ModelAssociationManager: Encountered an undecryptable type";
      needs_crypto_types_.Put(type);
    } else {
      DVLOG(1) << "ModelAssociationManager: Encountered a failed type";
      AppendToFailedDatatypesAndLogError(local_merge_result.error());
    }
  }

  if (state_ != CONFIGURING)
    return;

  TRACE_EVENT_ASYNC_END1("sync", "ModelAssociation",
                         controllers_->find(type)->second.get(),
                         "DataType",
                         ModelTypeToString(type));

  // Track the merge results if we succeeded or an association failure
  // occurred.
  if ((DataTypeController::IsSuccessfulResult(start_result) ||
       start_result == DataTypeController::ASSOCIATION_FAILED) &&
      syncer::ProtocolTypes().Has(type)) {
    base::TimeDelta association_wait_time =
        std::max(base::TimeDelta(), type_start_time - association_start_time_);
    base::TimeDelta association_time =
        base::TimeTicks::Now() - type_start_time;;
    syncer::DataTypeAssociationStats stats =
        BuildAssociationStatsFromMergeResults(local_merge_result,
                                              syncer_merge_result,
                                              association_wait_time,
                                              association_time);
    delegate_->OnSingleDataTypeAssociationDone(type, stats);
  }

  // Update configuration result.
  if (configure_status_ == DataTypeManager::OK &&
      start_result == DataTypeController::ASSOCIATION_FAILED) {
    configure_status_ = DataTypeManager::PARTIAL_SUCCESS;
  }
  if (start_result == DataTypeController::UNRECOVERABLE_ERROR)
    configure_status_ = DataTypeManager::UNRECOVERABLE_ERROR;

  associating_types_.Remove(type);

  if (associating_types_.Empty())
    ModelAssociationDone();
}

void ModelAssociationManager::ModelAssociationDone() {
  CHECK_EQ(CONFIGURING, state_);

  timer_.Stop();

  slow_types_.PutAll(associating_types_);

  // TODO(haitaol): temporary fix for 335606.
  for (syncer::ModelTypeSet::Iterator it = associating_types_.First();
      it.Good(); it.Inc()) {
    AppendToFailedDatatypesAndLogError(
        syncer::SyncError(FROM_HERE, syncer::SyncError::DATATYPE_ERROR,
                          "Association timed out.", it.Get()));
  }

  // Stop controllers of failed types.
  StopDisabledTypes();

  if (configure_status_ == DataTypeManager::OK &&
      (!associating_types_.Empty() || !failed_data_types_info_.empty() ||
          !needs_crypto_types_.Empty())) {
    // We have not configured all types that we have been asked to configure.
    // Either we have failed types or types that have not completed loading
    // yet.
    DVLOG(1) << "ModelAssociationManager: setting partial success";
    configure_status_ = DataTypeManager::PARTIAL_SUCCESS;
  }

  DataTypeManager::ConfigureResult result(configure_status_,
                                          requested_types_,
                                          failed_data_types_info_,
                                          associating_types_,
                                          needs_crypto_types_);

  // Reset state before notifying |delegate_| because that might
  // trigger a new round of configuration.
  ResetForNextAssociation();
  state_ = IDLE;

  delegate_->OnModelAssociationDone(result);
}

base::OneShotTimer<ModelAssociationManager>*
    ModelAssociationManager::GetTimerForTesting() {
  return &timer_;
}

}  // namespace browser_sync
